forked from Atmosphere-NX/Atmosphere
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
fs: implement AccessLog, enable for File operations
- Loading branch information
Showing
36 changed files
with
1,985 additions
and
417 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
33 changes: 33 additions & 0 deletions
33
libraries/libstratosphere/include/stratosphere/fs/fs_access_log.hpp
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,33 @@ | ||
/* | ||
* Copyright (c) 2018-2020 Atmosphère-NX | ||
* | ||
* This program is free software; you can redistribute it and/or modify it | ||
* under the terms and conditions of the GNU General Public License, | ||
* version 2, as published by the Free Software Foundation. | ||
* | ||
* This program is distributed in the hope it will be useful, but WITHOUT | ||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or | ||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for | ||
* more details. | ||
* | ||
* You should have received a copy of the GNU General Public License | ||
* along with this program. If not, see <http://www.gnu.org/licenses/>. | ||
*/ | ||
#pragma once | ||
#include <vapours.hpp> | ||
|
||
namespace ams::fs { | ||
|
||
enum AccessLogMode : u32 { | ||
AccessLogMode_None = 0, | ||
AccessLogMode_Log = 1, | ||
AccessLogMode_SdCard = 2, | ||
}; | ||
|
||
Result GetGlobalAccessLogMode(u32 *out); | ||
Result SetGlobalAccessLogMode(u32 mode); | ||
|
||
void SetLocalAccessLog(bool enabled); | ||
void SetLocalSystemAccessLogForDebug(bool enabled); | ||
|
||
} |
68 changes: 68 additions & 0 deletions
68
libraries/libstratosphere/include/stratosphere/fs/fs_context.hpp
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,68 @@ | ||
/* | ||
* Copyright (c) 2018-2020 Atmosphère-NX | ||
* | ||
* This program is free software; you can redistribute it and/or modify it | ||
* under the terms and conditions of the GNU General Public License, | ||
* version 2, as published by the Free Software Foundation. | ||
* | ||
* This program is distributed in the hope it will be useful, but WITHOUT | ||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or | ||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for | ||
* more details. | ||
* | ||
* You should have received a copy of the GNU General Public License | ||
* along with this program. If not, see <http://www.gnu.org/licenses/>. | ||
*/ | ||
#pragma once | ||
#include <vapours.hpp> | ||
|
||
namespace ams::fs { | ||
|
||
enum class AbortSpecifier { | ||
Default, | ||
Abort, | ||
Return, | ||
}; | ||
|
||
using ResultHandler = AbortSpecifier (*)(Result); | ||
|
||
class FsContext { | ||
private: | ||
ResultHandler handler; | ||
public: | ||
constexpr explicit FsContext(ResultHandler h) : handler(h) { /* ... */ } | ||
|
||
constexpr void SetHandler(ResultHandler h) { this->handler = h; } | ||
|
||
constexpr AbortSpecifier HandleResult(Result result) const { return this->handler(result); } | ||
}; | ||
|
||
void SetDefaultFsContextResultHandler(const ResultHandler handler); | ||
|
||
const FsContext *GetCurrentThreadFsContext(); | ||
void SetCurrentThreadFsContext(const FsContext *context); | ||
|
||
class ScopedFsContext { | ||
private: | ||
const FsContext * const prev_context; | ||
public: | ||
ALWAYS_INLINE ScopedFsContext(const FsContext &ctx) : prev_context(GetCurrentThreadFsContext()) { | ||
SetCurrentThreadFsContext(std::addressof(ctx)); | ||
} | ||
|
||
ALWAYS_INLINE ~ScopedFsContext() { | ||
SetCurrentThreadFsContext(this->prev_context); | ||
} | ||
}; | ||
|
||
class ScopedAutoAbortDisabler { | ||
private: | ||
const FsContext * const prev_context; | ||
public: | ||
ScopedAutoAbortDisabler(); | ||
ALWAYS_INLINE ~ScopedAutoAbortDisabler() { | ||
SetCurrentThreadFsContext(this->prev_context); | ||
} | ||
}; | ||
|
||
} |
44 changes: 44 additions & 0 deletions
44
libraries/libstratosphere/include/stratosphere/fs/fs_priority.hpp
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,44 @@ | ||
/* | ||
* Copyright (c) 2018-2020 Atmosphère-NX | ||
* | ||
* This program is free software; you can redistribute it and/or modify it | ||
* under the terms and conditions of the GNU General Public License, | ||
* version 2, as published by the Free Software Foundation. | ||
* | ||
* This program is distributed in the hope it will be useful, but WITHOUT | ||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or | ||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for | ||
* more details. | ||
* | ||
* You should have received a copy of the GNU General Public License | ||
* along with this program. If not, see <http://www.gnu.org/licenses/>. | ||
*/ | ||
#pragma once | ||
#include <vapours.hpp> | ||
|
||
namespace ams::fs { | ||
|
||
enum Priority { | ||
Priority_Realtime = 0, | ||
Priority_Normal = 1, | ||
Priority_Low = 2, | ||
}; | ||
|
||
enum PriorityRaw { | ||
PriorityRaw_Realtime = 0, | ||
PriorityRaw_Normal = 1, | ||
PriorityRaw_Low = 2, | ||
PriorityRaw_Background = 3, | ||
}; | ||
|
||
Priority GetPriorityOnCurrentThread(); | ||
Priority GetPriority(os::ThreadType *thread); | ||
PriorityRaw GetPriorityRawOnCurrentThread(); | ||
PriorityRaw GetPriorityRaw(os::ThreadType *thread); | ||
|
||
void SetPriorityOnCurrentThread(Priority prio); | ||
void SetPriority(os::ThreadType *thread, Priority prio); | ||
void SetPriorityRawOnCurrentThread(PriorityRaw prio); | ||
void SetPriorityRaw(os::ThreadType *thread, PriorityRaw prio); | ||
|
||
} |
24 changes: 24 additions & 0 deletions
24
libraries/libstratosphere/include/stratosphere/fs/fs_result_config.hpp
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,24 @@ | ||
/* | ||
* Copyright (c) 2018-2020 Atmosphère-NX | ||
* | ||
* This program is free software; you can redistribute it and/or modify it | ||
* under the terms and conditions of the GNU General Public License, | ||
* version 2, as published by the Free Software Foundation. | ||
* | ||
* This program is distributed in the hope it will be useful, but WITHOUT | ||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or | ||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for | ||
* more details. | ||
* | ||
* You should have received a copy of the GNU General Public License | ||
* along with this program. If not, see <http://www.gnu.org/licenses/>. | ||
*/ | ||
#pragma once | ||
#include <vapours.hpp> | ||
|
||
namespace ams::fs { | ||
|
||
void SetEnabledAutoAbort(bool enabled); | ||
void SetResultHandledByApplication(bool application); | ||
|
||
} |
153 changes: 153 additions & 0 deletions
153
libraries/libstratosphere/include/stratosphere/fs/impl/fs_access_log_impl.hpp
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,153 @@ | ||
/* | ||
* Copyright (c) 2018-2020 Atmosphère-NX | ||
* | ||
* This program is free software; you can redistribute it and/or modify it | ||
* under the terms and conditions of the GNU General Public License, | ||
* version 2, as published by the Free Software Foundation. | ||
* | ||
* This program is distributed in the hope it will be useful, but WITHOUT | ||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or | ||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for | ||
* more details. | ||
* | ||
* You should have received a copy of the GNU General Public License | ||
* along with this program. If not, see <http://www.gnu.org/licenses/>. | ||
*/ | ||
#pragma once | ||
#include <vapours.hpp> | ||
#include <stratosphere/fs/fs_access_log.hpp> | ||
#include <stratosphere/fs/fs_directory.hpp> | ||
#include <stratosphere/fs/fs_file.hpp> | ||
#include <stratosphere/fs/fs_priority.hpp> | ||
#include <stratosphere/os/os_tick.hpp> | ||
|
||
namespace ams::fs::impl { | ||
|
||
enum AccessLogTarget : u32 { | ||
AccessLogTarget_None = (0 << 0), | ||
AccessLogTarget_Application = (1 << 0), | ||
AccessLogTarget_System = (1 << 1), | ||
}; | ||
|
||
struct IdentifyAccessLogHandle { | ||
void *handle; | ||
public: | ||
static constexpr IdentifyAccessLogHandle MakeHandle(void *h) { | ||
return IdentifyAccessLogHandle{h}; | ||
} | ||
}; | ||
|
||
bool IsEnabledAccessLog(u32 target); | ||
bool IsEnabledAccessLog(); | ||
|
||
bool IsEnabledHandleAccessLog(fs::FileHandle handle); | ||
bool IsEnabledHandleAccessLog(fs::DirectoryHandle handle); | ||
bool IsEnabledHandleAccessLog(fs::impl::IdentifyAccessLogHandle handle); | ||
bool IsEnabledHandleAccessLog(const void *handle); | ||
|
||
bool IsEnabledFileSystemAccessorAccessLog(const char *mount_name); | ||
void EnableFileSystemAccessorAccessLog(const char *mount_name); | ||
|
||
using AccessLogPrinterCallback = int (*)(char *buffer, size_t buffer_size); | ||
void RegisterStartAccessLogPrinterCallback(AccessLogPrinterCallback callback); | ||
|
||
void OutputAccessLog(Result result, os::Tick start, os::Tick end, const char *name, fs::FileHandle handle, const char *fmt, ...) __attribute__((format (printf, 6, 7))); | ||
void OutputAccessLog(Result result, os::Tick start, os::Tick end, const char *name, fs::DirectoryHandle handle, const char *fmt, ...) __attribute__((format (printf, 6, 7))); | ||
void OutputAccessLog(Result result, os::Tick start, os::Tick end, const char *name, fs::impl::IdentifyAccessLogHandle handle, const char *fmt, ...) __attribute__((format (printf, 6, 7))); | ||
void OutputAccessLog(Result result, os::Tick start, os::Tick end, const char *name, const void *handle, const char *fmt, ...) __attribute__((format (printf, 6, 7))); | ||
void OutputAccessLog(Result result, fs::Priority priority, os::Tick start, os::Tick end, const char *name, const void *handle, const char *fmt, ...) __attribute__((format (printf, 7, 8))); | ||
void OutputAccessLog(Result result, fs::PriorityRaw priority_raw, os::Tick start, os::Tick end, const char *name, const void *handle, const char *fmt, ...) __attribute__((format (printf, 7, 8))); | ||
|
||
void OutputAccessLogToOnlySdCard(const char *fmt, ...) __attribute__((format (printf, 1, 2))); | ||
|
||
void OutputAccessLogUnlessResultSuccess(Result result, os::Tick start, os::Tick end, const char *name, fs::FileHandle handle, const char *fmt, ...) __attribute__((format (printf, 6, 7))); | ||
void OutputAccessLogUnlessResultSuccess(Result result, os::Tick start, os::Tick end, const char *name, fs::DirectoryHandle handle, const char *fmt, ...) __attribute__((format (printf, 6, 7))); | ||
void OutputAccessLogUnlessResultSuccess(Result result, os::Tick start, os::Tick end, const char *name, const void *handle, const char *fmt, ...) __attribute__((format (printf, 6, 7))); | ||
|
||
class IdString { | ||
private: | ||
char buffer[0x20]; | ||
private: | ||
const char *ToValueString(int id); | ||
public: | ||
template<typename T> | ||
const char *ToString(T id); | ||
}; | ||
|
||
} | ||
|
||
/* Access log components. */ | ||
#define AMS_FS_IMPL_ACCESS_LOG_FORMAT_SIZE ", size: %" PRId64 "" | ||
#define AMS_FS_IMPL_ACCESS_LOG_FORMAT_OFFSET_AND_SIZE ", offset: %" PRId64 ", size: %zu" | ||
#define AMS_FS_IMPL_ACCESS_LOG_FORMAT_THREAD_ID ", thread_id: %" PRIu64 "" | ||
|
||
/* Access log formats. */ | ||
#define AMS_FS_IMPL_ACCESS_LOG_FORMAT_NONE "" | ||
|
||
#define AMS_FS_IMPL_ACCESS_LOG_FORMAT_WRITE_FILE_WITH_NO_OPTION AMS_FS_IMPL_ACCESS_LOG_FORMAT_OFFSET_AND_SIZE | ||
#define AMS_FS_IMPL_ACCESS_LOG_FORMAT_WRITE_FILE_WITH_FLUSH_OPTION AMS_FS_IMPL_ACCESS_LOG_FORMAT_WRITE_FILE_WITH_NO_OPTION ", write_option: Flush" | ||
#define AMS_FS_IMPL_ACCESS_LOG_FORMAT_WRITE_FILE(__OPTION__) ((__OPTION__).HasFlushFlag() ? AMS_FS_IMPL_ACCESS_LOG_FORMAT_WRITE_FILE_WITH_FLUSH_OPTION : AMS_FS_IMPL_ACCESS_LOG_FORMAT_WRITE_FILE_WITH_NO_OPTION) | ||
|
||
/* Access log invocation lambdas. */ | ||
#define AMS_FS_IMPL_ACCESS_LOG_IMPL(__EXPR__, __HANDLE__, __ENABLED__, __NAME__, ...) \ | ||
[&](const char *name) { \ | ||
if (!(__ENABLED__)) { \ | ||
return (__EXPR__); \ | ||
} else { \ | ||
const ::ams::os::Tick start = ::ams::os::GetSystemTick(); \ | ||
const auto result = (__EXPR__); \ | ||
const ::ams::os::Tick end = ::ams::os::GetSystemTick(); \ | ||
::ams::fs::impl::OutputAccessLog(result, start, end, name, __HANDLE__, __VA_ARGS__); \ | ||
return result; \ | ||
} \ | ||
}(__NAME__) | ||
|
||
#define AMS_FS_IMPL_ACCESS_LOG_WITH_PRIORITY_IMPL(__EXPR__, __PRIORITY__, __HANDLE__, __ENABLED__, __NAME__, ...) \ | ||
[&](const char *name) { \ | ||
if (!(__ENABLED__)) { \ | ||
return (__EXPR__); \ | ||
} else { \ | ||
const ::ams::os::Tick start = ::ams::os::GetSystemTick(); \ | ||
const auto result = (__EXPR__); \ | ||
const ::ams::os::Tick end = ::ams::os::GetSystemTick(); \ | ||
::ams::fs::impl::OutputAccessLog(result, __PRIORITY__, start, end, name, __HANDLE__, __VA_ARGS__); \ | ||
return result; \ | ||
} \ | ||
}(__NAME__) | ||
|
||
#define AMS_FS_IMPL_ACCESS_LOG_EXPLICIT_IMPL(__RESULT__, __START__, __END__, __HANDLE__, __ENABLED__, __NAME__, ...) \ | ||
[&](const char *name) { \ | ||
if (!(__ENABLED__)) { \ | ||
return __RESULT__; \ | ||
} else { \ | ||
::ams::fs::impl::OutputAccessLog(__RESULT__, __START__, __END__, name, __HANDLE__, __VA_ARGS__); \ | ||
return __RESULT__; \ | ||
} \ | ||
}(__NAME__) | ||
|
||
#define AMS_FS_IMPL_ACCESS_LOG_UNLESS_R_SUCCEEDED_IMPL(__EXPR__, __ENABLED__, __NAME__, ...) \ | ||
[&](const char *name) { \ | ||
if (!(__ENABLED__)) { \ | ||
return (__EXPR__); \ | ||
} else { \ | ||
const ::ams::os::Tick start = ::ams::os::GetSystemTick(); \ | ||
const auto result = (__EXPR__); \ | ||
const ::ams::os::Tick end = ::ams::os::GetSystemTick(); \ | ||
::ams::fs::impl::OutputAccessLogUnlessResultSuccess(result, start, end, name, nullptr, __VA_ARGS__); \ | ||
return result; \ | ||
} \ | ||
}(__NAME__) | ||
|
||
|
||
/* Access log api. */ | ||
#define AMS_FS_IMPL_ACCESS_LOG(__EXPR__, __HANDLE__, ...) \ | ||
AMS_FS_IMPL_ACCESS_LOG_IMPL((__EXPR__), __HANDLE__, ::ams::fs::impl::IsEnabledAccessLog() && ::ams::fs::impl::IsEnabledHandleAccessLog(__HANDLE__), AMS_CURRENT_FUNCTION_NAME, __VA_ARGS__) | ||
|
||
#define AMS_FS_IMPL_ACCESS_LOG_WITH_NAME(__EXPR__, __HANDLE__, __NAME__, ...) \ | ||
AMS_FS_IMPL_ACCESS_LOG_IMPL((__EXPR__), __HANDLE__, ::ams::fs::impl::IsEnabledAccessLog() && ::ams::fs::impl::IsEnabledHandleAccessLog(__HANDLE__), __NAME__, __VA_ARGS__) | ||
|
||
#define AMS_FS_IMPL_ACCESS_LOG_EXPLICIT(__RESULT__, __START__, __END__, __HANDLE__, __NAME__, ...) \ | ||
AMS_FS_IMPL_ACCESS_LOG_EXPLICIT_IMPL((__RESULT__), __START__, __END__, __HANDLE__, ::ams::fs::impl::IsEnabledAccessLog() && ::ams::fs::impl::IsEnabledHandleAccessLog(__HANDLE__), __NAME__, __VA_ARGS__) | ||
|
||
#define AMS_FS_IMPL_ACCESS_LOG_UNLESS_R_SUCCEEDED(__EXPR__, ...) \ | ||
AMS_FS_IMPL_ACCESS_LOG_UNLESS_R_SUCCEEDED_IMPL((__EXPR__), ::ams::fs::impl::IsEnabledAccessLog(), AMS_CURRENT_FUNCTION_NAME, __VA_ARGS__) |
Oops, something went wrong.