mirror of
https://github.com/Thealexbarney/LibHac.git
synced 2024-11-14 10:49:41 +01:00
Add StatusReportService
This commit is contained in:
parent
e5291eb06a
commit
2f9fbdb818
10 changed files with 309 additions and 74 deletions
|
@ -5,17 +5,16 @@ namespace LibHac.Fs
|
||||||
[StructLayout(LayoutKind.Sequential, Size = 0x80)]
|
[StructLayout(LayoutKind.Sequential, Size = 0x80)]
|
||||||
public struct MemoryReportInfo
|
public struct MemoryReportInfo
|
||||||
{
|
{
|
||||||
long PooledBufferFreeSizePeak;
|
public long PooledBufferFreeSizePeak;
|
||||||
long PooledBufferRetriedCount;
|
public long PooledBufferRetriedCount;
|
||||||
long PooledBufferReduceAllocationCount;
|
public long PooledBufferReduceAllocationCount;
|
||||||
long BufferManagerFreeSizePeak;
|
public long BufferManagerFreeSizePeak;
|
||||||
long BufferManagerRetiredCount;
|
public long BufferManagerRetriedCount;
|
||||||
long ExpHeapFreeSizePeak;
|
public long ExpHeapFreeSizePeak;
|
||||||
long BufferPoolFreeSizePeak;
|
public long BufferPoolFreeSizePeak;
|
||||||
long PatrolAllocateSuccessCount;
|
public long PatrolAllocateSuccessCount;
|
||||||
long PatrolAllocateFailureCount;
|
public long PatrolAllocateFailureCount;
|
||||||
long BufferManagerTotalAllocatableSizePeak;
|
public long BufferManagerTotalAllocatableSizePeak;
|
||||||
long BufferPoolAllocateSizeMax;
|
public long BufferPoolAllocateSizeMax;
|
||||||
};
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -9,4 +9,6 @@ namespace LibHac.FsSrv
|
||||||
|
|
||||||
public delegate Result SaveTransferCmacGenerator(Span<byte> mac, ReadOnlySpan<byte> data,
|
public delegate Result SaveTransferCmacGenerator(Span<byte> mac, ReadOnlySpan<byte> data,
|
||||||
SaveDataTransferCryptoConfiguration.KeyIndex index, int keyGeneration);
|
SaveDataTransferCryptoConfiguration.KeyIndex index, int keyGeneration);
|
||||||
|
|
||||||
|
public delegate Result PatrolAllocateCountGetter(out long successCount, out long failureCount);
|
||||||
}
|
}
|
||||||
|
|
|
@ -10,6 +10,7 @@ namespace LibHac.FsSrv
|
||||||
public NcaFileSystemServiceImpl NcaFileSystemService { get; set; }
|
public NcaFileSystemServiceImpl NcaFileSystemService { get; set; }
|
||||||
public SaveDataFileSystemServiceImpl SaveDataFileSystemService { get; set; }
|
public SaveDataFileSystemServiceImpl SaveDataFileSystemService { get; set; }
|
||||||
public TimeServiceImpl TimeService { get; set; }
|
public TimeServiceImpl TimeService { get; set; }
|
||||||
|
public StatusReportServiceImpl StatusReportService { get; set; }
|
||||||
public ProgramRegistryServiceImpl ProgramRegistryService { get; set; }
|
public ProgramRegistryServiceImpl ProgramRegistryService { get; set; }
|
||||||
public AccessLogServiceImpl AccessLogService { get; set; }
|
public AccessLogServiceImpl AccessLogService { get; set; }
|
||||||
}
|
}
|
||||||
|
|
|
@ -28,6 +28,65 @@ namespace LibHac.FsSrv
|
||||||
CurrentProcess = ulong.MaxValue;
|
CurrentProcess = ulong.MaxValue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private Result GetProgramInfo(out ProgramInfo programInfo)
|
||||||
|
{
|
||||||
|
return FsProxyCore.ProgramRegistry.GetProgramInfo(out programInfo, CurrentProcess);
|
||||||
|
}
|
||||||
|
|
||||||
|
private Result GetNcaFileSystemService(out NcaFileSystemService ncaFsService)
|
||||||
|
{
|
||||||
|
if (NcaFsService is null)
|
||||||
|
{
|
||||||
|
ncaFsService = null;
|
||||||
|
return ResultFs.PreconditionViolation.Log();
|
||||||
|
}
|
||||||
|
|
||||||
|
ncaFsService = NcaFsService.Target;
|
||||||
|
return Result.Success;
|
||||||
|
}
|
||||||
|
|
||||||
|
private Result GetSaveDataFileSystemService(out SaveDataFileSystemService saveFsService)
|
||||||
|
{
|
||||||
|
if (SaveFsService is null)
|
||||||
|
{
|
||||||
|
saveFsService = null;
|
||||||
|
return ResultFs.PreconditionViolation.Log();
|
||||||
|
}
|
||||||
|
|
||||||
|
saveFsService = SaveFsService.Target;
|
||||||
|
return Result.Success;
|
||||||
|
}
|
||||||
|
|
||||||
|
private BaseStorageService GetBaseStorageService()
|
||||||
|
{
|
||||||
|
return new BaseStorageService(FsProxyCore.Config.BaseStorageService, CurrentProcess);
|
||||||
|
}
|
||||||
|
|
||||||
|
private BaseFileSystemService GetBaseFileSystemService()
|
||||||
|
{
|
||||||
|
return new BaseFileSystemService(FsProxyCore.Config.BaseFileSystemService, CurrentProcess);
|
||||||
|
}
|
||||||
|
|
||||||
|
private TimeService GetTimeService()
|
||||||
|
{
|
||||||
|
return new TimeService(FsProxyCore.Config.TimeService, CurrentProcess);
|
||||||
|
}
|
||||||
|
|
||||||
|
private StatusReportService GetStatusReportService()
|
||||||
|
{
|
||||||
|
return new StatusReportService(FsProxyCore.Config.StatusReportService);
|
||||||
|
}
|
||||||
|
|
||||||
|
private ProgramIndexRegistryService GetProgramIndexRegistryService()
|
||||||
|
{
|
||||||
|
return new ProgramIndexRegistryService(FsProxyCore.Config.ProgramRegistryService, CurrentProcess);
|
||||||
|
}
|
||||||
|
|
||||||
|
private AccessLogService GetAccessLogService()
|
||||||
|
{
|
||||||
|
return new AccessLogService(FsProxyCore.Config.AccessLogService, CurrentProcess);
|
||||||
|
}
|
||||||
|
|
||||||
public Result OpenFileSystemWithId(out ReferenceCountedDisposable<IFileSystemSf> fileSystem, in FspPath path,
|
public Result OpenFileSystemWithId(out ReferenceCountedDisposable<IFileSystemSf> fileSystem, in FspPath path,
|
||||||
ulong id, FileSystemProxyType fsType)
|
ulong id, FileSystemProxyType fsType)
|
||||||
{
|
{
|
||||||
|
@ -863,7 +922,7 @@ namespace LibHac.FsSrv
|
||||||
|
|
||||||
public Result GetAndClearErrorInfo(out FileSystemProxyErrorInfo errorInfo)
|
public Result GetAndClearErrorInfo(out FileSystemProxyErrorInfo errorInfo)
|
||||||
{
|
{
|
||||||
throw new NotImplementedException();
|
return GetStatusReportService().GetAndClearFileSystemProxyErrorInfo(out errorInfo);
|
||||||
}
|
}
|
||||||
|
|
||||||
public Result RegisterProgramIndexMapInfo(InBuffer programIndexMapInfoBuffer, int programCount)
|
public Result RegisterProgramIndexMapInfo(InBuffer programIndexMapInfoBuffer, int programCount)
|
||||||
|
@ -984,14 +1043,14 @@ namespace LibHac.FsSrv
|
||||||
return ncaFsService.OpenRegisteredUpdatePartition(out fileSystem);
|
return ncaFsService.OpenRegisteredUpdatePartition(out fileSystem);
|
||||||
}
|
}
|
||||||
|
|
||||||
public Result GetAndClearMemoryReportInfo(out MemoryReportInfo report)
|
public Result GetAndClearMemoryReportInfo(out MemoryReportInfo reportInfo)
|
||||||
{
|
{
|
||||||
throw new NotImplementedException();
|
return GetStatusReportService().GetAndClearMemoryReportInfo(out reportInfo);
|
||||||
}
|
}
|
||||||
|
|
||||||
public Result GetFsStackUsage(out uint stackUsage, FsStackUsageThreadType threadType)
|
public Result GetFsStackUsage(out uint stackUsage, FsStackUsageThreadType threadType)
|
||||||
{
|
{
|
||||||
throw new NotImplementedException();
|
return GetStatusReportService().GetFsStackUsage(out stackUsage, threadType);
|
||||||
}
|
}
|
||||||
|
|
||||||
public Result OverrideSaveDataTransferTokenSignVerificationKey(InBuffer key)
|
public Result OverrideSaveDataTransferTokenSignVerificationKey(InBuffer key)
|
||||||
|
@ -1058,59 +1117,5 @@ namespace LibHac.FsSrv
|
||||||
{
|
{
|
||||||
return GetBaseFileSystemService().OpenBisWiper(out bisWiper, transferMemoryHandle, transferMemorySize);
|
return GetBaseFileSystemService().OpenBisWiper(out bisWiper, transferMemoryHandle, transferMemorySize);
|
||||||
}
|
}
|
||||||
|
|
||||||
private Result GetProgramInfo(out ProgramInfo programInfo)
|
|
||||||
{
|
|
||||||
return FsProxyCore.ProgramRegistry.GetProgramInfo(out programInfo, CurrentProcess);
|
|
||||||
}
|
|
||||||
|
|
||||||
private Result GetNcaFileSystemService(out NcaFileSystemService ncaFsService)
|
|
||||||
{
|
|
||||||
if (NcaFsService is null)
|
|
||||||
{
|
|
||||||
ncaFsService = null;
|
|
||||||
return ResultFs.PreconditionViolation.Log();
|
|
||||||
}
|
|
||||||
|
|
||||||
ncaFsService = NcaFsService.Target;
|
|
||||||
return Result.Success;
|
|
||||||
}
|
|
||||||
|
|
||||||
private Result GetSaveDataFileSystemService(out SaveDataFileSystemService saveFsService)
|
|
||||||
{
|
|
||||||
if (SaveFsService is null)
|
|
||||||
{
|
|
||||||
saveFsService = null;
|
|
||||||
return ResultFs.PreconditionViolation.Log();
|
|
||||||
}
|
|
||||||
|
|
||||||
saveFsService = SaveFsService.Target;
|
|
||||||
return Result.Success;
|
|
||||||
}
|
|
||||||
|
|
||||||
private BaseStorageService GetBaseStorageService()
|
|
||||||
{
|
|
||||||
return new BaseStorageService(FsProxyCore.Config.BaseStorageService, CurrentProcess);
|
|
||||||
}
|
|
||||||
|
|
||||||
private BaseFileSystemService GetBaseFileSystemService()
|
|
||||||
{
|
|
||||||
return new BaseFileSystemService(FsProxyCore.Config.BaseFileSystemService, CurrentProcess);
|
|
||||||
}
|
|
||||||
|
|
||||||
private TimeService GetTimeService()
|
|
||||||
{
|
|
||||||
return new TimeService(FsProxyCore.Config.TimeService, CurrentProcess);
|
|
||||||
}
|
|
||||||
|
|
||||||
private ProgramIndexRegistryService GetProgramIndexRegistryService()
|
|
||||||
{
|
|
||||||
return new ProgramIndexRegistryService(FsProxyCore.Config.ProgramRegistryService, CurrentProcess);
|
|
||||||
}
|
|
||||||
|
|
||||||
private AccessLogService GetAccessLogService()
|
|
||||||
{
|
|
||||||
return new AccessLogService(FsProxyCore.Config.AccessLogService, CurrentProcess);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,10 +1,12 @@
|
||||||
using System;
|
using System;
|
||||||
|
using LibHac.Diag;
|
||||||
using LibHac.Fs;
|
using LibHac.Fs;
|
||||||
using LibHac.Fs.Impl;
|
using LibHac.Fs.Impl;
|
||||||
using LibHac.Fs.Shim;
|
using LibHac.Fs.Shim;
|
||||||
using LibHac.FsSrv.Creators;
|
using LibHac.FsSrv.Creators;
|
||||||
using LibHac.FsSrv.Impl;
|
using LibHac.FsSrv.Impl;
|
||||||
using LibHac.FsSrv.Sf;
|
using LibHac.FsSrv.Sf;
|
||||||
|
using LibHac.FsSrv.Storage;
|
||||||
using LibHac.Sm;
|
using LibHac.Sm;
|
||||||
|
|
||||||
namespace LibHac.FsSrv
|
namespace LibHac.FsSrv
|
||||||
|
@ -17,6 +19,7 @@ namespace LibHac.FsSrv
|
||||||
private const ulong SpeedEmulationProgramIdMaximum = 0x100000000001FFF;
|
private const ulong SpeedEmulationProgramIdMaximum = 0x100000000001FFF;
|
||||||
|
|
||||||
private FileSystemProxyCoreImpl FsProxyCore { get; }
|
private FileSystemProxyCoreImpl FsProxyCore { get; }
|
||||||
|
public StorageService Storage { get; }
|
||||||
|
|
||||||
/// <summary>The client instance to be used for internal operations like save indexer access.</summary>
|
/// <summary>The client instance to be used for internal operations like save indexer access.</summary>
|
||||||
public HorizonClient Hos { get; }
|
public HorizonClient Hos { get; }
|
||||||
|
@ -48,6 +51,8 @@ namespace LibHac.FsSrv
|
||||||
|
|
||||||
Hos = horizonClient;
|
Hos = horizonClient;
|
||||||
|
|
||||||
|
Storage = new StorageService(this);
|
||||||
|
|
||||||
IsDebugMode = false;
|
IsDebugMode = false;
|
||||||
|
|
||||||
Timer = config.TimeSpanGenerator ?? new StopWatchTimeSpanGenerator();
|
Timer = config.TimeSpanGenerator ?? new StopWatchTimeSpanGenerator();
|
||||||
|
@ -155,6 +160,19 @@ namespace LibHac.FsSrv
|
||||||
|
|
||||||
var saveFsService = new SaveDataFileSystemServiceImpl(in saveFsServiceConfig);
|
var saveFsService = new SaveDataFileSystemServiceImpl(in saveFsServiceConfig);
|
||||||
|
|
||||||
|
var statusReportServiceConfig = new StatusReportServiceImpl.Configuration();
|
||||||
|
statusReportServiceConfig.NcaFsServiceImpl = ncaFsService;
|
||||||
|
statusReportServiceConfig.SaveFsServiceImpl = saveFsService;
|
||||||
|
statusReportServiceConfig.BufferManagerMemoryReport = null;
|
||||||
|
statusReportServiceConfig.ExpHeapMemoryReport = null;
|
||||||
|
statusReportServiceConfig.BufferPoolMemoryReport = null;
|
||||||
|
statusReportServiceConfig.GetPatrolAllocateCounts = null;
|
||||||
|
statusReportServiceConfig.MainThreadStackUsageReporter = new DummyStackUsageReporter();
|
||||||
|
statusReportServiceConfig.IpcWorkerThreadStackUsageReporter = new DummyStackUsageReporter();
|
||||||
|
statusReportServiceConfig.PipeLineWorkerThreadStackUsageReporter = new DummyStackUsageReporter();
|
||||||
|
|
||||||
|
var statusReportService = new StatusReportServiceImpl(in statusReportServiceConfig);
|
||||||
|
|
||||||
var accessLogServiceConfig = new AccessLogServiceImpl.Configuration();
|
var accessLogServiceConfig = new AccessLogServiceImpl.Configuration();
|
||||||
accessLogServiceConfig.MinimumProgramIdForSdCardLog = 0x0100000000003000;
|
accessLogServiceConfig.MinimumProgramIdForSdCardLog = 0x0100000000003000;
|
||||||
accessLogServiceConfig.HorizonClient = Hos;
|
accessLogServiceConfig.HorizonClient = Hos;
|
||||||
|
@ -169,6 +187,7 @@ namespace LibHac.FsSrv
|
||||||
NcaFileSystemService = ncaFsService,
|
NcaFileSystemService = ncaFsService,
|
||||||
SaveDataFileSystemService = saveFsService,
|
SaveDataFileSystemService = saveFsService,
|
||||||
TimeService = timeService,
|
TimeService = timeService,
|
||||||
|
StatusReportService = statusReportService,
|
||||||
ProgramRegistryService = programRegistryService,
|
ProgramRegistryService = programRegistryService,
|
||||||
AccessLogService = accessLogService
|
AccessLogService = accessLogService
|
||||||
};
|
};
|
||||||
|
@ -238,6 +257,11 @@ namespace LibHac.FsSrv
|
||||||
return Result.Success;
|
return Result.Success;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private class DummyStackUsageReporter : IStackUsageReporter
|
||||||
|
{
|
||||||
|
public uint GetStackUsage() => 0;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
@ -268,6 +292,31 @@ namespace LibHac.FsSrv
|
||||||
public ITimeSpanGenerator TimeSpanGenerator { get; set; }
|
public ITimeSpanGenerator TimeSpanGenerator { get; set; }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public class StorageService
|
||||||
|
{
|
||||||
|
internal FileSystemServer Fs;
|
||||||
|
private IStorageDeviceManagerFactory _factory;
|
||||||
|
|
||||||
|
internal StorageService(FileSystemServer parentServer)
|
||||||
|
{
|
||||||
|
Fs = parentServer;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void SetStorageDeviceManagerFactory(IStorageDeviceManagerFactory factory)
|
||||||
|
{
|
||||||
|
Assert.NotNull(factory);
|
||||||
|
Assert.Null(_factory);
|
||||||
|
|
||||||
|
_factory = factory;
|
||||||
|
}
|
||||||
|
|
||||||
|
public IStorageDeviceManagerFactory GetStorageDeviceManagerFactory()
|
||||||
|
{
|
||||||
|
Assert.NotNull(_factory);
|
||||||
|
return _factory;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// Functions in the nn::fssrv::detail namespace use this struct.
|
// Functions in the nn::fssrv::detail namespace use this struct.
|
||||||
// Possibly move this to the main class if the separation doesn't seem necessary.
|
// Possibly move this to the main class if the separation doesn't seem necessary.
|
||||||
internal struct FileSystemServerImpl
|
internal struct FileSystemServerImpl
|
||||||
|
|
7
src/LibHac/FsSrv/IStackUsageReporter.cs
Normal file
7
src/LibHac/FsSrv/IStackUsageReporter.cs
Normal file
|
@ -0,0 +1,7 @@
|
||||||
|
namespace LibHac.FsSrv
|
||||||
|
{
|
||||||
|
public interface IStackUsageReporter
|
||||||
|
{
|
||||||
|
uint GetStackUsage();
|
||||||
|
}
|
||||||
|
}
|
11
src/LibHac/FsSrv/MemoryReport.cs
Normal file
11
src/LibHac/FsSrv/MemoryReport.cs
Normal file
|
@ -0,0 +1,11 @@
|
||||||
|
namespace LibHac.FsSrv
|
||||||
|
{
|
||||||
|
public abstract class MemoryReport
|
||||||
|
{
|
||||||
|
public abstract long GetFreeSizePeak();
|
||||||
|
public abstract long GetTotalAllocatableSizePeak();
|
||||||
|
public abstract long GetRetriedCount();
|
||||||
|
public abstract long GetAllocateSizeMax();
|
||||||
|
public abstract void Clear();
|
||||||
|
}
|
||||||
|
}
|
|
@ -612,9 +612,23 @@ namespace LibHac.FsSrv
|
||||||
return programId;
|
return programId;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void ResetTemporaryStorageIndexer()
|
public Result GetSaveDataIndexCount(out int count)
|
||||||
{
|
{
|
||||||
_config.SaveIndexerManager.ResetIndexer(SaveDataSpaceId.Temporary);
|
Unsafe.SkipInit(out count);
|
||||||
|
|
||||||
|
SaveDataIndexerAccessor accessor = null;
|
||||||
|
try
|
||||||
|
{
|
||||||
|
Result rc = OpenSaveDataIndexerAccessor(out accessor, out bool _, SaveDataSpaceId.User);
|
||||||
|
if (rc.IsFailure()) return rc;
|
||||||
|
|
||||||
|
count = accessor.Indexer.GetIndexCount();
|
||||||
|
return Result.Success;
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
accessor?.Dispose();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public Result OpenSaveDataIndexerAccessor(out SaveDataIndexerAccessor accessor, out bool neededInit,
|
public Result OpenSaveDataIndexerAccessor(out SaveDataIndexerAccessor accessor, out bool neededInit,
|
||||||
|
@ -622,5 +636,10 @@ namespace LibHac.FsSrv
|
||||||
{
|
{
|
||||||
return _config.SaveIndexerManager.OpenSaveDataIndexerAccessor(out accessor, out neededInit, spaceId);
|
return _config.SaveIndexerManager.OpenSaveDataIndexerAccessor(out accessor, out neededInit, spaceId);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void ResetTemporaryStorageIndexer()
|
||||||
|
{
|
||||||
|
_config.SaveIndexerManager.ResetIndexer(SaveDataSpaceId.Temporary);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -114,7 +114,7 @@ namespace LibHac.FsSrv.Sf
|
||||||
Result OutputAccessLogToSdCard(InBuffer textBuffer);
|
Result OutputAccessLogToSdCard(InBuffer textBuffer);
|
||||||
Result RegisterUpdatePartition();
|
Result RegisterUpdatePartition();
|
||||||
Result OpenRegisteredUpdatePartition(out ReferenceCountedDisposable<IFileSystemSf> fileSystem);
|
Result OpenRegisteredUpdatePartition(out ReferenceCountedDisposable<IFileSystemSf> fileSystem);
|
||||||
Result GetAndClearMemoryReportInfo(out MemoryReportInfo report);
|
Result GetAndClearMemoryReportInfo(out MemoryReportInfo reportInfo);
|
||||||
Result GetProgramIndexForAccessLog(out int programIndex, out int programCount);
|
Result GetProgramIndexForAccessLog(out int programIndex, out int programCount);
|
||||||
Result GetFsStackUsage(out uint stackUsage, FsStackUsageThreadType threadType);
|
Result GetFsStackUsage(out uint stackUsage, FsStackUsageThreadType threadType);
|
||||||
Result UnsetSaveDataRootPath();
|
Result UnsetSaveDataRootPath();
|
||||||
|
|
142
src/LibHac/FsSrv/StatusReportService.cs
Normal file
142
src/LibHac/FsSrv/StatusReportService.cs
Normal file
|
@ -0,0 +1,142 @@
|
||||||
|
using LibHac.Diag;
|
||||||
|
using LibHac.Fs;
|
||||||
|
using LibHac.Os;
|
||||||
|
|
||||||
|
namespace LibHac.FsSrv
|
||||||
|
{
|
||||||
|
public readonly struct StatusReportService
|
||||||
|
{
|
||||||
|
private readonly StatusReportServiceImpl _serviceImpl;
|
||||||
|
|
||||||
|
public StatusReportService(StatusReportServiceImpl serviceImpl)
|
||||||
|
{
|
||||||
|
_serviceImpl = serviceImpl;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Result GetAndClearFileSystemProxyErrorInfo(out FileSystemProxyErrorInfo errorInfo)
|
||||||
|
{
|
||||||
|
return _serviceImpl.GetAndClearFileSystemProxyErrorInfo(out errorInfo);
|
||||||
|
}
|
||||||
|
|
||||||
|
public Result GetAndClearMemoryReportInfo(out MemoryReportInfo reportInfo)
|
||||||
|
{
|
||||||
|
return _serviceImpl.GetAndClearMemoryReportInfo(out reportInfo);
|
||||||
|
}
|
||||||
|
|
||||||
|
public Result GetFsStackUsage(out uint stackUsage, FsStackUsageThreadType threadType)
|
||||||
|
{
|
||||||
|
stackUsage = _serviceImpl.ReportStackUsage(threadType);
|
||||||
|
return Result.Success;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public class StatusReportServiceImpl
|
||||||
|
{
|
||||||
|
private Configuration _config;
|
||||||
|
private SdkMutexType _mutex;
|
||||||
|
|
||||||
|
public StatusReportServiceImpl(in Configuration configuration)
|
||||||
|
{
|
||||||
|
_config = configuration;
|
||||||
|
_mutex.Initialize();
|
||||||
|
}
|
||||||
|
|
||||||
|
public struct Configuration
|
||||||
|
{
|
||||||
|
public NcaFileSystemServiceImpl NcaFsServiceImpl;
|
||||||
|
public SaveDataFileSystemServiceImpl SaveFsServiceImpl;
|
||||||
|
// Missing: FatFileSystemCreator (Not an IFatFileSystemCreator)
|
||||||
|
public MemoryReport BufferManagerMemoryReport;
|
||||||
|
public MemoryReport ExpHeapMemoryReport;
|
||||||
|
public MemoryReport BufferPoolMemoryReport;
|
||||||
|
public PatrolAllocateCountGetter GetPatrolAllocateCounts;
|
||||||
|
public IStackUsageReporter MainThreadStackUsageReporter;
|
||||||
|
public IStackUsageReporter IpcWorkerThreadStackUsageReporter;
|
||||||
|
public IStackUsageReporter PipeLineWorkerThreadStackUsageReporter;
|
||||||
|
|
||||||
|
public FileSystemServer FsServer;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Result GetAndClearFileSystemProxyErrorInfo(out FileSystemProxyErrorInfo errorInfo)
|
||||||
|
{
|
||||||
|
errorInfo = new FileSystemProxyErrorInfo();
|
||||||
|
|
||||||
|
_config.NcaFsServiceImpl.GetAndClearRomFsErrorInfo(out errorInfo.RomFsRemountForDataCorruptionCount,
|
||||||
|
out errorInfo.RomFsUnrecoverableDataCorruptionByRemountCount,
|
||||||
|
out errorInfo.RomFsRecoveredByInvalidateCacheCount);
|
||||||
|
|
||||||
|
// Missing: GetFatInfo
|
||||||
|
|
||||||
|
Result rc = _config.SaveFsServiceImpl.GetSaveDataIndexCount(out int count);
|
||||||
|
if (rc.IsFailure()) return rc;
|
||||||
|
|
||||||
|
errorInfo.SaveDataIndexCount = count;
|
||||||
|
return Result.Success;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Result GetAndClearMemoryReportInfo(out MemoryReportInfo reportInfo)
|
||||||
|
{
|
||||||
|
using ScopedLock<SdkMutexType> lk = ScopedLock.Lock(ref _mutex);
|
||||||
|
|
||||||
|
reportInfo = new MemoryReportInfo();
|
||||||
|
|
||||||
|
// Missing: Get and clear pooled buffer stats
|
||||||
|
reportInfo.PooledBufferFreeSizePeak = 0;
|
||||||
|
reportInfo.PooledBufferRetriedCount = 0;
|
||||||
|
reportInfo.PooledBufferReduceAllocationCount = 0;
|
||||||
|
|
||||||
|
MemoryReport report = _config.BufferManagerMemoryReport;
|
||||||
|
if (report != null)
|
||||||
|
{
|
||||||
|
reportInfo.BufferManagerFreeSizePeak = report.GetFreeSizePeak();
|
||||||
|
reportInfo.BufferManagerTotalAllocatableSizePeak = report.GetTotalAllocatableSizePeak();
|
||||||
|
reportInfo.BufferManagerRetriedCount = report.GetRetriedCount();
|
||||||
|
report.Clear();
|
||||||
|
}
|
||||||
|
|
||||||
|
report = _config.ExpHeapMemoryReport;
|
||||||
|
if (report != null)
|
||||||
|
{
|
||||||
|
reportInfo.ExpHeapFreeSizePeak = report.GetFreeSizePeak();
|
||||||
|
report.Clear();
|
||||||
|
}
|
||||||
|
|
||||||
|
report = _config.BufferPoolMemoryReport;
|
||||||
|
if (report != null)
|
||||||
|
{
|
||||||
|
reportInfo.BufferPoolFreeSizePeak = report.GetFreeSizePeak();
|
||||||
|
reportInfo.BufferPoolAllocateSizeMax = report.GetAllocateSizeMax();
|
||||||
|
report.Clear();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (_config.GetPatrolAllocateCounts != null)
|
||||||
|
{
|
||||||
|
_config.GetPatrolAllocateCounts(out reportInfo.PatrolAllocateSuccessCount,
|
||||||
|
out reportInfo.PatrolAllocateFailureCount);
|
||||||
|
}
|
||||||
|
|
||||||
|
return Result.Success;
|
||||||
|
}
|
||||||
|
|
||||||
|
public uint ReportStackUsage(FsStackUsageThreadType threadType)
|
||||||
|
{
|
||||||
|
switch (threadType)
|
||||||
|
{
|
||||||
|
case FsStackUsageThreadType.MainThread:
|
||||||
|
Assert.NotNull(_config.MainThreadStackUsageReporter);
|
||||||
|
return _config.MainThreadStackUsageReporter.GetStackUsage();
|
||||||
|
|
||||||
|
case FsStackUsageThreadType.IpcWorker:
|
||||||
|
Assert.NotNull(_config.IpcWorkerThreadStackUsageReporter);
|
||||||
|
return _config.IpcWorkerThreadStackUsageReporter.GetStackUsage();
|
||||||
|
|
||||||
|
case FsStackUsageThreadType.PipelineWorker:
|
||||||
|
Assert.NotNull(_config.PipeLineWorkerThreadStackUsageReporter);
|
||||||
|
return _config.PipeLineWorkerThreadStackUsageReporter.GetStackUsage();
|
||||||
|
|
||||||
|
default:
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in a new issue