Workaround the inability to access FAT attributes in Linux

This commit is contained in:
Alex Barney 2019-07-07 23:45:02 -05:00
parent 6f1596ae5f
commit 74a3929eb9
2 changed files with 54 additions and 2 deletions

View file

@ -1,5 +1,9 @@
using System.Collections.Generic; using System.Collections.Generic;
#if NETCOREAPP
using System.Runtime.InteropServices;
#endif
namespace LibHac.Fs namespace LibHac.Fs
{ {
public class ConcatenationDirectory : IDirectory public class ConcatenationDirectory : IDirectory
@ -23,7 +27,7 @@ namespace LibHac.Fs
{ {
foreach (DirectoryEntry entry in ParentDirectory.Read()) foreach (DirectoryEntry entry in ParentDirectory.Read())
{ {
bool isSplit = ConcatenationFileSystem.HasConcatenationFileAttribute(entry.Attributes); bool isSplit = IsConcatenationFile(entry);
if (!CanReturnEntry(entry, isSplit)) continue; if (!CanReturnEntry(entry, isSplit)) continue;
@ -44,7 +48,7 @@ namespace LibHac.Fs
foreach (DirectoryEntry entry in ParentDirectory.Read()) foreach (DirectoryEntry entry in ParentDirectory.Read())
{ {
bool isSplit = ConcatenationFileSystem.HasConcatenationFileAttribute(entry.Attributes); bool isSplit = IsConcatenationFile(entry);
if (CanReturnEntry(entry, isSplit)) count++; if (CanReturnEntry(entry, isSplit)) count++;
} }
@ -57,5 +61,21 @@ namespace LibHac.Fs
return Mode.HasFlag(OpenDirectoryMode.Files) && (entry.Type == DirectoryEntryType.File || isSplit) || return Mode.HasFlag(OpenDirectoryMode.Files) && (entry.Type == DirectoryEntryType.File || isSplit) ||
Mode.HasFlag(OpenDirectoryMode.Directories) && entry.Type == DirectoryEntryType.Directory && !isSplit; Mode.HasFlag(OpenDirectoryMode.Directories) && entry.Type == DirectoryEntryType.Directory && !isSplit;
} }
private bool IsConcatenationFile(DirectoryEntry entry)
{
#if NETCOREAPP
if (RuntimeInformation.IsOSPlatform(OSPlatform.Windows))
{
return ConcatenationFileSystem.HasConcatenationFileAttribute(entry.Attributes);
}
else
{
return ParentFileSystem.IsConcatenationFile(entry.FullPath);
}
#else
return ConcatenationFileSystem.HasConcatenationFileAttribute(entry.Attributes);
#endif
}
} }
} }

View file

@ -1,6 +1,10 @@
using System; using System;
using System.Collections.Generic; using System.Collections.Generic;
#if NETCOREAPP
using System.Runtime.InteropServices;
#endif
namespace LibHac.Fs namespace LibHac.Fs
{ {
public class ConcatenationFileSystem : IFileSystem public class ConcatenationFileSystem : IFileSystem
@ -17,10 +21,38 @@ namespace LibHac.Fs
SubFileSize = subFileSize; SubFileSize = subFileSize;
} }
// .NET Core on platforms other than Windows doesn't support getting the
// archive flag in FAT file systems. Try to work around that for now for reading,
// but writing still won't work properly on those platforms
internal bool IsConcatenationFile(string path) internal bool IsConcatenationFile(string path)
{ {
#if NETCOREAPP
if (RuntimeInformation.IsOSPlatform(OSPlatform.Windows))
{
return HasConcatenationFileAttribute(BaseFileSystem.GetFileAttributes(path)); return HasConcatenationFileAttribute(BaseFileSystem.GetFileAttributes(path));
} }
else
{
return IsConcatenationFileHeuristic(path);
}
#else
return HasConcatenationFileAttribute(BaseFileSystem.GetFileAttributes(path));
#endif
}
#if NETCOREAPP
private bool IsConcatenationFileHeuristic(string path)
{
if (BaseFileSystem.GetEntryType(path) != DirectoryEntryType.Directory) return false;
if (BaseFileSystem.GetEntryType(PathTools.Combine(path, "00")) != DirectoryEntryType.File) return false;
if (BaseFileSystem.OpenDirectory(path, OpenDirectoryMode.Directories).GetEntryCount() > 0) return false;
// Should be enough checks to avoid most false positives. Maybe
return true;
}
#endif
internal static bool HasConcatenationFileAttribute(NxFileAttributes attributes) internal static bool HasConcatenationFileAttribute(NxFileAttributes attributes)
{ {