diff --git a/.gitmodules b/.gitmodules index fb274755..7e8b5a73 100644 --- a/.gitmodules +++ b/.gitmodules @@ -1,15 +1,3 @@ -[submodule "lib/sead"] - path = lib/sead - url = https://github.com/open-ead/sead -[submodule "lib/NintendoSDK"] - path = lib/NintendoSDK - url = https://github.com/open-ead/nnheaders -[submodule "lib/agl"] - path = lib/agl - url = https://github.com/open-ead/agl -[submodule "lib/EventFlow"] - path = lib/EventFlow - url = https://github.com/open-ead/EventFlow [submodule "tools/common"] path = tools/common url = https://github.com/open-ead/nx-decomp-tools diff --git a/Contributing.md b/Contributing.md index 62d9533a..49d19623 100644 --- a/Contributing.md +++ b/Contributing.md @@ -220,6 +220,41 @@ This project sometimes uses small hacks to force particular code to be generated * `MATCHING_HACK_NX_CLANG`: Hacks for Switch, when compiling with Clang. +## Modifying library code + +Changes to the following libraries must be PR'd/submitted to their own repository: + +* sead: https://github.com/open-ead/sead +* NintendoSDK: https://github.com/open-ead/nnheaders +* agl: https://github.com/open-ead/agl +* EventFlow: https://github.com/open-ead/EventFlow + +The recommended workflow is to commit your changes as usual in the BotW repo, and then do a "subrepo push" to +your fork of the library repo once you are ready to open a pull request. + +Example: + +``` +echo test > lib/sead/test_file +git add -A +git commit -m "test" +git subrepo push lib/sead -r -b +``` + +You can then open one PR in the BotW repo and another one in the library repo. + +Once the library repo PR has been merged, a maintainer will let you know what you should do +to update the library subrepo in the BotW repo. + +Follow the [instructions here](https://github.com/ingydotnet/git-subrepo#installation) to install the git-subrepo command +if you do not already have it. + +### Updating the library repos + +Library subrepos can be updated with e.g. `git subrepo pull lib/sead`. This will pull the latest changes from the +library repository and git-subrepo will automatically create a commit in the BotW repo to reflect the changes. +Do not attempt to amend the commit message -- doing so could break the subrepo. + ## Project tools * Check all decompiled functions for issues: `tools/check` diff --git a/lib/EventFlow b/lib/EventFlow deleted file mode 160000 index c35d21b3..00000000 --- a/lib/EventFlow +++ /dev/null @@ -1 +0,0 @@ -Subproject commit c35d21b34397bec6dd3c67a649fc66b68839341e diff --git a/lib/EventFlow/.clang-format b/lib/EventFlow/.clang-format new file mode 100644 index 00000000..cea20307 --- /dev/null +++ b/lib/EventFlow/.clang-format @@ -0,0 +1,75 @@ +--- +Language: Cpp +AccessModifierOffset: -4 +AlignAfterOpenBracket: Align +AlignConsecutiveAssignments: false +AlignConsecutiveDeclarations: false +AlignOperands: true +AlignTrailingComments: true +AllowAllParametersOfDeclarationOnNextLine: true +AllowShortBlocksOnASingleLine: Never +AllowShortCaseLabelsOnASingleLine: false +AllowShortFunctionsOnASingleLine: Inline +AllowShortIfStatementsOnASingleLine: Never +AllowShortLoopsOnASingleLine: false +AlwaysBreakAfterDefinitionReturnType: None +AlwaysBreakAfterReturnType: None +AlwaysBreakBeforeMultilineStrings: false +AlwaysBreakTemplateDeclarations: Yes +BinPackArguments: true +BinPackParameters: true +BreakBeforeBinaryOperators: None +BreakBeforeBraces: Attach +BreakBeforeTernaryOperators: false +BreakConstructorInitializersBeforeComma: false +ColumnLimit: 100 +CommentPragmas: '^ (IWYU pragma:|NOLINT)' +ConstructorInitializerAllOnOneLineOrOnePerLine: false +ConstructorInitializerIndentWidth: 4 +ContinuationIndentWidth: 4 +Cpp11BracedListStyle: true +DerivePointerAlignment: false +DisableFormat: false +ForEachMacros: [] +IncludeCategories: + - Regex: '^<[Ww]indows\.h>$' + Priority: 1 + - Regex: '^<' + Priority: 2 + - Regex: '^"' + Priority: 3 +IndentCaseLabels: false +IndentWidth: 4 +IndentWrappedFunctionNames: false +KeepEmptyLinesAtTheStartOfBlocks: false +MacroBlockBegin: '' +MacroBlockEnd: '' +MaxEmptyLinesToKeep: 1 +NamespaceIndentation: None +ObjCBlockIndentWidth: 4 +ObjCSpaceAfterProperty: false +ObjCSpaceBeforeProtocolList: true +PenaltyBreakBeforeFirstCallParameter: 19 +PenaltyBreakComment: 300 +PenaltyBreakFirstLessLess: 120 +PenaltyBreakString: 1000 +PenaltyExcessCharacter: 1000000 +PenaltyReturnTypeOnItsOwnLine: 60 +PointerAlignment: Left +ReflowComments: true +SortIncludes: true +SpaceAfterCStyleCast: false +SpaceBeforeAssignmentOperators: true +SpaceBeforeParens: ControlStatements +SpaceInEmptyParentheses: false +SpacesBeforeTrailingComments: 2 +SpacesInAngles: false +SpacesInContainerLiterals: true +SpacesInCStyleCastParentheses: false +SpacesInParentheses: false +SpacesInSquareBrackets: false +Standard: c++17 +TabWidth: 4 +UseTab: Never +WhitespaceSensitiveMacros: ["ORE_ENUM"] +... diff --git a/lib/EventFlow/.gitignore b/lib/EventFlow/.gitignore new file mode 100644 index 00000000..343c32e3 --- /dev/null +++ b/lib/EventFlow/.gitignore @@ -0,0 +1,31 @@ +__pycache__/ +*.pyc +*.egg-info/ +*.dist-info/ +*.so +*.dll +dist/ +build/ +bin/ +.mypy_cache/ +.benchmarks/ + +.idea/ +.vscode/ + +*.id0 +*.id1 +*.id2 +*.idb +*.i64 +*.nam +*.til + +main.elf + +perf.mData +perf.mData.old +.gdb_history + +.DS_Store +tools/aarch64-none-elf-objdump \ No newline at end of file diff --git a/lib/EventFlow/.gitrepo b/lib/EventFlow/.gitrepo new file mode 100644 index 00000000..b5109f06 --- /dev/null +++ b/lib/EventFlow/.gitrepo @@ -0,0 +1,12 @@ +; DO NOT EDIT (unless you know what you are doing) +; +; This subdirectory is a git "subrepo", and this file is maintained by the +; git-subrepo command. See https://github.com/git-commands/git-subrepo#readme +; +[subrepo] + remote = https://github.com/open-ead/EventFlow + branch = master + commit = c35d21b34397bec6dd3c67a649fc66b68839341e + parent = ffcc7f659ebc9bc9d149e52bec553b906bb47369 + method = merge + cmdver = 0.4.3 diff --git a/lib/EventFlow/CMakeLists.txt b/lib/EventFlow/CMakeLists.txt new file mode 100644 index 00000000..394c6ffa --- /dev/null +++ b/lib/EventFlow/CMakeLists.txt @@ -0,0 +1,56 @@ +project(EventFlow CXX ASM) + +option(EVFL_VER_LABO "Build Labo's version of this library" OFF) + +add_library(evfl OBJECT + include/evfl/Action.h + include/evfl/EvflAllocator.h + include/evfl/Flowchart.h + include/evfl/Param.h + include/evfl/Query.h + include/evfl/ResActor.h + include/evfl/ResEventFlowFile.h + include/evfl/ResFlowchart.h + include/evfl/ResTimeline.h + include/evfl/TimelineObj.h + include/ore/Allocator.h + include/ore/Array.h + include/ore/BinaryFile.h + include/ore/BitUtils.h + include/ore/Buffer.h + include/ore/EnumUtil.h + include/ore/IntrusiveList.h + include/ore/IterRange.h + include/ore/RelocationTable.h + include/ore/ResDic.h + include/ore/ResEndian.h + include/ore/ResMetaData.h + include/ore/StringPool.h + include/ore/StringView.h + include/ore/Types.h + src/evfl/Action.cpp + src/evfl/Param.cpp + src/evfl/Flowchart.cpp + src/evfl/FlowchartObj.cpp + src/evfl/TimelineObj.cpp + src/evfl/ResEventFlowFile.cpp + src/evfl/ResTimeline.cpp + src/evfl/ResActor.cpp + src/evfl/ResFlowchart.cpp + src/ore/BitUtils.cpp + src/ore/EnumUtil.cpp + src/ore/BinaryFile.cpp + src/ore/RelocationTable.cpp + src/ore/StringPool.cpp + src/ore/ResDic.cpp + src/ore/ResMetaData.cpp +) + +target_compile_options(evfl PRIVATE -fno-exceptions) +target_compile_options(evfl PRIVATE -fno-strict-aliasing) +target_compile_options(evfl PRIVATE -Wno-invalid-offsetof) +target_include_directories(evfl PUBLIC include/) + +if(EVFL_VER_LABO) + target_compile_definitions(evfl PUBLIC EVFL_VER_LABO=1) +endif() diff --git a/lib/EventFlow/include/evfl/Action.h b/lib/EventFlow/include/evfl/Action.h new file mode 100644 index 00000000..88dea6dd --- /dev/null +++ b/lib/EventFlow/include/evfl/Action.h @@ -0,0 +1,125 @@ +#pragma once + +#include +#include +#include +#include + +namespace evfl { + +class FlowchartContext; +class FlowchartContextNode; +class FlowchartObj; +struct ResClip; +struct ResEvent; +struct ResOneshot; +class TimelineObj; +class VariablePack; + +ORE_VALUED_ENUM(TriggerType, kFlowchart = 0, kClipEnter = 1, kClipLeave = 2, kOneshot = 3, + kNormal = 0, kEnter = 1, kLeave = 2) + +class ActionDoneHandler { +public: + ActionDoneHandler() = default; + ActionDoneHandler(FlowchartObj* obj, FlowchartContext* context, int node_idx); + explicit ActionDoneHandler(TimelineObj* obj) : m_is_flowchart(false) { m_timeline_obj = obj; } + ~ActionDoneHandler() { m_list_node.Erase(); } + + ActionDoneHandler(const ActionDoneHandler&) = delete; + auto operator=(const ActionDoneHandler&) = delete; + + ActionDoneHandler(ActionDoneHandler&& other) noexcept { *this = std::move(other); } + + ActionDoneHandler& operator=(ActionDoneHandler&& other) noexcept { + m_context = other.m_context; + m_node_idx = other.m_node_idx; + m_obj = other.m_obj; + m_node_counter = other.m_node_counter; + m_handled = other.m_handled; + m_is_flowchart = other.m_is_flowchart; + m_list_node = std::move(other.m_list_node); + + other.m_context = nullptr; + other.m_node_idx = -1; + other.m_node_counter = -1; + other.m_obj = nullptr; + other.m_handled = false; + other.m_is_flowchart = true; + + return *this; + } + + FlowchartContextNode* GetContextNode(); + void InvokeFromFlowchartImpl(); + void InvokeFromTimelineImpl(); + bool IsWaitingJoin(); + bool CancelWaiting(); + + void Reset() { + m_context = nullptr; + m_obj = nullptr; + m_node_idx = -1; + m_node_counter = -1; + m_handled = false; + m_is_flowchart = true; + } + + static constexpr size_t GetListNodeOffset() { return offsetof(ActionDoneHandler, m_list_node); } + +private: + friend class FlowchartContext; + + ore::IntrusiveListNode m_list_node; + FlowchartContext* m_context = nullptr; + int m_node_idx = -1; + int m_node_counter = -1; + union { + FlowchartObj* m_obj = nullptr; + TimelineObj* m_timeline_obj; + }; + bool m_handled = false; + bool m_is_flowchart = true; +}; + +struct ActionArg { + ActionArg(FlowchartContext* context, int node_idx, void* actor_user_data_, + void* action_user_data_, VariablePack* variable_pack_, const ResEvent* event_) + : param_accessor(context, node_idx), actor_user_data(actor_user_data_), + action_user_data(action_user_data_), flowchart_ctx(context), + variable_pack(variable_pack_), res(event_), timeline_time_delta(0.0), + trigger_type(TriggerType::kFlowchart) {} + + ActionArg(const ResClip* clip, void* actor_user_data_, void* action_user_data_, + float timeline_time_delta_, TriggerType::Type type, const ore::ResMetaData* params) + : param_accessor(params), actor_user_data(actor_user_data_), + action_user_data(action_user_data_), res(clip), timeline_time_delta(timeline_time_delta_), + trigger_type(type) {} + + ActionArg(const ResOneshot* oneshot, void* actor_user_data_, void* action_user_data_, + float timeline_time_delta_, const ore::ResMetaData* params) + : param_accessor(params), actor_user_data(actor_user_data_), + action_user_data(action_user_data_), res(oneshot), + timeline_time_delta(timeline_time_delta_), trigger_type(TriggerType::kOneshot) { + res.oneshot = oneshot; + } + + ParamAccessor param_accessor; + void* actor_user_data = nullptr; + void* action_user_data = nullptr; + FlowchartContext* flowchart_ctx = nullptr; + VariablePack* variable_pack = nullptr; + union Res { + explicit Res(const ResEvent* e) : event(e) {} + explicit Res(const ResClip* c) : clip(c) {} + explicit Res(const ResOneshot* o) : oneshot(o) {} + + const ResEvent* event; + const ResClip* clip; + const ResOneshot* oneshot; + } res; + float timeline_time_delta{}; + TriggerType::Type trigger_type{}; +}; + +} // namespace evfl diff --git a/lib/EventFlow/include/evfl/EvflAllocator.h b/lib/EventFlow/include/evfl/EvflAllocator.h new file mode 100644 index 00000000..e81d4441 --- /dev/null +++ b/lib/EventFlow/include/evfl/EvflAllocator.h @@ -0,0 +1,31 @@ +#pragma once + +#include + +namespace evfl { + +struct AllocateArg { + void* (*alloc)(size_t size, size_t alignment, void* userdata); + void (*free)(void* ptr, void* userdata); + void* alloc_userdata; + void* free_userdata; +}; + +class EvflAllocator : public ore::Allocator { +public: + EvflAllocator() = default; + explicit EvflAllocator(AllocateArg arg) : m_arg(arg) {} + + void* AllocImpl(size_t size, size_t alignment) override { + return m_arg.alloc(size, alignment, m_arg.alloc_userdata); + } + + void FreeImpl(void* ptr) override { m_arg.free(ptr, m_arg.free_userdata); } + + AllocateArg GetArg() const { return m_arg; } + +private: + AllocateArg m_arg; +}; + +} // namespace evfl diff --git a/lib/EventFlow/include/evfl/Flowchart.h b/lib/EventFlow/include/evfl/Flowchart.h new file mode 100644 index 00000000..4bc40a17 --- /dev/null +++ b/lib/EventFlow/include/evfl/Flowchart.h @@ -0,0 +1,208 @@ +#pragma once + +#include +#include +#include +#include +#include +#include +#include +#include +#include + +namespace ore { +class Allocator; +class BitArray; +} // namespace ore + +namespace evfl { + +class MetaDataPack; +struct ResEntryPoint; +struct ResEvent; +struct ResFlowchart; +class VariablePack; + +ORE_ENUM(SubFlowCallbackType, kEnter, kLeave) + +class FlowchartObj { +public: + class Builder { + public: + Builder(const ResFlowchart* flowchart, ore::BitArray* visited_entry_points) + : m_flowchart(flowchart), m_entry_points_mask(visited_entry_points) {} + + bool Build(FlowchartObj* obj, ore::Allocator* allocator, + ore::IterRange flowcharts); + + private: + const ResFlowchart* m_flowchart{}; + ore::BitArray* m_entry_points_mask{}; + ActBinder::Builder m_act_binder_builder{}; + }; + +#ifdef MATCHING_HACK_NX_CLANG + [[gnu::always_inline]] +#endif + ~FlowchartObj() = default; + + const ResFlowchart* GetFlowchart() const { return m_flowchart; } + const ActBinder& GetActBinder() const { return m_act_binder; } + ActBinder& GetActBinder() { return m_act_binder; } + +private: + const ResFlowchart* m_flowchart{}; + ActBinder m_act_binder; +}; + +class FlowchartContextNode { +public: + ORE_ENUM(State, kInvalid, kFree, kNotInvoked, kInvoked, kDone, kWaiting) + + FlowchartContextNode() { Reset(); } + + bool IsInvalidOrFree() const { return m_state == State::kInvalid || m_state == State::kFree; } + FlowchartObj* GetObj() const { return m_obj; } + VariablePack* GetVariablePack() const { return m_variable_pack; } + int GetNodeCounter() const { return m_node_counter; } + u16 GetEventIdx() const { return m_event_idx; } + u16 GetNextNodeIdx() const { return m_next_node_idx; } + State::Type GetState() const { return m_state; } + + void Reset() { + m_node_counter = -1; + m_obj = nullptr; + m_event_idx = -1; + m_next_node_idx = -1; + m_idx = -1; + m_state = State::kInvalid; + m_variable_pack = nullptr; + m_owns_variable_pack = false; + } + +private: + friend class ActionDoneHandler; + friend class FlowchartContext; + + FlowchartObj* m_obj; + VariablePack* m_variable_pack; + int m_node_counter; + u16 m_event_idx; + u16 m_next_node_idx; + u16 m_idx; + ore::SizedEnum m_state; + bool m_owns_variable_pack; +}; + +class FlowchartContext { +public: + class Builder { + public: + using FlowchartRange = ore::IterRange; + ORE_ENUM(BuildResultType, kSuccess, kInvalidOperation, kResFlowchartNotFound, kEntryPointNotFound) + + struct BuildResult { + BuildResultType::Type result; + /// Indicates which flowchart was required yet couldn't be found. + ore::StringView missing_flowchart_name{}; + /// Indicates which entry point was required yet couldn't be found. + ore::StringView missing_entry_point_name{}; + }; + + Builder() = default; + explicit Builder(FlowchartRange flowcharts, int flowchart_idx = 0) + : m_flowcharts(flowcharts), m_flowchart_idx(flowchart_idx) {} + + bool SetEntryPoint(const ore::StringView& flowchart_name, + const ore::StringView& entry_point_name); + bool SetEntryPoint(BuildResult* result, const ore::StringView& flowchart_name, + const ore::StringView& entry_point_name); + + bool Build(FlowchartContext* context, AllocateArg allocate_arg); + bool Build(BuildResult* result, FlowchartContext* context, AllocateArg allocate_arg); + + private: + bool BuildImpl(BuildResult* result, FlowchartRange flowcharts, FlowchartContext* context, + AllocateArg allocate_arg, ore::Buffer flowchart_obj_buffer); + + FlowchartRange m_flowcharts{}; + int m_flowchart_idx = 0; + int m_entry_point_idx = -1; + }; + + FlowchartContext(); + ~FlowchartContext() { + Dispose(); + m_objs.DestructElements(); + } + + FlowchartContext(const FlowchartContext&) = delete; + auto operator=(const FlowchartContext&) = delete; + + void Start(MetaDataPack* pack); + int AllocNode(); + void AllocVariablePack(FlowchartContextNode& node, const ResEntryPoint& entry_point); + void ProcessContext(); + FlowchartObj* FindFlowchartObj(ore::StringView name); + const FlowchartObj* FindFlowchartObj(ore::StringView name) const; + void UnbindAll(); + void Clear(); + void FreeVariablePack(FlowchartContextNode& node); + void CopyVariablePack(FlowchartContextNode& src, FlowchartContextNode& dst); + bool ProcessContextNode(int node_idx); + ActorBinding* TrackBackArgumentActor(int node_idx, const ore::StringView& name); + bool IsUsing(const ResFlowchart* flowchart) const; + bool IsPlaying(const ResFlowchart* flowchart) const; + const ore::Array* GetUsedResActors(ore::StringView flowchart_name) const; + + FlowchartContextNode& GetNode(int idx) { return m_nodes[idx]; } + const FlowchartContextNode& GetNode(int idx) const { return m_nodes[idx]; } + MetaDataPack* GetMetaDataPack() const { return m_metadata_pack; } + ore::Array& GetObjs() { return m_objs; } + const ore::Array& GetObjs() const { return m_objs; } + +private: + void Dispose() { + m_obj_idx = -1; + m_active_entry_point_idx = -1; + m_metadata_pack = nullptr; + m_objs.Clear(&m_allocator); + for (auto& node : m_nodes) + FreeVariablePack(node); + m_nodes.Reset(); + } + + void UpdateNodeCounter(int node_idx) { + auto& node = GetNode(node_idx); + node.m_node_counter = ++s_GlobalCounter; + } + + void CallSubFlowCallback(const ResFlowchart* flowchart, const ResEvent* event, + SubFlowCallbackType::Type type) { +#ifdef EVFL_VER_LABO + if (m_on_sub_flow_callback) + m_on_sub_flow_callback(this, flowchart, event, type); +#endif + } + + static int s_GlobalCounter; + + EvflAllocator m_allocator; + ore::Array m_objs; + ore::DynArrayList m_nodes; + ore::IntrusiveList m_handlers; +#ifdef EVFL_VER_LABO + void (*m_on_sub_flow_callback)(FlowchartContext* context, const ResFlowchart* flowchart, + const ResEvent* event, SubFlowCallbackType::Type type) = nullptr; +#endif + MetaDataPack* m_metadata_pack = nullptr; + void* _78 = nullptr; + int m_next_node_idx = 0; + int m_num_allocated_nodes = 0; + int m_obj_idx = -1; + int m_active_entry_point_idx = -1; + bool m_is_processing = false; + u8 _91 = 0; +}; + +} // namespace evfl diff --git a/lib/EventFlow/include/evfl/Param.h b/lib/EventFlow/include/evfl/Param.h new file mode 100644 index 00000000..439aba28 --- /dev/null +++ b/lib/EventFlow/include/evfl/Param.h @@ -0,0 +1,208 @@ +#pragma once + +#include +#include +#include +#include +#include +#include +#include +#include +#include + +namespace ore { +struct ResDic; +struct ResMetaData; +} // namespace ore + +namespace evfl { + +class FlowchartContext; +class FlowchartObj; +struct ResEntryPoint; + +class MetaDataPack { +public: + ORE_ENUM(DataType, kInt, kBool, kFloat, kString, kWString) + + struct Entry { + union Value { + bool b; + int i; + float f; + const char* str; + const wchar_t* wstr; + }; + + bool IsKey(const ore::StringView& other) const { return ore::StringView(key) == other; } + + const char* key; + Value value; + DataType::Type type; + }; + + class Builder { + public: + void CalcMemSize(); + bool Build(MetaDataPack* pack, ore::Buffer buffer); + void SetNumEntries(int num) { m_num_entries = num; } + int GetRequiredSize() const { return m_required_size; } + + private: + int m_num_entries = 16; + int m_required_size = 0; + int m_alignment_real = 16; + int m_entries_byte_size = 0; + int m_alignment = 16; + int _14 = 0; + int m_buffer_offset = -1; + }; + + void AddInt(const char* key, int value); + void AddBool(const char* key, bool value); + void AddFloat(const char* key, float value); + void AddStringPtr(const char* key, const char* value); + void AddWStringPtr(const char* key, const wchar_t* value); + + bool FindInt(int* value, const ore::StringView& key) const; + bool FindBool(bool* value, const ore::StringView& key) const; + bool FindFloat(float* value, const ore::StringView& key) const; + bool FindString(ore::StringView* value, const ore::StringView& key) const; + bool FindWString(ore::WStringView* value, const ore::StringView& key) const; + + ore::ResMetaData::DataType::Type GetType(const ore::StringView& key) const; + +private: + Entry* Find(const ore::StringView& key) const; + Entry& AddEntry() { return m_entries[m_entries_num++]; } + + ore::Array GetEntries() const { return {m_entries, m_entries_num}; } + + ore::Buffer m_buffer{}; + Entry* m_entries{}; + int m_entries_num{}; + int m_entries_capacity{}; +}; + +class VariablePack { +public: + using VariableType = ore::ResMetaData::DataType::Type; + + struct Entry { + union Value { + void* dummy; + int i; + float f; + ore::DynArrayList* int_array; + ore::DynArrayList* float_array; + }; + + Value value; + VariableType type; + }; + + VariablePack(); + ~VariablePack(); + VariablePack(const VariablePack&) = delete; + auto operator=(const VariablePack&) = delete; + + void Init(AllocateArg arg, const ResEntryPoint* entry_point); + + Entry* GetVariableEntry(const ore::StringView& name); + const Entry* GetVariableEntry(const ore::StringView& name) const; + VariableType GetVariableType(const ore::StringView& name) const; + ore::StringView GetVariableName(int idx) const; + int GetVariableCount() const; + + bool Contains(const ore::StringView& name) const; + + bool FindInt(int* value, const ore::StringView& name) const; + bool FindBool(bool* value, const ore::StringView& name) const; + bool FindFloat(float* value, const ore::StringView& name) const; + bool FindIntList(ore::DynArrayList** value, const ore::StringView& name) const; + bool FindFloatList(ore::DynArrayList** value, const ore::StringView& name) const; + + int GetInt(const ore::StringView& name) const; + bool GetBool(const ore::StringView& name) const; + float GetFloat(const ore::StringView& name) const; + ore::DynArrayList* GetIntList(const ore::StringView& name) const; + ore::DynArrayList* GetFloatList(const ore::StringView& name) const; + + void SetInt(const ore::StringView& name, int value); + void SetFloat(const ore::StringView& name, float value); + void SetBool(const ore::StringView& name, bool value); + +private: + void Dispose(); + ore::Allocator* GetAllocator() { return &m_allocator; } + + const ore::ResDic* m_names = nullptr; + ore::Array m_variables; + EvflAllocator m_allocator; +}; + +class ParamAccessor { +public: + using Type = ore::ResMetaData::DataType::Type; + using IntRange = ore::IterRange; + using FloatRange = ore::IterRange; + using StringRange = ore::IterRange*>; + using WStringRange = ore::IterRange*>; + + explicit ParamAccessor(const ore::ResMetaData* metadata); + explicit ParamAccessor(const FlowchartContext* context, int node_idx); + + const ore::ResMetaData* GetFrontResMetaData() const; + int GetParamCount() const; + ore::StringView GetParamName(int idx) const; + Type GetParamType(int idx) const; + + /// @param out_metadata Must be nonnull. + /// @param out_metadata_pack Must be nonnull. + /// @param out_variable_pack Must be nonnull. + /// @param out_obj May be null. + /// @param argument Name of the argument to search for. + ore::StringView TrackBackArgument(const ore::ResMetaData** out_metadata, + const MetaDataPack** out_metadata_pack, + const VariablePack** out_variable_pack, + FlowchartObj** out_obj, + const ore::StringView& argument) const; + + int GetInt(int idx) const; + bool FindInt(int* value, const ore::StringView& name) const; + + bool GetBool(int idx) const; + bool FindBool(bool* value, const ore::StringView& name) const; + + float GetFloat(int idx) const; + bool FindFloat(float* value, const ore::StringView& name) const; + + ore::StringView GetString(int idx) const; + bool FindString(ore::StringView* value, const ore::StringView& name) const; + + ore::WStringView GetWString(int idx) const; + bool FindWString(ore::WStringView* value, const ore::StringView& name) const; + + IntRange GetIntArray(int idx) const; + bool FindIntArray(IntRange* value, const ore::StringView& name) const; + + FloatRange GetFloatArray(int idx) const; + bool FindFloatArray(FloatRange* value, const ore::StringView& name) const; + + StringRange GetStringArray(int idx) const; + bool FindStringArray(StringRange* value, const ore::StringView& name) const; + + WStringRange GetWStringArray(int idx) const; + bool FindWStringArray(WStringRange* value, const ore::StringView& name) const; + + bool FindActorIdentifier(ore::StringView* actor_name, ore::StringView* actor_sub_name, + const ore::StringView& name) const; + +private: + const ore::ResMetaData* m_metadata = nullptr; + const FlowchartContext* m_context = nullptr; + int m_node_idx = -1; + u32 m_node_counter = -1; +}; + +} // namespace evfl diff --git a/lib/EventFlow/include/evfl/Query.h b/lib/EventFlow/include/evfl/Query.h new file mode 100644 index 00000000..979907c7 --- /dev/null +++ b/lib/EventFlow/include/evfl/Query.h @@ -0,0 +1,29 @@ +#pragma once + +#include +#include + +namespace evfl { + +class FlowchartContext; +struct ResEvent; +class VariablePack; + +ORE_ENUM(QueryValueType, kBool, kInt, kFloat, kString, kConst) + +struct QueryArg { + QueryArg(FlowchartContext* context, int node_idx, void* actor_user_data_, + void* query_user_data_, const ResEvent* event_, VariablePack* variable_pack_) + : actor_user_data(actor_user_data_), query_user_data(query_user_data_), main_event(event_), + flowchart_ctx(context), variable_pack(variable_pack_), param_accessor(context, node_idx) { + } + + void* actor_user_data; + void* query_user_data; + const ResEvent* main_event; + FlowchartContext* flowchart_ctx; + VariablePack* variable_pack; + ParamAccessor param_accessor; +}; + +} // namespace evfl diff --git a/lib/EventFlow/include/evfl/ResActor.h b/lib/EventFlow/include/evfl/ResActor.h new file mode 100644 index 00000000..5a43e1a4 --- /dev/null +++ b/lib/EventFlow/include/evfl/ResActor.h @@ -0,0 +1,187 @@ +#pragma once + +#include +#include +#include +#include +#include + +namespace ore { +struct ResEndian; +struct ResMetaData; +} // namespace ore + +namespace evfl { + +struct ActionArg; +class ActionDoneHandler; +class FlowchartContext; +class FlowchartContextNode; +class FlowchartObj; +struct QueryArg; + +struct ResAction { + ore::BinTPtr name; +}; + +struct ResQuery { + ore::BinTPtr name; +}; + +struct ResActor { + bool HasArgumentName() const { return !argument_name.Get()->empty(); } + + ore::BinTPtr name; + ore::BinTPtr secondary_name; + ore::BinTPtr argument_name; + ore::BinTPtr actions; + ore::BinTPtr queries; + ore::BinTPtr params; + u16 num_actions; + u16 num_queries; + /// Entry point index for assicated entry point (0xffff if none) + u16 entry_point_idx; + // TODO: Cut number? This is set to 1 for flowcharts but other values have been seen + // for timeline actors. + u8 cut_number; +}; + +using ActionHandler = void (*)(const ActionArg& arg, ActionDoneHandler done_handler); +using QueryHandler = int (*)(const QueryArg& arg); + +class ActorBinding { +public: + struct Action { + ActionHandler handler{}; + void* user_data{}; + const ResAction* res_action{}; + }; + + struct Query { + QueryHandler handler{}; + void* user_data{}; + const ResQuery* res_query{}; + }; + + ActorBinding() = default; + + void Register(const ResAction* action); + void Register(const ResQuery* query); + + // Similar to std::find_if. Returns m_actions.end() if the specified action is not found. + Action* GetAction(const ore::StringView& name); + const Action* GetAction(const ore::StringView& name) const; + Query* GetQuery(const ore::StringView& name); + const Query* GetQuery(const ore::StringView& name) const; + + ore::DynArrayList& GetActions() { return m_actions; } + ore::DynArrayList& GetQueries() { return m_queries; } + const ore::DynArrayList& GetActions() const { return m_actions; } + const ore::DynArrayList& GetQueries() const { return m_queries; } + auto ActionsEnd() const { return m_actions.end(); } + auto QueriesEnd() const { return m_queries.end(); } + + auto GetActor() const { return m_actor; } + + void* GetUserData() const { return m_user_data; } + void SetUserData(void* user_data) { m_user_data = user_data; } + + bool IsInitialized() const { return m_initialized; } + bool IsUsed() const { return m_is_used; } + void SetInitialized(bool initialized) { m_initialized = initialized; } + void SetIsUsed(bool used) { m_is_used = used; } + + void UnbindAll() { + m_user_data = nullptr; + m_initialized = false; + for (auto it = m_actions.begin(); it != m_actions.end(); ++it) { + it->handler = nullptr; + it->user_data = nullptr; + } + for (auto it = m_queries.begin(); it != m_queries.end(); ++it) { + it->handler = nullptr; + it->user_data = nullptr; + } + } + +private: + friend class ActBinder; + + ore::DynArrayList m_actions{}; + ore::DynArrayList m_queries{}; + void* m_user_data{}; + const ResActor* m_actor{}; + bool m_initialized{}; + bool m_is_used{}; +}; + +class ActBinder { +public: + class Builder { + public: + bool Build(evfl::ActBinder* binder, ore::Allocator* allocator, + ore::IterRange actors); + }; + + ActBinder() = default; + ActBinder(const ActBinder&) = delete; + auto operator=(const ActBinder&) = delete; + +#ifdef MATCHING_HACK_NX_CLANG + [[gnu::always_inline]] +#endif + ~ActBinder() { + Reset(); + } + + u32 GetEventUsedActorCount() const { return m_event_used_actor_count; } + const ore::Array* GetUsedResActors() const; + + ore::Array& GetBindings() { return m_bindings; } + const ore::Array& GetBindings() const { return m_bindings; } + void IncrementNumActors() { ++m_event_used_actor_count; } + void SetIsUsed() { m_is_used = true; } + bool IsUsed() const { return m_is_used; } + + void RegisterAction(int actor_idx, const evfl::ResAction* action) { + auto& binding = GetBindings()[actor_idx]; + if (!binding.IsUsed() && binding.GetActor()->argument_name.Get()->empty()) { + IncrementNumActors(); + binding.SetIsUsed(true); + } + binding.Register(action); + } + + void RegisterQuery(int actor_idx, const evfl::ResQuery* query) { + auto& binding = GetBindings()[actor_idx]; + if (!binding.IsUsed() && binding.GetActor()->argument_name.Get()->empty()) { + IncrementNumActors(); + binding.SetIsUsed(true); + } + binding.Register(query); + } + + void UnbindAll() { + for (auto it = m_bindings.begin(); it != m_bindings.end(); ++it) + it->UnbindAll(); + } + + void Reset() { + m_event_used_actor_count = 0; + if (auto* data = m_bindings.data()) { + m_bindings.ClearWithoutFreeing(); + m_allocator->Free(data); + } + m_allocator = nullptr; + } + +private: + u32 m_event_used_actor_count{}; + ore::Allocator* m_allocator{}; + ore::SelfDestructingArray m_bindings{}; + bool m_is_used{}; +}; + +void SwapEndian(ore::ResEndian* endian, ResActor* actor); + +} // namespace evfl diff --git a/lib/EventFlow/include/evfl/ResEventFlowFile.h b/lib/EventFlow/include/evfl/ResEventFlowFile.h new file mode 100644 index 00000000..30d8217c --- /dev/null +++ b/lib/EventFlow/include/evfl/ResEventFlowFile.h @@ -0,0 +1,36 @@ +#pragma once + +#include +#include + +namespace ore { +struct ResDic; +struct ResEndian; +} // namespace ore + +namespace evfl { + +struct ResFlowchart; +struct ResTimeline; + +struct ResEventFlowFile { + /// data must be a pointer to a buffer of size >= 0x20. + static bool IsValid(void* data); + /// data must be a valid ResEventFlowFile. + static ResEventFlowFile* ResCast(void* data); + + void Relocate(); + void Unrelocate(); + + ore::BinaryFileHeader header; + u16 num_flowcharts; + u16 num_timelines; + ore::BinTPtr> flowcharts; + ore::BinTPtr flowchart_names; + ore::BinTPtr> timelines; + ore::BinTPtr timeline_names; +}; + +void SwapEndian(ore::ResEndian* endian, ResEventFlowFile* file); + +} // namespace evfl diff --git a/lib/EventFlow/include/evfl/ResFlowchart.h b/lib/EventFlow/include/evfl/ResFlowchart.h new file mode 100644 index 00000000..99517bd2 --- /dev/null +++ b/lib/EventFlow/include/evfl/ResFlowchart.h @@ -0,0 +1,136 @@ +#pragma once + +#include +#include +#include +#include +#include + +namespace ore { +struct ResEndian; +} + +namespace evfl { + +struct ResActor; + +struct ResCase { + u32 value; + u16 event_idx; +}; + +struct ResEvent { + ORE_ENUM(EventType, kAction, kSwitch, kFork, kJoin, kSubFlow) + + ore::BinTPtr name; + ore::SizedEnum type; + + union { + // Action, Join, Sub flow + u16 next_event_idx; + // Switch + u16 num_cases; + // Fork + u16 num_forks; + }; + + union { + // Action, Switch + u16 actor_idx; + // Fork + u16 join_event_idx; + }; + + union { + // Action + u16 actor_action_idx; + // Switch + u16 actor_query_idx; + }; + + union { + // Action, Switch, Sub flow + ore::BinTPtr params; + // Fork + ore::BinTPtr fork_event_indices; + }; + + union { + // Switch + ore::BinTPtr cases; + // Sub flow + ore::BinTPtr sub_flow_flowchart; + }; + + union { + // Sub flow + ore::BinTPtr sub_flow_entry_point; + }; +}; + +struct ResVariableDef { + union Value { + // Also used for booleans. Anything that is != 0 is treated as true. + int i; + float f; + ore::BinTPtr int_array; + ore::BinTPtr float_array; + }; + + Value value; + u16 num; + ore::SizedEnum type; +}; + +struct ResEntryPoint { + ore::BinTPtr sub_flow_event_indices; + ore::BinTPtr variable_defs_names; + ore::BinTPtr variable_defs; + u16 num_sub_flow_event_indices; + u16 num_variable_defs; + u16 main_event_idx; +}; + +struct ResFlowchart { + int CountEvent(ResEvent::EventType::Type type) const; + + const ResEntryPoint* GetEntryPoint(const ore::StringView& entry_point_name) const { + const int idx = entry_point_names.Get()->FindIndex(entry_point_name); + if (idx == -1) + return nullptr; + + return entry_points.Get() + idx; + } + + ore::StringView GetEntryPointName(int idx) const { + return entry_point_names.Get()->GetEntries()[1 + idx].GetKey(); + } + + /// 'EVFL' + u32 magic; + /// String pool offset (relative to this structure) + u32 string_pool_offset; + u32 reserved_8; + u32 reserved_c; + u16 num_actors; + u16 num_actions; + u16 num_queries; + u16 num_events; + u16 num_entry_points; + u16 reserved_1a; + u16 reserved_1c; + u16 reserved_1e; + ore::BinTPtr name; + ore::BinTPtr actors; + ore::BinTPtr events; + ore::BinTPtr entry_point_names; + ore::BinTPtr entry_points; +}; + +void SwapEndian(ore::ResEndian* endian, ResCase* case_); +void SwapEndian(ore::ResEndian* endian, ResEvent* event); +void SwapEndian(ore::ResEndian* endian, ResEntryPoint* entry); +void SwapEndian(ore::ResEndian* endian, ResVariableDef* def); +void SwapEndian(ore::ResEndian* endian, ResFlowchart* flowchart); + +} // namespace evfl diff --git a/lib/EventFlow/include/evfl/ResTimeline.h b/lib/EventFlow/include/evfl/ResTimeline.h new file mode 100644 index 00000000..f6a45ff8 --- /dev/null +++ b/lib/EventFlow/include/evfl/ResTimeline.h @@ -0,0 +1,80 @@ +#pragma once + +#include +#include +#include + +namespace ore { +struct ResEndian; +struct ResMetaData; +} // namespace ore + +namespace evfl { + +struct ResActor; + +struct ResTrigger { + u16 clip_index; + u8 trigger_type; +}; + +struct ResCut { + float start_time; + ore::BinTPtr name; + ore::BinTPtr params; +}; + +struct ResClip { + float start_time; + float duration; + u16 actor_index; + u16 actor_action_index; + u8 _c; + ore::BinTPtr params; +}; + +struct ResOneshot { + float time; + u16 actor_index; + u16 actor_action_index; + u32 _8; + u32 _c; + ore::BinTPtr params; +}; + +struct ResSubtimeline { + ore::BinTPtr name; +}; + +struct ResTimeline { + /// 'TLIN' + u32 magic; + /// String pool offset (relative to this structure) + int string_pool_offset; + u32 reserved_8; + u32 reserved_c; + float duration; + u16 num_actors; + u16 num_actions; + u16 num_clips; + u16 num_oneshots; + u16 num_subtimelines; + u16 num_cuts; + ore::BinTPtr name; + ore::BinTPtr actors; + ore::BinTPtr clips; + ore::BinTPtr oneshots; + ore::BinTPtr triggers; + ore::BinTPtr subtimelines; + ore::BinTPtr cuts; + ore::BinTPtr params; +}; + +void SwapEndian(ore::ResEndian* endian, ResTrigger* trigger); +void SwapEndian(ore::ResEndian* endian, ResCut* cut); +void SwapEndian(ore::ResEndian* endian, ResClip* clip); +void SwapEndian(ore::ResEndian* endian, ResOneshot* oneshot); +void SwapEndian(ore::ResEndian* endian, ResSubtimeline* subtimeline); +void SwapEndian(ore::ResEndian* endian, ResTimeline* timeline); + +} // namespace evfl diff --git a/lib/EventFlow/include/evfl/TimelineObj.h b/lib/EventFlow/include/evfl/TimelineObj.h new file mode 100644 index 00000000..5d1ab38a --- /dev/null +++ b/lib/EventFlow/include/evfl/TimelineObj.h @@ -0,0 +1,78 @@ +#pragma once + +#include +#include +#include +#include +#include + +namespace evfl { + +struct ResTimeline; + +ORE_ENUM(TimelineState, kNotStarted, kPlaying, kStop, kPause) + +class TimelineObj { +public: + class Builder { + public: + explicit Builder(const ResTimeline* timeline) : m_timeline(timeline) {} + + bool Build(TimelineObj* obj, AllocateArg allocate_arg); + + private: + const ResTimeline* m_timeline = nullptr; + ActBinder::Builder m_act_binder_builder; + }; + + TimelineObj(); + + void Calc(); + void Reset(); + void SetState(TimelineState::Type state); + void Start(float start_time); + void JumpTimeTo(float time); + void AdvanceTimeTo(float time); + bool RegisterSubtimeline(TimelineObj* obj); + + ActBinder& GetActBinder() { return m_act_binder; } + const ActBinder& GetActBinder() const { return m_act_binder; } + const ore::Array& GetSubTimelines() const { return m_sub_timelines; } + const ResTimeline* GetTimeline() const { return m_timeline; } + float GetTime() const { return m_time; } + float GetNewTime() const { return m_new_time; } + int GetLastTriggerIdx() const { return m_last_trigger_idx; } + int GetLastOneshotIdx() const { return m_last_oneshot_idx; } + int GetPlayCounter() const { return m_play_counter; } + bool IsStarted() const { return m_started; } + bool IsJumpedTime() const { return m_jumped_time; } + TimelineState::Type GetState() const { return m_state; } + +private: + void CalcImpl(); + void JumpTimeToImpl(float time); + void AdvanceTimeToImpl(float time); + + static int s_GlobalPlayCounter; + + void Finalize() { + m_timeline = nullptr; + m_act_binder.Reset(); + m_sub_timelines.Clear(&m_allocator); + } + + EvflAllocator m_allocator; + ore::Array m_sub_timelines; + const ResTimeline* m_timeline{}; + ActBinder m_act_binder{}; + float m_time{}; + float m_new_time{}; + int m_last_trigger_idx = -1; + int m_last_oneshot_idx = -1; + int m_play_counter = 0; + bool m_started = false; + bool m_jumped_time = false; + ore::SizedEnum m_state = TimelineState::kNotStarted; +}; + +} // namespace evfl diff --git a/lib/EventFlow/include/ore/Allocator.h b/lib/EventFlow/include/ore/Allocator.h new file mode 100644 index 00000000..23f6cd81 --- /dev/null +++ b/lib/EventFlow/include/ore/Allocator.h @@ -0,0 +1,45 @@ +#pragma once + +#include +#include +#include + +namespace ore { + +class Allocator { +public: + Allocator() = default; + virtual ~Allocator() = default; + + void* New(size_t size, size_t alignment = alignof(std::max_align_t)) { + return AllocImpl(size, alignment); + } + + template + T* New(size_t alignment = alignof(std::max_align_t)) { + auto* buffer = AllocImpl(sizeof(T), alignment); + if (buffer) + return new (buffer) T; + return static_cast(buffer); + } + + template + void Delete(T* ptr) { + std::destroy_at(ptr); + Free(ptr); + } + + template + void DeleteAndNull(T*& ptr) { + std::destroy_at(ptr); + Free(ptr); + ptr = nullptr; + } + + void Free(void* ptr) { FreeImpl(ptr); } + + virtual void* AllocImpl(size_t size, size_t alignment) = 0; + virtual void FreeImpl(void* ptr) = 0; +}; + +} // namespace ore diff --git a/lib/EventFlow/include/ore/Array.h b/lib/EventFlow/include/ore/Array.h new file mode 100644 index 00000000..342ce62d --- /dev/null +++ b/lib/EventFlow/include/ore/Array.h @@ -0,0 +1,287 @@ +#pragma once + +#include +#include +#include +#include +#include +#include +#include + +namespace ore { + +// This is like a std::span, not a fixed-size array like std::array. +// Elements will NOT be automatically freed. +template +class Array { +public: + Array() = default; + Array(T* data, int size) : m_data(data), m_size(size) {} + + T* data() const { return m_data; } + int size() const { return m_size; } + + auto begin() const { return data(); } + auto end() const { return data() + size(); } + + T& operator[](int idx) { return m_data[idx]; } + const T& operator[](int idx) const { return m_data[idx]; } + + T& front() { return m_data[0]; } + const T& front() const { return m_data[0]; } + + T& back() { return m_data[m_size - 1]; } + const T& back() const { return m_data[m_size - 1]; } + + void SetBuffer(void* new_buffer, int num) { + DestructElements(); + m_data = static_cast(new_buffer); + m_size = num; + } + + void SetBuffer(int num, Allocator* allocator) { + auto* new_buffer = allocator->AllocImpl(num * int(sizeof(T)), alignof(std::max_align_t)); + SetBuffer(new_buffer, num); + } + + void ConstructElements(int num, Allocator* allocator) { + SetBuffer(num, allocator); + DefaultConstructElements(); + } + + void ConstructElements(void* new_buffer, int num) { + SetBuffer(new_buffer, num); + DefaultConstructElements(); + } + + void ConstructElements(Buffer buffer) { + DestructElements(); + m_data = reinterpret_cast(buffer.data); + m_size = buffer.size / int(sizeof(T)); + DefaultConstructElements(); + } + + void DestructElements() { std::destroy(begin(), end()); } + + void ClearWithoutFreeing() { + DestructElements(); + m_data = nullptr; + m_size = 0; + } + + void Clear(Allocator* allocator) { + if (!m_data) + return; + auto* data = m_data; + ClearWithoutFreeing(); + allocator->Free(data); + } + + void DefaultConstructElements() { + for (auto it = begin(), e = end(); it != e;) + new (it++) T; + } + + void UninitializedDefaultConstructElements() { + std::uninitialized_default_construct(begin(), end()); + } + +private: + T* m_data{}; + int m_size{}; +}; + +template +class SelfDestructingArray : public Array { +public: + ~SelfDestructingArray() { this->DestructElements(); } +}; + +template +class ArrayListBase { +public: + ArrayListBase() : m_data(), m_size(), m_capacity() {} + ArrayListBase(T* data, int capacity) { + m_size = 0; + m_data = data; + m_capacity = capacity; + } + ~ArrayListBase() { clear(); } + + ArrayListBase(const ArrayListBase&) = delete; + auto operator=(const ArrayListBase&) = delete; + + T* begin() { return m_data; } + const T* begin() const { return m_data; } + + T* end() { return m_data + m_size; } + const T* end() const { return m_data + m_size; } + + T* data() { return m_data; } + const T* data() const { return m_data; } + + int size() const { return m_size; } + int capacity() const { return m_capacity; } + + T& operator[](int idx) { return m_data[idx]; } + const T& operator[](int idx) const { return m_data[idx]; } + + T& front() { return m_data[0]; } + const T& front() const { return m_data[0]; } + + T& back() { return m_data[m_size - 1]; } + const T& back() const { return m_data[m_size - 1]; } + + template + T& emplace_back(Args&&... args) { + auto* item = new (&m_data[m_size++]) T(std::forward(args)...); + return *item; + } + + void push_back(const T& item) { new (&m_data[m_size++]) T(item); } + + void pop_back() { + std::destroy_at(&back()); + --m_size; + } + + void clear() { + std::destroy(begin(), end()); + m_size = 0; + } + + T* m_data; + int m_size; + int m_capacity; +}; + +template +class FixedArrayList : public ArrayListBase { +public: + FixedArrayList() : ArrayListBase(reinterpret_cast(m_storage), N) {} + +private: + std::aligned_storage_t m_storage[N]; +}; + +// This is like a std::vector. +template +class DynArrayList : public ArrayListBase { +public: + DynArrayList() = default; + explicit DynArrayList(Allocator* allocator) : m_allocator(allocator) {} + + ~DynArrayList() { + clear(); + m_allocator = nullptr; + this->m_size = 0; + } + + void Reset() { + clear(); + m_allocator = nullptr; + } + + DynArrayList(const DynArrayList&) = delete; + auto operator=(const DynArrayList&) = delete; + + void Init(Allocator* allocator, int initial_capacity = 1) { + clear(); + m_allocator = allocator; + Reallocate(initial_capacity); + } + + template + T& emplace_back(Args&&... args) { + GrowIfNeeded(); + return ArrayListBase::emplace_back(std::forward(args)...); + } + + void push_back(const T& item) { + GrowIfNeeded(); + return ArrayListBase::push_back(item); + } + + void clear() { + std::destroy(this->begin(), this->end()); + auto* data = this->m_data; + this->m_data = nullptr; + this->m_size = 0; + this->m_capacity = 0; + Free(data); + } + + template + void OverwriteWith(InputIterator src_begin, InputIterator src_end) { + const int src_size = std::distance(src_begin, src_end); + if (src_size > this->m_capacity) { + this->m_size = 0; + Reallocate(2 * src_size); + } + this->m_size = src_size; + std::uninitialized_copy(src_begin, src_end, this->begin()); + } + + /// Quadratic complexity; only use this for small copies. + template + void DeduplicateCopy(const Range& range) { + for (auto it = range.begin(), end = range.end(); it != end; ++it) { + auto value = *it; + if (std::find_if(range.begin(), it, [&](const auto& v) { return value == v; }) == it) + this->emplace_back(value); + } + } + + /// Resize the array so that it contains `new_size` elements. + /// + /// - If the new size is greater than the current size, new elements are added and + /// default initialized. Iterators may be invalidated. + /// - If the new size is less than the current size, excess elements are destroyed. + /// + /// @param new_size The new size of the array. + void Resize(int new_size) { + if (this->m_capacity < new_size) + Reallocate(new_size); + + if (this->m_size < new_size) { + std::uninitialized_default_construct(this->m_data + this->m_size, + this->m_data + new_size); + } else { + std::destroy(this->m_data + new_size, this->m_data + this->m_size); + } + + this->m_size = new_size; + } + +private: + void GrowIfNeeded() { + if (this->m_size < this->m_capacity) + return; + Reallocate(2 * this->m_size + 2); + } + + void Reallocate(int new_capacity) { + const int num_bytes = sizeof(T) * new_capacity; + auto* new_buffer = + static_cast(m_allocator->AllocImpl(num_bytes, alignof(std::max_align_t))); + auto* old_buffer = this->m_data; + auto* capacity = &this->m_capacity; + UninitializedCopyTo(new_buffer); + this->m_data = new_buffer; + *capacity = new_capacity; + Free(old_buffer); + } + + void UninitializedCopyTo(T* destination) const { + std::uninitialized_copy(this->begin(), this->end(), destination); + } + + void Free(void* ptr) { + if (ptr) + m_allocator->Free(ptr); + } + + Allocator* m_allocator{}; +}; + +} // namespace ore diff --git a/lib/EventFlow/include/ore/BinaryFile.h b/lib/EventFlow/include/ore/BinaryFile.h new file mode 100644 index 00000000..c2d62587 --- /dev/null +++ b/lib/EventFlow/include/ore/BinaryFile.h @@ -0,0 +1,153 @@ +#pragma once + +#include +#include +#include +#include + +namespace ore { + +template +constexpr T AlignUpToPowerOf2(T val, int base) { + return val + base - 1 & static_cast(-base); +} + +struct RelocationTable; + +struct BinaryBlockHeader { + BinaryBlockHeader* FindNextBlock(int type); + const BinaryBlockHeader* FindNextBlock(int type) const; + BinaryBlockHeader* GetNextBlock(); + const BinaryBlockHeader* GetNextBlock() const; + void SetNextBlock(BinaryBlockHeader* block); + + u32 magic; + int next_block_offset; +}; + +struct BinaryFileHeader { + bool IsValid(s64 magic_, int ver_major_, int ver_minor_, int ver_patch_, int ver_sub_) const; + bool IsSignatureValid(s64 magic_) const; + bool IsVersionValid(int major, int minor, int patch, int sub) const; + bool IsEndianReverse() const; + bool IsEndianValid() const; + + bool IsAlignmentValid() const; + int GetAlignment() const; + void SetAlignment(int alignment_); + + bool IsRelocated() const; + void SetRelocated(bool relocated); + + void SetByteOrderMark(); + + int GetFileSize() const; + void SetFileSize(int size); + + StringView GetFileName() const; + void SetFileName(const StringView& name); + + RelocationTable* GetRelocationTable(); + void SetRelocationTable(RelocationTable* table); + + BinaryBlockHeader* GetFirstBlock(); + const BinaryBlockHeader* GetFirstBlock() const; + void SetFirstBlock(BinaryBlockHeader* block); + + BinaryBlockHeader* FindFirstBlock(int type); + const BinaryBlockHeader* FindFirstBlock(int type) const; + + u64 magic; + u8 ver_major; + u8 ver_minor; + u8 ver_patch; + u8 ver_sub; + s16 bom; + u8 alignment; + u8 _f; + int file_name_offset; + u16 relocation_flags; + u16 first_block_offset; + int relocation_table_offset; + int file_size; +}; + +template +struct BinTString { + // Make it impossible to accidentally construct a (partial, broken) copy. + BinTString(const BinTString&) = delete; + auto operator=(const BinTString&) = delete; + + T* data() { return chars; } + const T* data() const { return chars; } + + T& operator[](size_t idx) { return data()[idx]; } + const T& operator[](size_t idx) const { return data()[idx]; } + + auto begin() { return data(); } + auto begin() const { return data(); } + + auto end() { return data() + length; } + auto end() const { return data() + length; } + + bool empty() const { return length == 0; } + + // NOLINTNEXTLINE(google-explicit-constructor) + operator TStringView() const { return {data(), length}; } + + BinTString* NextString() { return const_cast(std::as_const(*this).NextString()); } + + const BinTString* NextString() const { + // XXX: this shouldn't have to be a separate case. + if constexpr (std::is_same_v) { + const auto offset = ((2 + (4 * (length + 1) - 1)) & -4) + 2; + return reinterpret_cast(reinterpret_cast(this) + + offset); + + } else { + // + 1 for the null terminator + const auto offset = offsetof(BinTString, chars) + sizeof(T) * (length + 1); + return reinterpret_cast( + reinterpret_cast(this) + + AlignUpToPowerOf2(offset, alignof(BinTString))); + } + } + + u16 length; + T chars[1]; +}; + +using BinString = BinTString; +using BinWString = BinTString; + +template +struct BinTPtr { + void Clear() { offset_or_ptr = 0; } + void Set(T* ptr) { offset_or_ptr = reinterpret_cast(ptr); } + + // Only use this after relocation. + T* Get() { return reinterpret_cast(offset_or_ptr); } + const T* Get() const { return reinterpret_cast(offset_or_ptr); } + + void SetOffset(void* base, void* ptr) { + offset_or_ptr = static_cast(ptr ? uintptr_t(ptr) - uintptr_t(base) : 0); + } + + u64 GetOffset() const { return offset_or_ptr; } + + T* ToPtr(void* base) const { + const auto offset = static_cast(offset_or_ptr); + if (offset == 0) + return nullptr; + return reinterpret_cast(reinterpret_cast(base) + offset); + } + + void Relocate(void* base) { Set(ToPtr(base)); } + void Unrelocate(void* base) { SetOffset(base, Get()); } + + u64 offset_or_ptr; +}; + +static_assert(sizeof(u64) >= sizeof(void*)); + +} // namespace ore diff --git a/lib/EventFlow/include/ore/BitUtils.h b/lib/EventFlow/include/ore/BitUtils.h new file mode 100644 index 00000000..fd907f9c --- /dev/null +++ b/lib/EventFlow/include/ore/BitUtils.h @@ -0,0 +1,149 @@ +#pragma once + +#include +#include + +namespace ore { + +constexpr int PopCount(u32 x) { + x = x - ((x >> 1) & 0x55555555); + x = (x & 0x33333333) + ((x >> 2) & 0x33333333); + x = (x + (x >> 4)) & 0x0F0F0F0F; + x += (x >> 8); + x += (x >> 16); + return int(x & 0x3f); +} + +constexpr int PopCount(u64 x) { + x = x - ((x >> 1) & 0x5555555555555555); + x = (x & 0x3333333333333333) + ((x >> 2) & 0x3333333333333333); + x = (x + (x >> 4)) & 0x0F0F0F0F0F0F0F0F; + x += (x >> 8); + x += (x >> 16); + x += (x >> 32); + return int(x & 0x7f); +} + +constexpr int CountTrailingZeros(u32 x) { + return PopCount((x & -x) - 1); +} + +constexpr int CountTrailingZeros(u64 x) { + return PopCount((x & -x) - 1); +} + +namespace detail { +template +constexpr T AlignUpToPowerOf2(T val, int base) { + return val + base - 1 & static_cast(-base); +} +} // namespace detail + +class BitArray { +public: + using Word = size_t; + static constexpr int NumBitsPerWord = sizeof(Word) * 8; + static constexpr int ClearMask = ~(NumBitsPerWord - 1); + static constexpr int ShiftAmount = CountTrailingZeros(u32(NumBitsPerWord)); + + class TestIter { + public: + TestIter(const Word* start, const Word* end); + TestIter& operator++(); + + int operator*() const { return m_bit; } + bool operator==(const TestIter& other) const { return m_bit == other.m_bit; } + bool operator!=(const TestIter& other) const { return !operator==(other); } + + private: + void SetInvalid() { + m_bit = -1; + m_current_word = nullptr; + m_last_word = nullptr; + m_next = 0; + } + + int m_bit; + const Word* m_current_word; + const Word* m_last_word; + Word m_next; + }; + + /// Same as TestIter but clears bits after iterating over them. + class TestClearIter { + public: + TestClearIter(Word* start, Word* end); + TestClearIter& operator++(); + int operator*() const { return m_bit; } + bool operator==(const TestClearIter& other) const { return m_bit == other.m_bit; } + bool operator!=(const TestClearIter& other) const { return !operator==(other); } + + private: + void SetInvalid() { + m_bit = -1; + m_current_word = nullptr; + m_last_word = nullptr; + m_next = 0; + } + + int m_bit; + Word* m_current_word; + Word* m_last_word; + Word m_next; + }; + + constexpr BitArray() = default; + constexpr BitArray(void* buffer, int num_bits) { SetData(buffer, num_bits); } + constexpr BitArray(ore::Allocator* allocator, int num_bits) { + AllocateBuffer(allocator, num_bits); + } + + void SetData(void* buffer, int num_bits) { + m_words = reinterpret_cast(buffer); + m_num_bits = num_bits; + } + + void AllocateBuffer(ore::Allocator* allocator, int num_bits) { + SetData(allocator->New(GetRequiredBufferSize(num_bits)), num_bits); + SetAllOff(); + } + + void FreeBufferIfNeeded(ore::Allocator* allocator) { + if (m_words) + allocator->Delete(m_words); + } + + void FreeBuffer(ore::Allocator* allocator) { allocator->Delete(m_words); } + + bool Test(int bit) const { + return (GetWord(bit) & (Word(1) << (Word(bit) % NumBitsPerWord))) != 0; + } + void Set(int bit) { GetWord(bit) |= Word(1) << (Word(bit) % NumBitsPerWord); } + void Clear(int bit) { GetWord(bit) &= ~(Word(1) << (Word(bit) % NumBitsPerWord)); } + + void SetAllOn(); + void SetAllOff(); + TestIter BeginTest() const; + TestIter EndTest() const; + TestClearIter BeginTestClear(); + TestClearIter EndTestClear(); + + static int GetRequiredBufferSize(int num_bits) { + return sizeof(Word) * (detail::AlignUpToPowerOf2(num_bits, NumBitsPerWord) >> ShiftAmount); + } + +private: + Word& GetWord(int bit) const { return m_words[bit >> ShiftAmount]; } + int GetNumWords() const { return int((m_num_bits + NumBitsPerWord - 1) >> ShiftAmount); } + + void Fill(int num, Word value) { + auto* it = m_words; + for (int i = num - 1; i >= 0; --i) + *it++ = value; + } + + Word* m_words{}; + int m_num_bits{}; +}; + +} // namespace ore diff --git a/lib/EventFlow/include/ore/Buffer.h b/lib/EventFlow/include/ore/Buffer.h new file mode 100644 index 00000000..0952ab6c --- /dev/null +++ b/lib/EventFlow/include/ore/Buffer.h @@ -0,0 +1,25 @@ +#pragma once + +#include +#include + +namespace ore { + +struct Buffer { + template + void Allocate(Allocator* allocator, int num) { + size = sizeof(T) * num; + data = static_cast(allocator->New(size)); + } + + void Free(Allocator* allocator) { + allocator->Free(data); + data = nullptr; + size = 0; + } + + char* data; + int size; +}; + +} // namespace ore diff --git a/lib/EventFlow/include/ore/EnumUtil.h b/lib/EventFlow/include/ore/EnumUtil.h new file mode 100644 index 00000000..e0c2d953 --- /dev/null +++ b/lib/EventFlow/include/ore/EnumUtil.h @@ -0,0 +1,115 @@ +#pragma once + +#include +#include +#include +#include + +namespace ore { + +namespace detail::EnumUtil { + +int FindIndex(int value, const IterRange& values); +void Parse(const IterRange& out, StringView definition); + +constexpr int CountValues(const char* text_all, size_t text_all_len) { + int count = 1; + for (size_t i = 0; i < text_all_len; ++i) { + if (text_all[i] == ',') + ++count; + } + return count; +} + +} // namespace detail::EnumUtil + +template +struct Enum { +public: + Enum() { T::Init(); } + + static Enum& Info() { return s_Info; } + + StringView name{}; + IterRange members{}; + +private: + static inline Enum s_Info{}; +}; + +#define ORE_ENUM(NAME, ...) \ + class NAME { \ + public: \ + enum Type { __VA_ARGS__ }; \ + \ + static void Init() { \ + static ore::StringView names[cCount]; \ + ore::detail::EnumUtil::Parse(ore::IterRange(names), cTextAll); \ + ore::Enum::Info().name = #NAME; \ + ore::Enum::Info().members = ore::IterRange(names); \ + } \ + \ + static constexpr int Size() { return cCount; } \ + static constexpr Type Invalid() { return Type(Size()); } \ + \ + private: \ + static constexpr const char* cTextAll = #__VA_ARGS__; \ + static constexpr size_t cTextAllLen = sizeof(#__VA_ARGS__); \ + static constexpr int cCount = ore::detail::EnumUtil::CountValues(cTextAll, cTextAllLen); \ + }; + +// FIXME +template +class ValuedEnum { +public: + ValuedEnum() { T::Init(); } + + static Enum& Info() { return s_Info; } + + StringView name{}; + IterRange members{}; + +private: + static inline Enum s_Info{}; +}; + +#define ORE_VALUED_ENUM(NAME, ...) \ + class NAME { \ + public: \ + enum Type { __VA_ARGS__ }; \ + \ + static void Init() { \ + static ore::StringView names[cCount]; \ + ore::detail::EnumUtil::Parse(ore::IterRange(names), cTextAll); \ + ore::ValuedEnum::Info().name = #NAME; \ + ore::ValuedEnum::Info().members = ore::IterRange(names); \ + } \ + \ + static constexpr int Size() { return cCount; } \ + static constexpr Type Invalid() { return Type(Size()); } \ + \ + private: \ + static constexpr const char* cTextAll = #__VA_ARGS__; \ + static constexpr size_t cTextAllLen = sizeof(#__VA_ARGS__); \ + static constexpr int cCount = ore::detail::EnumUtil::CountValues(cTextAll, cTextAllLen); \ + }; + +/// For storing an enum with a particular storage size when specifying the underlying type of the +/// enum is not an option. +template +struct SizedEnum { + static_assert(std::is_enum()); + static_assert(!std::is_enum()); + + constexpr SizedEnum() = default; + constexpr SizedEnum(Enum value) { *this = value; } + constexpr operator Enum() const { return static_cast(mValue); } + constexpr SizedEnum& operator=(Enum value) { + mValue = static_cast(value); + return *this; + } + + Storage mValue; +}; + +} // namespace ore diff --git a/lib/EventFlow/include/ore/IntrusiveList.h b/lib/EventFlow/include/ore/IntrusiveList.h new file mode 100644 index 00000000..33f4e257 --- /dev/null +++ b/lib/EventFlow/include/ore/IntrusiveList.h @@ -0,0 +1,100 @@ +#pragma once + +#include + +namespace ore { + +class IntrusiveListNode { +public: + constexpr explicit IntrusiveListNode() { m_prev = m_next = this; } + + IntrusiveListNode(const IntrusiveListNode&) = delete; + auto operator=(const IntrusiveListNode&) = delete; + + IntrusiveListNode(IntrusiveListNode&& other) noexcept { *this = std::move(other); } + IntrusiveListNode& operator=(IntrusiveListNode&& other) noexcept { + auto* prev = other.m_prev; + other.m_prev = this; + prev->m_next = this; + m_prev = prev; + m_next = &other; + other.Erase(); + return *this; + } + + IntrusiveListNode* Prev() const { return m_prev; } + IntrusiveListNode* Next() const { return m_next; } + bool IsLinked() const { return Prev() || Next(); } + + void Erase() { + auto* next = m_next; + auto* next_prev = next->m_prev; + m_prev->m_next = next; + next->m_prev = m_prev; + // This is a circular list. + next_prev->m_next = this; + m_prev = next_prev; + } + + void InsertFront(IntrusiveListNode* node) { + auto* prev = node->m_prev; + node->m_prev = m_prev; + prev->m_next = this; + m_prev->m_next = node; + m_prev = prev; + } + +private: + template + friend class IntrusiveList; + + IntrusiveListNode* m_prev{}; + IntrusiveListNode* m_next{}; +}; + +template +class IntrusiveList { +public: + void SetOffset(int offset) { m_offset = offset; } + + bool Empty() const { return m_node.m_next == &m_node; } + T* Front() { return NodeToItemWithNullCheck(m_node.m_next); } + T* Back() { return NodeToItemWithNullCheck(m_node.m_prev); } + const T* Front() const { return NodeToItemWithNullCheck(m_node.m_next); } + const T* Back() const { return NodeToItemWithNullCheck(m_node.m_prev); } + + void Erase(T* item) { ItemToNode(item)->Erase(); } + + void InsertFront(T* item) { m_node.InsertFront(ItemToNode(item)); } + +private: + IntrusiveListNode* ItemToNode(T* item) const { + return reinterpret_cast(reinterpret_cast(item) + m_offset); + } + + const IntrusiveListNode* ItemToNode(const T* item) const { + return reinterpret_cast(reinterpret_cast(item) + + m_offset); + } + + T* NodeToItem(IntrusiveListNode* node) const { + return reinterpret_cast(reinterpret_cast(node) - m_offset); + } + + const T* NodeToItem(const IntrusiveListNode* node) const { + return reinterpret_cast(reinterpret_cast(node) - m_offset); + } + + T* NodeToItemWithNullCheck(IntrusiveListNode* node) const { + return node == &m_node ? nullptr : NodeToItem(node); + } + + const T* NodeToItemWithNullCheck(const IntrusiveListNode* node) const { + return node == &m_node ? nullptr : NodeToItem(node); + } + + IntrusiveListNode m_node; + int m_offset = -1; +}; + +} // namespace ore diff --git a/lib/EventFlow/include/ore/IterRange.h b/lib/EventFlow/include/ore/IterRange.h new file mode 100644 index 00000000..338628ca --- /dev/null +++ b/lib/EventFlow/include/ore/IterRange.h @@ -0,0 +1,28 @@ +#pragma once + +#include + +namespace ore { + +template +class IterRange { +public: + constexpr IterRange() = default; + constexpr IterRange(const T& begin_, const T& end_) : m_begin(begin_), m_end(end_) {} + template + // NOLINTNEXTLINE(google-explicit-constructor) + constexpr IterRange(Other& x) : IterRange(std::begin(x), std::end(x)) {} + + constexpr IterRange(const T& begin, int size) : m_begin(begin), m_end(begin + size) {} + + const auto& begin() const { return m_begin; } + const auto& end() const { return m_end; } + + int size() const { return end() - begin(); } + +private: + T m_begin{}; + T m_end{}; +}; + +} // namespace ore diff --git a/lib/EventFlow/include/ore/RelocationTable.h b/lib/EventFlow/include/ore/RelocationTable.h new file mode 100644 index 00000000..4593abb3 --- /dev/null +++ b/lib/EventFlow/include/ore/RelocationTable.h @@ -0,0 +1,50 @@ +#pragma once + +#include + +namespace ore { + +struct RelocationTable { + struct Section { + struct Entry { + /// Offset to pointers to relocate + int pointers_offset; + /// Bit field that determines which pointers need to be relocated + /// (next to 32 contiguous pointers starting from the listed offset) + u32 mask; + }; + + void SetPtr(void* ptr_); + void* GetPtr() const; + void* GetPtrInFile(void* base) const; + void* GetBasePtr(void* base) const; + u32 GetSize() const; + + u64 ptr; + int offset; + int size; + int first_entry_idx; + int num_entries; + }; + + u32 magic; + int table_start_offset; + int num_sections; + Section sections[1]; + + Section* GetSections() { return sections; } + const Section* GetSections() const { return sections; } + + Section::Entry* GetEntries() { + return reinterpret_cast(GetSections() + num_sections); + } + const Section::Entry* GetEntries() const { + return reinterpret_cast(GetSections() + num_sections); + } + + void Relocate(); + void Unrelocate(); + static int CalcSize(int num_sections, int num_entries); +}; + +} // namespace ore diff --git a/lib/EventFlow/include/ore/ResDic.h b/lib/EventFlow/include/ore/ResDic.h new file mode 100644 index 00000000..d9a686f6 --- /dev/null +++ b/lib/EventFlow/include/ore/ResDic.h @@ -0,0 +1,62 @@ +#pragma once + +#include +#include +#include + +namespace ore { + +struct ResEndian; + +struct ResDicEntry { + StringView GetKey() const { return *name.Get(); } + + // Bits 3-7: index of the byte that should be checked + // Bits 0-2: index of the bit in that byte + int compact_bit_idx; + u16 next_indices[2]; + BinTPtr name; +}; + +struct ResDic { + static int FindRefBit(const StringView& str1, const StringView& str2); + + const ResDicEntry* FindEntry(const StringView& key) const { + auto* prev = &entries[0]; + auto* entry = &entries[prev->next_indices[0]]; + while (prev->compact_bit_idx < entry->compact_bit_idx) { + const int bit_idx = entry->compact_bit_idx; + long bit = 0; + if (u32(key.length()) > u32(bit_idx >> 3)) + bit = ((key[key.length() + -((bit_idx >> 3) + 1)] >> (bit_idx & 7))) & 1; + + prev = entry; + entry = &entries[prev->next_indices[bit]]; + } + return entry; + } + + /// Returns the index for the specified key or -1 if it cannot be found. + int FindIndex(const StringView& key) const { + const auto* entry = FindEntry(key); + const auto entry_name = entry->GetKey(); + bool ok = [&] { return StringView(key.data(), key.length()) == entry_name; }(); + if (!ok) + return -1; + return static_cast(entry - &GetEntries()[1]); + } + + /// Entry 0 is the root entry. + ResDicEntry* GetEntries() { return entries; } + /// Entry 0 is the root entry. + const ResDicEntry* GetEntries() const { return entries; } + + u32 magic; + int num_entries; + ResDicEntry entries[1]; + // Followed by ResDicEntry[num_entries]. +}; + +void SwapEndian(ResEndian* endian, ResDic* dic); + +} // namespace ore diff --git a/lib/EventFlow/include/ore/ResEndian.h b/lib/EventFlow/include/ore/ResEndian.h new file mode 100644 index 00000000..dc38e111 --- /dev/null +++ b/lib/EventFlow/include/ore/ResEndian.h @@ -0,0 +1,75 @@ +#pragma once + +#ifdef _MSC_VER +#include +#endif + +#include +#include + +namespace ore { + +[[nodiscard]] inline u8 SwapEndian(u8 x) { + return x; +} + +[[nodiscard]] inline u16 SwapEndian(u16 x) { +#ifdef _MSC_VER + return _byteswap_ushort(x); +#else + return __builtin_bswap16(x); +#endif +} + +[[nodiscard]] inline u32 SwapEndian(u32 x) { +#ifdef _MSC_VER + return _byteswap_ulong(x); +#else + return __builtin_bswap32(x); +#endif +} + +[[nodiscard]] inline u64 SwapEndian(u64 x) { +#ifdef _MSC_VER + return _byteswap_uint64(x); +#else + return __builtin_bswap64(x); +#endif +} + +[[nodiscard]] inline s8 SwapEndian(s8 x) { + return SwapEndian(u8(x)); +} + +[[nodiscard]] inline s16 SwapEndian(s16 x) { + return SwapEndian(u16(x)); +} + +[[nodiscard]] inline s32 SwapEndian(s32 x) { + return SwapEndian(u32(x)); +} + +[[nodiscard]] inline s64 SwapEndian(s64 x) { + return SwapEndian(u64(x)); +} + +[[nodiscard]] inline f32 SwapEndian(f32 x) { + static_assert(sizeof(u32) == sizeof(f32)); + u32 i; + std::memcpy(&i, &x, sizeof(i)); + i = SwapEndian(i); + std::memcpy(&x, &i, sizeof(i)); + return x; +} + +template +inline void SwapEndian(T* value) { + *value = SwapEndian(*value); +} + +struct ResEndian { + char* base; + bool is_serializing; +}; + +} // namespace ore diff --git a/lib/EventFlow/include/ore/ResMetaData.h b/lib/EventFlow/include/ore/ResMetaData.h new file mode 100644 index 00000000..60e84cd0 --- /dev/null +++ b/lib/EventFlow/include/ore/ResMetaData.h @@ -0,0 +1,58 @@ +#pragma once + +#include +#include +#include +#include +#include + +namespace ore { + +struct ResDic; +struct ResEndian; + +struct ResMetaData { + struct ActorIdentifier { + BinTPtr name; + BinTPtr sub_name; + }; + + union Value { + BinTPtr container; + // Also used for booleans. Anything that is != 0 is treated as true. + int i; + float f; + BinTPtr str; + BinTPtr wstr; + ActorIdentifier actor; + }; + + ORE_ENUM(DataType, kArgument, kContainer, kInt, kBool, kFloat, kString, kWString, kIntArray, kBoolArray, kFloatArray, kStringArray, kWStringArray, kActorIdentifier) + + /// @warning Only usable if type == kContainer. + const ResMetaData* Get(const StringView& key, DataType::Type expected_type) const { + const int idx = dictionary.Get()->FindIndex(key); + if (idx == -1) + return nullptr; + + const auto* meta = (&value.container + idx)->Get(); + if (meta->type != expected_type) + return nullptr; + + return meta; + } + + SizedEnum type; + u16 num_items; + BinTPtr dictionary; + Value value; +}; + +// XXX: is this unused? +struct ResUserData { + ORE_ENUM(DataType, kInt, kFloat, kString, kWString, kStream) +}; + +void SwapEndian(ResEndian* endian, ResMetaData* res); + +} // namespace ore diff --git a/lib/EventFlow/include/ore/StringPool.h b/lib/EventFlow/include/ore/StringPool.h new file mode 100644 index 00000000..2777ce2b --- /dev/null +++ b/lib/EventFlow/include/ore/StringPool.h @@ -0,0 +1,20 @@ +#pragma once + +#include +#include + +namespace ore { + +struct StringPool : BinaryBlockHeader { + int GetLength() const; + void SetLength(int len); + + BinString* GetFirstString() { return dummy_string.NextString(); } + + u32 reserved_8; + u32 reserved_c; + int length; + BinString dummy_string; +}; + +} // namespace ore diff --git a/lib/EventFlow/include/ore/StringView.h b/lib/EventFlow/include/ore/StringView.h new file mode 100644 index 00000000..f23d47f5 --- /dev/null +++ b/lib/EventFlow/include/ore/StringView.h @@ -0,0 +1,79 @@ +#pragma once + +#include +#include +#include + +namespace ore { + +template +constexpr size_t StringLength(const T* str) { + if (str == nullptr || str[0] == 0) + return 0; + + size_t len = 0; + while (*str++ != 0) + ++len; + +#ifdef MATCHING_HACK_NX_CLANG + __builtin_assume(len <= 0xffffffff); +#endif + return len; +} + +template +class TStringView { +public: + // Annoyingly enough, this cannot be defaulted (otherwise Clang will not dynamically + // initialize static StringView variables). + TStringView() {} + + constexpr TStringView(const T* data, size_t len) : m_data(data), m_len(len) {} + + /// @param data A null-terminated string. Must not be nullptr. + // NOLINTNEXTLINE(google-explicit-constructor) + TStringView(const T* data) : m_data(data), m_len(StringLength(data)) {} + + constexpr const T* data() const { return m_data; } + constexpr int size() const { return m_len; } + constexpr int length() const { return m_len; } + constexpr bool empty() const { return size() == 0; } + + constexpr auto begin() const { return m_data; } + constexpr auto cbegin() const { return m_data; } + constexpr auto end() const { return m_data + m_len; } + constexpr auto cend() const { return m_data + m_len; } + + const T& operator[](size_t idx) const { return m_data[idx]; } + + static int Compare(TStringView lhs, TStringView rhs) { + const T* s1 = lhs.data(); + const T* s2 = rhs.data(); + int len = std::min(lhs.size(), rhs.size()); + if (len < 1) + return lhs.size() - rhs.size(); + while (len-- > 0) { + if (*s1 == 0 || *s1 != *s2) + return *s1 - *s2; + ++s1, ++s2; + } + return lhs.size() - rhs.size(); + } + + int Compare(TStringView rhs) const { return Compare(*this, rhs); } + + friend bool operator==(TStringView lhs, TStringView rhs) { + return lhs.size() == rhs.size() && Compare(lhs, rhs) == 0; + } + + friend bool operator!=(TStringView lhs, TStringView rhs) { return !operator==(lhs, rhs); } + +private: + const T* m_data{}; + u32 m_len{}; +}; + +using StringView = TStringView; +using WStringView = TStringView; + +} // namespace ore diff --git a/lib/EventFlow/include/ore/Types.h b/lib/EventFlow/include/ore/Types.h new file mode 100644 index 00000000..601d9dd6 --- /dev/null +++ b/lib/EventFlow/include/ore/Types.h @@ -0,0 +1,20 @@ +#pragma once + +#include +#include + +using u8 = std::uint8_t; +using u16 = std::uint16_t; +using u32 = std::uint32_t; +using u64 = std::uint64_t; + +using s8 = std::int8_t; +using s16 = std::int16_t; +using s32 = std::int32_t; +using s64 = std::int64_t; + +using f32 = float; +using f64 = double; + +using char16 = char16_t; +using size_t = std::size_t; diff --git a/lib/EventFlow/src/evfl/Action.cpp b/lib/EventFlow/src/evfl/Action.cpp new file mode 100644 index 00000000..5fe7a490 --- /dev/null +++ b/lib/EventFlow/src/evfl/Action.cpp @@ -0,0 +1,56 @@ +#include +#include + +namespace evfl { + +ActionDoneHandler::ActionDoneHandler(FlowchartObj* obj, FlowchartContext* context, int node_idx) + : m_context(context) { + m_node_idx = node_idx; + m_obj = obj; + m_node_counter = context->GetNode(node_idx).GetNodeCounter(); +} + +FlowchartContextNode* ActionDoneHandler::GetContextNode() { + if (!m_context) + return nullptr; + + auto& node = m_context->GetNode(m_node_idx); + if (node.GetNodeCounter() != m_node_counter) + return nullptr; + + return &node; +} + +void ActionDoneHandler::InvokeFromFlowchartImpl() { + auto* node = GetContextNode(); + if (!node) + return; + + node->m_state = FlowchartContextNode::State::kDone; + m_context->ProcessContext(); +} + +void ActionDoneHandler::InvokeFromTimelineImpl() {} + +bool ActionDoneHandler::IsWaitingJoin() { + if (!m_context) + return false; + + const auto& node = m_context->GetNode(m_node_idx); + if (node.GetNodeCounter() != m_node_counter) + return false; + + return node.GetState() == FlowchartContextNode::State::kWaiting; +} + +bool ActionDoneHandler::CancelWaiting() { + auto* node = GetContextNode(); + if (!node) + return false; + + node->m_state = FlowchartContextNode::State::kInvoked; + m_handled = false; + return true; +} + +} // namespace evfl diff --git a/lib/EventFlow/src/evfl/Flowchart.cpp b/lib/EventFlow/src/evfl/Flowchart.cpp new file mode 100644 index 00000000..84c0af05 --- /dev/null +++ b/lib/EventFlow/src/evfl/Flowchart.cpp @@ -0,0 +1,694 @@ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +namespace evfl { + +int FlowchartContext::s_GlobalCounter{}; + +FlowchartContext::FlowchartContext() { + m_handlers.SetOffset(ActionDoneHandler::GetListNodeOffset()); +} + +void FlowchartContext::Start(MetaDataPack* pack) { + auto& obj = m_objs[m_obj_idx]; + const auto& entry_point = obj.GetFlowchart()->entry_points.Get()[m_active_entry_point_idx]; + + const auto main_event_idx = entry_point.main_event_idx; + if (main_event_idx == 0xffff) + return; + + m_metadata_pack = pack; + + const int node_idx = AllocNode(); + auto& node = m_nodes[node_idx]; + node.m_obj = &obj; + node.m_event_idx = main_event_idx; + node.m_next_node_idx = -1; + node.m_idx = node_idx; + node.m_state = FlowchartContextNode::State::kNotInvoked; + AllocVariablePack(node, entry_point); + + ProcessContext(); +} + +int FlowchartContext::AllocNode() { + int idx = m_next_node_idx; + + if (idx == 0xffff) { + idx = m_nodes.size(); + m_nodes.Resize(2 * m_nodes.size()); + for (int i = idx, n = m_nodes.size(); i < n - 1; ++i) { + m_nodes[i].m_next_node_idx = i + 1; + m_nodes[i].m_state = FlowchartContextNode::State::kFree; + } + } + + auto& node = m_nodes[idx]; + m_next_node_idx = node.m_next_node_idx; + node.m_event_idx = -1; + node.m_next_node_idx = -1; + node.m_idx = -1; + node.m_owns_variable_pack = false; + node.m_obj = nullptr; + node.m_variable_pack = nullptr; + node.m_node_counter = ++s_GlobalCounter; + node.m_state = FlowchartContextNode::State::kInvalid; + ++m_num_allocated_nodes; + return idx; +} + +void FlowchartContext::AllocVariablePack(FlowchartContextNode& node, + const ResEntryPoint& entry_point) { + FreeVariablePack(node); + + if (entry_point.num_variable_defs != 0) { + auto* pack = m_allocator.New(); + pack->Init(m_allocator.GetArg(), &entry_point); + node.m_variable_pack = pack; + node.m_owns_variable_pack = true; + } +} + +void FlowchartContext::ProcessContext() { + if (m_is_processing) { + _91 = 1; + } else { + m_is_processing = true; + do { + _91 = 0; + for (int i = 0, n = m_nodes.size(); i < n; ++i) { + if (!m_nodes[i].IsInvalidOrFree()) + _91 = (ProcessContextNode(i) | (_91 != 0)) & 1; + } + } while (_91); + m_is_processing = false; + } +} + +FlowchartObj* FlowchartContext::FindFlowchartObj(ore::StringView name) { + auto it = std::find_if(m_objs.begin(), m_objs.end(), [&](const FlowchartObj& obj) { + return name == *obj.GetFlowchart()->name.Get(); + }); + return it == m_objs.end() ? nullptr : it; +} + +const FlowchartObj* FlowchartContext::FindFlowchartObj(ore::StringView name) const { + auto it = std::find_if(m_objs.begin(), m_objs.end(), [&](const FlowchartObj& obj) { + return name == *obj.GetFlowchart()->name.Get(); + }); + return it == m_objs.end() ? nullptr : it; +} + +void FlowchartContext::UnbindAll() { + Clear(); + for (auto it = m_objs.begin(); it != m_objs.end(); ++it) + it->GetActBinder().UnbindAll(); +} + +void FlowchartContext::Clear() { + for (int i = 0, n = m_nodes.size(); i < n; ++i) { + FreeVariablePack(m_nodes[i]); + m_nodes[i].Reset(); + if (i < n - 1) { + m_nodes[i].m_next_node_idx = i + 1; + m_nodes[i].m_state = FlowchartContextNode::State::kFree; + } + } + + m_next_node_idx = 0; + m_num_allocated_nodes = 0; + m_metadata_pack = nullptr; + + while (!m_handlers.Empty()) { + auto* handler = m_handlers.Front(); + handler->m_list_node.Erase(); + handler->Reset(); + } +} + +void FlowchartContext::FreeVariablePack(FlowchartContextNode& node) { + if (node.m_variable_pack && node.m_owns_variable_pack) + m_allocator.DeleteAndNull(node.m_variable_pack); + + node.m_variable_pack = nullptr; + node.m_owns_variable_pack = false; +} + +void FlowchartContext::CopyVariablePack(FlowchartContextNode& src, FlowchartContextNode& dst) { + FreeVariablePack(dst); + dst.m_variable_pack = src.m_variable_pack; + dst.m_owns_variable_pack = false; +} + +bool FlowchartContext::ProcessContextNode(int node_idx) { + using State = FlowchartContextNode::State; + auto& node = GetNode(node_idx); + while (true) { + auto* obj = node.m_obj; + const auto* flowchart = obj->GetFlowchart(); + const auto& event = flowchart->events.Get()[node.m_event_idx]; + + int next_event_idx = -1; + + switch (event.type) { + case ResEvent::EventType::kAction: { + switch (node.m_state) { + case State::kNotInvoked: { + node.m_state = State::kInvoked; + + const auto actor_idx = event.actor_idx; +#ifdef EVFL_VER_LABO + const auto& actor = flowchart->actors.Get()[actor_idx]; +#else + const auto& actor = obj->GetFlowchart()->actors.Get()[actor_idx]; +#endif + const auto* actions = actor.actions.Get(); + const auto* arg_name = actor.argument_name.Get(); + const auto action_idx = event.actor_action_idx; + + const auto* binding = &obj->GetActBinder().GetBindings()[actor_idx]; + if (!arg_name->empty()) { + binding = TrackBackArgumentActor(node_idx, *arg_name); + if (!binding) + return false; + } + + const auto* action = binding->GetAction(*actions[action_idx].name.Get()); + const ActionArg arg(this, node_idx, binding->GetUserData(), action->user_data, + node.m_variable_pack, &event); + ActionDoneHandler done_handler(obj, this, node_idx); + m_handlers.InsertFront(&done_handler); + action->handler(arg, std::move(done_handler)); + return false; + } // action case State::kNotInvoked + case State::kDone: + next_event_idx = event.next_event_idx; + break; + default: + return false; + } + break; + } // case ResEvent::EventType::kAction + + case ResEvent::EventType::kSwitch: { + if (node.m_state != State::kNotInvoked) + return false; + + const auto actor_idx = event.actor_idx; + const auto& actor = flowchart->actors.Get()[actor_idx]; + const auto* queries = actor.queries.Get(); + const auto* arg_name = actor.argument_name.Get(); + const auto query_idx = event.actor_query_idx; + + const auto* binding = &obj->GetActBinder().GetBindings()[actor_idx]; + if (!arg_name->empty()) { + binding = TrackBackArgumentActor(node_idx, *arg_name); + if (!binding) + return false; + } + + const auto* query = binding->GetQuery(*queries[query_idx].name.Get()); + const QueryArg arg(this, node_idx, binding->GetUserData(), query->user_data, &event, + node.m_variable_pack); + const int result = query->handler(arg); + + next_event_idx = 0xffff; + ore::Array cases{event.cases.Get(), event.num_cases}; + for (const auto& case_ : cases) { + if (case_.value == result) { + next_event_idx = case_.event_idx; + break; + } + } + break; + } // case ResEvent::EventType::kSwitch + + case ResEvent::EventType::kFork: { + if (node.m_state != State::kNotInvoked) + return false; + + node.m_event_idx = event.join_event_idx; + node.m_state = State::kInvoked; + UpdateNodeCounter(node_idx); + + int prev_fork_node_idx = -1; + int first_fork_node_idx = -1; + int last_fork_node_idx = -1; + + const ore::Array forks{event.fork_event_indices.Get(), event.num_forks}; + for (const auto& fork : forks) { + last_fork_node_idx = AllocNode(); + auto& fork_node = GetNode(last_fork_node_idx); + fork_node.m_obj = obj; + fork_node.m_event_idx = fork; + fork_node.m_next_node_idx = node_idx; + fork_node.m_idx = prev_fork_node_idx; + fork_node.m_state = State::kNotInvoked; + if (first_fork_node_idx == -1) + first_fork_node_idx = last_fork_node_idx; + CopyVariablePack(node, fork_node); + prev_fork_node_idx = last_fork_node_idx; + } + + GetNode(first_fork_node_idx).m_idx = u16(last_fork_node_idx); + return true; + } // case ResEvent::EventType::kFork + + case ResEvent::EventType::kJoin: { + if (node.m_state != State::kDone) + return false; + next_event_idx = event.next_event_idx; + break; + } // case ResEvent::EventType::kJoin + + case ResEvent::EventType::kSubFlow: { + bool called; + bool valid_parameters; + bool tried_invoking = false; + switch (node.m_state) { + case State::kNotInvoked: { + tried_invoking = true; + node.m_state = State::kInvoked; + + const ore::StringView sub_flow_flowchart = *event.sub_flow_flowchart.Get(); + if (!sub_flow_flowchart.empty()) { + obj = FindFlowchartObj(sub_flow_flowchart); + if (obj == nullptr) { + called = false; + valid_parameters = false; + break; + } + } + + const int entry_point_idx = obj->GetFlowchart()->entry_point_names.Get()->FindIndex( + *event.sub_flow_entry_point.Get()); + if (entry_point_idx == -1) { + called = false; + valid_parameters = false; + break; + } + + const auto& entry_point = obj->GetFlowchart()->entry_points.Get()[entry_point_idx]; + + const u16 main_event_idx = entry_point.main_event_idx; + if (main_event_idx == 0xffff) { + node.m_state = State::kDone; + called = false; + valid_parameters = true; + break; + } + + // Optimization: if this is a tail call, we don't need to allocate a new node. + if (event.next_event_idx == 0xffff && event.params.Get() == nullptr) { + node.m_obj = obj; + node.m_event_idx = main_event_idx; + node.m_state = State::kNotInvoked; + AllocVariablePack(node, entry_point); + UpdateNodeCounter(node_idx); + } else { + const auto sub_flow_node_idx = AllocNode(); + auto& sub_flow_node = GetNode(sub_flow_node_idx); + sub_flow_node.m_obj = obj; + sub_flow_node.m_event_idx = main_event_idx; + sub_flow_node.m_next_node_idx = node_idx; + sub_flow_node.m_idx = sub_flow_node_idx; + sub_flow_node.m_state = State::kNotInvoked; + AllocVariablePack(sub_flow_node, entry_point); + } + CallSubFlowCallback(flowchart, &event, SubFlowCallbackType::kEnter); + called = true; + /// @bug valid_parameters should have been initialized to true here. + /// This bug causes LLVM to generate dumb code like + /// mov w8, wzr; mov w9, wzr; orr w8, w8, w9 (for the failure cases above) + /// or more worryingly: + /// mov w8, #1; orr w8, w8, w9 + /// where w9 is actually undefined! +#ifdef AVOID_UB + valid_parameters = true; +#endif + break; + } // subflow case State::kNotInvoked + case State::kInvoked: + return false; + case State::kDone: + next_event_idx = event.next_event_idx; + CallSubFlowCallback(flowchart, &event, SubFlowCallbackType::kLeave); + break; + default: + break; + } + if (tried_invoking) + return valid_parameters || called; + break; + } // case ResEvent::EventType::kSubFlow + } + + // We are checking for 0xffff (a 0xffff that comes from the ResEvent data), *not* -1. + if (next_event_idx == 0xffff) { + bool ready = false; + auto* node_2 = &node; + if (node.m_idx != node_idx) { + do { + node_2 = &GetNode(node_2->m_idx); + ready |= node_2->m_state != State::kWaiting; + } while (node_2->m_idx != node_idx); + } + + if (!ready) { + if (node.m_next_node_idx != 0xffff) + GetNode(node.m_next_node_idx).m_state = State::kDone; + + int next_node_idx = node_idx; + int next; + do { + auto& node_to_free = GetNode(next_node_idx); + next = node_to_free.m_idx; + FreeVariablePack(node_to_free); + node_to_free.Reset(); + node_to_free.m_next_node_idx = m_next_node_idx; + node_to_free.m_state = State::kFree; + m_next_node_idx = next_node_idx; + --m_num_allocated_nodes; + next_node_idx = next; + } while (next != node_idx); + return true; + } + + if (event.type == ResEvent::EventType::kAction) { + node.m_state = State::kWaiting; + return true; + } + + node_2->m_idx = node.m_idx; + auto& node_to_free = GetNode(node_idx); + FreeVariablePack(node_to_free); + node_to_free.Reset(); + node_to_free.m_next_node_idx = m_next_node_idx; + node_to_free.m_state = State::kFree; + m_next_node_idx = node_idx; + --m_num_allocated_nodes; + return true; + } + + node.m_event_idx = next_event_idx; + node.m_state = State::kNotInvoked; + UpdateNodeCounter(node_idx); + } +} + +ActorBinding* FlowchartContext::TrackBackArgumentActor(int node_idx, const ore::StringView& name) { + if (node_idx == -1) + return nullptr; + + const ore::ResMetaData* metadata; + const MetaDataPack* metadata_pack; + const VariablePack* variable_pack; + FlowchartObj* obj; + const ParamAccessor accessor{this, GetNode(node_idx).GetNextNodeIdx()}; + const auto real_name = + accessor.TrackBackArgument(&metadata, &metadata_pack, &variable_pack, &obj, name); + + if (real_name.empty() || !metadata || !obj) + return nullptr; + + const auto* param = metadata->Get(real_name, ore::ResMetaData::DataType::kActorIdentifier); + if (!param) + return nullptr; + + const ore::StringView actor_name = *param->value.actor.name.Get(); + const ore::StringView actor_sub_name = *param->value.actor.sub_name.Get(); + + auto actor = obj->GetFlowchart()->actors.Get(); + for (int i = 0; i < int(obj->GetFlowchart()->num_actors); ++i, ++actor) { + if (*actor->name.Get() == actor_name && *actor->secondary_name.Get() == actor_sub_name) { + if (!actor->argument_name.Get()->empty()) + return nullptr; + return &obj->GetActBinder().GetBindings()[i]; + } + } + + return nullptr; +} + +bool FlowchartContext::IsUsing(const ResFlowchart* flowchart) const { + auto* obj = FindFlowchartObj(*flowchart->name.Get()); + return obj && obj->GetActBinder().IsUsed(); +} + +// NON_MATCHING: if (((state | 4) & 7) != 4) -- extremely weird check +bool FlowchartContext::IsPlaying(const ResFlowchart* flowchart) const { + int state = 2; + for (int i = 0, n = m_nodes.size(); i < n; ++i) { + if (m_nodes[i].IsInvalidOrFree()) { + state = 4; + } else { + const auto flowchart_name = ore::StringView(*flowchart->name.Get()); + const auto node_flowchart_name = + ore::StringView(*m_nodes[i].m_obj->GetFlowchart()->name.Get()); + if (node_flowchart_name == flowchart_name) { + state = 1; + } else { + state = 0; + } + } + + if (((state | 4) & 7) != 4) + break; + } + return state != 2; +} + +const ore::Array* +FlowchartContext::GetUsedResActors(ore::StringView flowchart_name) const { + auto* obj = FindFlowchartObj(flowchart_name); + if (!obj) + return nullptr; + return obj->GetActBinder().GetUsedResActors(); +} + +/// Recursively checks subflow calls in the specified entry point for missing flowcharts +/// or entry points. +/// @param result Optional. +/// @param visited Visited entry points (one BitArray per flowchart) +/// @param flowchart_idx Index of the flowchart to which the entry point belongs. +/// @param entry_point_idx Index of the entry point to be checked. +/// @returns true on success, false on failure +bool CheckSubFlowCalls(FlowchartContext::Builder::BuildResult* result, + const ore::IterRange& flowcharts, + ore::Array& visited, int flowchart_idx, int entry_point_idx) { + if (visited[flowchart_idx].Test(entry_point_idx)) + return true; + visited[flowchart_idx].Set(entry_point_idx); + + const auto* flowchart = *std::next(flowcharts.begin(), flowchart_idx); + const auto entry_point_name = + flowchart->entry_point_names.Get()->GetEntries()[1 + entry_point_idx].GetKey(); + const auto* entry_point = flowchart->GetEntryPoint(entry_point_name); + + for (u16 i = 0; i != entry_point->num_sub_flow_event_indices; ++i) { + const auto& event = flowchart->events.Get()[entry_point->sub_flow_event_indices.Get()[i]]; + ore::StringView sub_flow_flowchart = *event.sub_flow_flowchart.Get(); + const ore::StringView sub_flow_entry_point = *event.sub_flow_entry_point.Get(); + + auto sub_flowchart_idx = flowchart_idx; + auto* sub_flowchart_res = flowchart; + + if (!sub_flow_flowchart.empty()) { + const auto it = + std::find_if(flowcharts.begin(), flowcharts.end(), [=](const ResFlowchart* f) { + return sub_flow_flowchart == *f->name.Get(); + }); + + if (it == flowcharts.end()) { + if (result) { + result->result = + FlowchartContext::Builder::BuildResultType::kResFlowchartNotFound; + result->missing_flowchart_name = sub_flow_flowchart; + result->missing_entry_point_name = {}; + } + return false; + } + + sub_flowchart_idx = std::distance(flowcharts.begin(), it); + sub_flowchart_res = *it; + + } else { + sub_flow_flowchart = *flowchart->name.Get(); + } + + const int sub_entry_point_idx = + sub_flowchart_res->entry_point_names.Get()->FindIndex(sub_flow_entry_point); + + if (sub_entry_point_idx == -1) { + if (result) { + result->result = FlowchartContext::Builder::BuildResultType::kEntryPointNotFound; + result->missing_flowchart_name = sub_flow_flowchart; + result->missing_entry_point_name = sub_flow_entry_point; + } + return false; + } + + if (!CheckSubFlowCalls(result, flowcharts, visited, sub_flowchart_idx, sub_entry_point_idx)) + return false; + } + + if (result) { + result->result = FlowchartContext::Builder::BuildResultType::kSuccess; + result->missing_flowchart_name = {}; + result->missing_entry_point_name = {}; + } + return true; +} + +bool FlowchartContext::Builder::SetEntryPoint(const ore::StringView& flowchart_name, + const ore::StringView& entry_point_name) { + return SetEntryPoint(nullptr, flowchart_name, entry_point_name); +} + +bool FlowchartContext::Builder::SetEntryPoint(BuildResult* result, + const ore::StringView& flowchart_name, + const ore::StringView& entry_point_name) { + const auto* flowchart_it = + std::find_if(m_flowcharts.begin(), m_flowcharts.end(), [=](const ResFlowchart* flowchart) { + return flowchart_name == *flowchart->name.Get(); + }); + + if (flowchart_it == m_flowcharts.end()) { + if (result) { + result->result = BuildResultType::kResFlowchartNotFound; + result->missing_flowchart_name = flowchart_name; + result->missing_entry_point_name = {}; + } + return false; + } + + const auto entry_point_idx = + (*flowchart_it)->entry_point_names.Get()->FindIndex(entry_point_name); + + if (entry_point_idx == -1) { + if (result) { + result->result = BuildResultType::kEntryPointNotFound; + result->missing_flowchart_name = flowchart_name; + result->missing_entry_point_name = entry_point_name; + } + return false; + } + + m_flowchart_idx = std::distance(m_flowcharts.begin(), flowchart_it); + m_entry_point_idx = entry_point_idx; + if (result) { + result->result = BuildResultType::kSuccess; + result->missing_flowchart_name = {}; + result->missing_entry_point_name = {}; + } + return true; +} + +bool FlowchartContext::Builder::BuildImpl(BuildResult* result, FlowchartRange flowcharts, + FlowchartContext* context, AllocateArg allocate_arg, + ore::Buffer flowchart_obj_buffer) { + context->m_nodes.Reset(); + EvflAllocator allocator{allocate_arg}; + context->m_allocator = allocator; + + const int num_flowcharts = flowcharts.size(); + + ore::Array visited_entry_points; + visited_entry_points.SetBuffer(num_flowcharts, &allocator); + visited_entry_points.UninitializedDefaultConstructElements(); + + const auto clean_up_visited_entry_points = [&] { + if (auto* data = visited_entry_points.data()) { + for (auto it = data; it != data + visited_entry_points.size(); ++it) + it->FreeBufferIfNeeded(&allocator); + + visited_entry_points.DestructElements(); + allocator.Free(data); + } + }; + + for (int i = 0; i < num_flowcharts; ++i) { + visited_entry_points[i].AllocateBuffer(&allocator, + (flowcharts.begin()[i])->num_entry_points); + } + + if (!CheckSubFlowCalls(result, flowcharts, visited_entry_points, m_flowchart_idx, + m_entry_point_idx)) { + clean_up_visited_entry_points(); + return false; + } + + context->m_objs.ConstructElements(flowchart_obj_buffer); + + for (int i = 0; i < num_flowcharts; ++i) { + auto* obj = &context->m_objs[i]; + FlowchartObj::Builder obj_builder{flowcharts.begin()[i], &visited_entry_points[i]}; + + if (!obj_builder.Build(obj, &context->m_allocator, flowcharts)) { + clean_up_visited_entry_points(); + context->m_objs.ClearWithoutFreeing(); + + if (result) { + const auto* flowchart = flowcharts.begin()[m_flowchart_idx]; + const ore::StringView name = *flowchart->name.Get(); + const ore::StringView ep_name = flowchart->GetEntryPointName(m_entry_point_idx); + result->result = BuildResultType::kInvalidOperation; + result->missing_flowchart_name = name; + result->missing_entry_point_name = ep_name; + } + return false; + } + } + + context->m_obj_idx = m_flowchart_idx; + context->m_active_entry_point_idx = m_entry_point_idx; + context->m_nodes.Init(&context->m_allocator, 16); + context->m_nodes.Resize(16); + context->Clear(); + clean_up_visited_entry_points(); + + if (result) { + result->result = BuildResultType::kSuccess; + result->missing_flowchart_name = {}; + result->missing_entry_point_name = {}; + } + return true; +} + +bool FlowchartContext::Builder::Build(FlowchartContext* context, AllocateArg allocate_arg) { + return Build(nullptr, context, allocate_arg); +} + +bool FlowchartContext::Builder::Build(BuildResult* result, FlowchartContext* context, + AllocateArg allocate_arg) { + context->Dispose(); + + EvflAllocator allocator{allocate_arg}; + + ore::DynArrayList flowcharts{&allocator}; + flowcharts.Init(&allocator); + flowcharts.DeduplicateCopy(m_flowcharts); + + FlowchartRange range{flowcharts}; + ore::Buffer obj_buffer{}; + obj_buffer.Allocate(&allocator, flowcharts.size()); + + if (!BuildImpl(result, range, context, allocate_arg, obj_buffer)) { + obj_buffer.Free(&allocator); + return false; + } + + return true; +} + +} // namespace evfl diff --git a/lib/EventFlow/src/evfl/FlowchartObj.cpp b/lib/EventFlow/src/evfl/FlowchartObj.cpp new file mode 100644 index 00000000..b0306b59 --- /dev/null +++ b/lib/EventFlow/src/evfl/FlowchartObj.cpp @@ -0,0 +1,243 @@ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +namespace evfl { + +namespace { + +void RegisterBindings(FlowchartObj* obj, ore::BitArray* visited_events, int event_idx) { + const ResActor* actors = obj->GetFlowchart()->actors.Get(); + const ResEvent* events = obj->GetFlowchart()->events.Get(); + + while (event_idx != 0xffff && !visited_events->Test(event_idx)) { + visited_events->Set(event_idx); + const ResEvent& event = events[event_idx]; + const auto event_type = event.type; + + switch (event_type.mValue) { + case ResEvent::EventType::kAction: + if (actors[event.actor_idx].argument_name.Get()->empty()) { + auto* action = actors[event.actor_idx].actions.Get() + event.actor_action_idx; + obj->GetActBinder().RegisterAction(event.actor_idx, action); + } + break; + case ResEvent::EventType::kSwitch: + if (actors[event.actor_idx].argument_name.Get()->empty()) { + auto* query = actors[event.actor_idx].queries.Get() + event.actor_query_idx; + obj->GetActBinder().RegisterQuery(event.actor_idx, query); + } + break; + default: + break; + } + + // Process the next event. + + switch (event_type) { + case ResEvent::EventType::kAction: + case ResEvent::EventType::kJoin: + case ResEvent::EventType::kSubFlow: + event_idx = event.next_event_idx; + break; + case ResEvent::EventType::kSwitch: { + ore::Array cases{event.cases.Get(), event.num_cases}; + std::for_each(cases.begin(), cases.end(), [&](const ResCase& case_) { + RegisterBindings(obj, visited_events, case_.event_idx); + }); + return; + } + case ResEvent::EventType::kFork: { + ore::Array forks{event.fork_event_indices.Get(), event.num_forks}; + std::for_each(forks.begin(), forks.end(), + [&](u16 fork) { RegisterBindings(obj, visited_events, fork); }); + event_idx = event.join_event_idx; + break; + } + } + } +} + +struct ActorArgumentInfo { + bool operator==(const ActorArgumentInfo& rhs) const { + return entry_point_idx == rhs.entry_point_idx && flowchart == rhs.flowchart && + rhs.GetActorArgumentName() == GetActorArgumentName(); + } + bool operator!=(const ActorArgumentInfo& rhs) const { return !(*this == rhs); } + + ore::StringView GetActorArgumentName() const { + return ore::StringView(actor_argument_name, actor_argument_name_len); + } + + const ResFlowchart* flowchart; + int entry_point_idx; + const char* actor_argument_name; + size_t actor_argument_name_len; +}; + +// NON_MATCHING: the if checks are reordered to hell for some reason +const ResActor* FindActor(const ActorArgumentInfo& entry) { + ore::Array actors{entry.flowchart->actors.Get(), entry.flowchart->num_actors}; + for (const auto& actor : actors) { + if (actor.entry_point_idx != entry.entry_point_idx) + continue; + if (actor.argument_name.Get()->empty()) + continue; + if (*actor.argument_name.Get() != entry.GetActorArgumentName()) + continue; + return &actor; + } + return nullptr; +} + +void RegisterBindingsForArguments(ActBinder& binder, int actor_idx, + const ore::IterRange& flowcharts, + ore::ArrayListBase& processed, + const ActorArgumentInfo& entry) { + if (std::find(processed.begin(), processed.end(), entry) != processed.end()) + return; + + processed.emplace_back(entry); + + if (auto* actor = FindActor(entry)) { + ore::Array actions{actor->actions.Get(), actor->num_actions}; + for (const auto& action : actions) + binder.RegisterAction(actor_idx, &action); + + ore::Array queries{actor->queries.Get(), actor->num_queries}; + for (const auto& query : queries) + binder.RegisterQuery(actor_idx, &query); + } + + const auto& entry_point = entry.flowchart->entry_points.Get()[entry.entry_point_idx]; + ore::Array sub_flow_event_indices{entry_point.sub_flow_event_indices.Get(), + entry_point.num_sub_flow_event_indices}; + for (auto sub_flow_event_idx : sub_flow_event_indices) { + const auto& event = entry.flowchart->events.Get()[sub_flow_event_idx]; + const ore::StringView sub_flow_flowchart = *event.sub_flow_flowchart.Get(); + const ore::StringView sub_flow_entry_point = *event.sub_flow_entry_point.Get(); + + auto* params = event.params.Get(); + if (!params) + continue; + + for (int i = 0; i < params->num_items; ++i) { + auto* param = (¶ms->value.container + i)->Get(); + if (param->type != ore::ResMetaData::DataType::kArgument) + continue; + if (entry.GetActorArgumentName() != *param->value.str.Get()) + continue; + + const ResFlowchart* flowchart = entry.flowchart; + if (!sub_flow_flowchart.empty()) { + flowchart = + *std::find_if(flowcharts.begin(), flowcharts.end(), [=](const ResFlowchart* f) { + return sub_flow_flowchart == *f->name.Get(); + }); + } + + const auto entry_point_idx = + flowchart->entry_point_names.Get()->FindIndex(sub_flow_entry_point); + const auto actor_argument_name = params->dictionary.Get()->GetEntries()[1 + i].GetKey(); + + ActorArgumentInfo arg; + arg.flowchart = flowchart; + arg.entry_point_idx = entry_point_idx; + arg.actor_argument_name = actor_argument_name.data(); + arg.actor_argument_name_len = actor_argument_name.size(); + RegisterBindingsForArguments(binder, actor_idx, flowcharts, processed, arg); + } + } + + processed.pop_back(); +} + +void RegisterBindingsForActorIdentifiers(FlowchartObj* obj, + ore::IterRange flowcharts, + int entry_point_idx) { + auto* flowchart = obj->GetFlowchart(); + const auto& entry_point = flowchart->entry_points.Get()[entry_point_idx]; + + ore::IterRange sub_flow_event_indices{entry_point.sub_flow_event_indices.Get(), + entry_point.num_sub_flow_event_indices}; + const ResEvent* events = flowchart->events.Get(); + ore::IterRange actors{flowchart->actors.Get(), flowchart->num_actors}; + + for (auto sub_flow_event_idx : sub_flow_event_indices) { + const auto& event = events[sub_flow_event_idx]; + + auto* params = event.params.Get(); + if (!params) + continue; + + const ore::StringView sub_flow_flowchart = *event.sub_flow_flowchart.Get(); + const ore::StringView sub_flow_entry_point = *event.sub_flow_entry_point.Get(); + const ResFlowchart* arg_flowchart = flowchart; + if (!sub_flow_flowchart.empty()) { + arg_flowchart = + *std::find_if(flowcharts.begin(), flowcharts.end(), [=](const ResFlowchart* f) { + return sub_flow_flowchart == *f->name.Get(); + }); + } + + for (int i = 0; i < params->num_items; ++i) { + auto* param = (¶ms->value.container + i)->Get(); + if (param->type != ore::ResMetaData::DataType::kActorIdentifier) + continue; + + const ore::StringView param_name = + params->dictionary.Get()->GetEntries()[1 + i].GetKey(); + const ore::StringView name = *param->value.actor.name.Get(); + const ore::StringView sub_name = *param->value.actor.sub_name.Get(); + auto* actor = std::find_if(actors.begin(), actors.end(), [&](const ResActor& a) { + return name == *a.name.Get() && sub_name == *a.secondary_name.Get(); + }); + const int actor_idx = std::distance(actors.begin(), actor); + const int arg_entry_point_idx = + arg_flowchart->entry_point_names.Get()->FindIndex(sub_flow_entry_point); + + ore::FixedArrayList processed; + ActorArgumentInfo arg; + arg.flowchart = arg_flowchart; + arg.entry_point_idx = arg_entry_point_idx; + arg.actor_argument_name = param_name.data(); + arg.actor_argument_name_len = param_name.size(); + RegisterBindingsForArguments(obj->GetActBinder(), actor_idx, flowcharts, processed, + arg); + } + } +} + +} // namespace + +bool FlowchartObj::Builder::Build(FlowchartObj* obj, ore::Allocator* allocator, + ore::IterRange flowcharts) { + obj->m_flowchart = m_flowchart; + m_act_binder_builder.Build(&obj->GetActBinder(), allocator, + {m_flowchart->actors.Get(), m_flowchart->num_actors}); + + const int num_events = m_flowchart->num_events; + ore::BitArray visited_events{allocator, num_events}; + + auto* entry_points = obj->m_flowchart->entry_points.Get(); + auto entry_point_it = m_entry_points_mask->BeginTest(); + const auto entry_point_end = m_entry_points_mask->EndTest(); + while (entry_point_it != entry_point_end) { + RegisterBindings(obj, &visited_events, entry_points[*entry_point_it].main_event_idx); + RegisterBindingsForActorIdentifiers(obj, flowcharts, *entry_point_it); + obj->GetActBinder().SetIsUsed(); + ++entry_point_it; + } + + visited_events.FreeBuffer(allocator); + return true; +} + +} // namespace evfl diff --git a/lib/EventFlow/src/evfl/Param.cpp b/lib/EventFlow/src/evfl/Param.cpp new file mode 100644 index 00000000..596ca7ee --- /dev/null +++ b/lib/EventFlow/src/evfl/Param.cpp @@ -0,0 +1,714 @@ +#include +#include +#include +#include +#include +#include + +namespace evfl { + +namespace { + +constexpr ore::ResMetaData::DataType::Type +ConvertMetaDataPackTypeToMDType(MetaDataPack::DataType::Type type) { + if (u32(type) < u32(MetaDataPack::DataType::Invalid())) + return ore::ResMetaData::DataType::Type(ore::ResMetaData::DataType::kInt + type); + +#ifdef MATCHING_HACK_NX_CLANG + // Force a branch to be generated (instead of CSEL) + __builtin_assume(type >= 0); +#endif + return ore::ResMetaData::DataType::Invalid(); +} + +} // namespace + +void MetaDataPack::AddInt(const char* key, int value) { + auto& entry = AddEntry(); + entry.key = key; + entry.value.i = value; + entry.type = DataType::kInt; +} + +// NON_MATCHING: ??? +void MetaDataPack::AddBool(const char* key, bool value) { + auto& entry = AddEntry(); + entry.key = key; + entry.value.i = value; + entry.type = DataType::kBool; +} + +void MetaDataPack::AddFloat(const char* key, float value) { + auto& entry = AddEntry(); + entry.key = key; + entry.value.f = value; + entry.type = DataType::kFloat; +} + +void MetaDataPack::AddStringPtr(const char* key, const char* value) { + auto& entry = AddEntry(); + entry.key = key; + entry.value.str = value; + entry.type = DataType::kString; +} + +void MetaDataPack::AddWStringPtr(const char* key, const wchar_t* value) { + auto& entry = AddEntry(); + entry.key = key; + entry.value.wstr = value; + entry.type = DataType::kWString; +} + +MetaDataPack::Entry* MetaDataPack::Find(const ore::StringView& key) const { + for (auto& entry : GetEntries()) { + if (entry.IsKey(key)) + return &entry; + } + return nullptr; +} + +bool MetaDataPack::FindInt(int* value, const ore::StringView& key) const { + auto* entry = Find(key); + if (!entry || entry->type != DataType::kInt) + return false; + *value = entry->value.i; + return true; +} + +bool MetaDataPack::FindBool(bool* value, const ore::StringView& key) const { + auto* entry = Find(key); + if (!entry || entry->type != DataType::kBool) + return false; + *value = entry->value.i == 1; + return true; +} + +bool MetaDataPack::FindFloat(float* value, const ore::StringView& key) const { + auto* entry = Find(key); + if (!entry || entry->type != DataType::kFloat) + return false; + *value = entry->value.f; + return true; +} + +bool MetaDataPack::FindString(ore::StringView* value, const ore::StringView& key) const { + auto* entry = Find(key); + if (!entry || entry->type != DataType::kString) + return false; + *value = entry->value.str; + return true; +} + +bool MetaDataPack::FindWString(ore::WStringView* value, const ore::StringView& key) const { + auto* entry = Find(key); + if (!entry || entry->type != DataType::kWString) + return false; + *value = entry->value.wstr; + return true; +} + +ore::ResMetaData::DataType::Type MetaDataPack::GetType(const ore::StringView& key) const { + auto* entry = Find(key); + return ConvertMetaDataPackTypeToMDType(entry ? entry->type : DataType::Invalid()); +} + +// NON_MATCHING: two add operands swapped +void MetaDataPack::Builder::CalcMemSize() { + m_entries_byte_size = sizeof(Entry) * m_num_entries; + m_required_size = 0; + m_alignment_real = 16; + if (m_num_entries != 0) { + m_alignment_real = std::max(16, m_alignment); + m_buffer_offset = ore::AlignUpToPowerOf2(_14, m_alignment) - _14; + m_required_size = m_buffer_offset + m_entries_byte_size; + } +} + +bool MetaDataPack::Builder::Build(MetaDataPack* pack, ore::Buffer buffer) { + if (m_alignment_real <= 0) + return false; + if (m_required_size > buffer.size) + return false; + pack->m_buffer.data = buffer.data; + pack->m_buffer.size = buffer.size; + const int byte_size = m_entries_byte_size; + pack->m_entries = reinterpret_cast(buffer.data + m_buffer_offset); + pack->m_entries_capacity = byte_size / int(sizeof(Entry)); + pack->m_entries_num = 0; + return true; +} + +ParamAccessor::ParamAccessor(const ore::ResMetaData* metadata) : m_metadata(metadata) {} + +ParamAccessor::ParamAccessor(const FlowchartContext* context, int node_idx) + : m_context(context), m_node_idx(node_idx) { + m_node_counter = context->GetNode(node_idx).GetNodeCounter(); +} + +const ore::ResMetaData* ParamAccessor::GetFrontResMetaData() const { + if (m_node_idx == -1) + return m_metadata; + + const auto& node = m_context->GetNode(m_node_idx); + const auto& event = node.GetObj()->GetFlowchart()->events.Get()[node.GetEventIdx()]; + return event.params.Get(); +} + +int ParamAccessor::GetParamCount() const { + auto* meta = GetFrontResMetaData(); + return meta ? meta->num_items : 0; +} + +ore::StringView ParamAccessor::GetParamName(int idx) const { + auto* meta = GetFrontResMetaData(); + return meta->dictionary.Get()->GetEntries()[1 + idx].GetKey(); +} + +ParamAccessor::Type ParamAccessor::GetParamType(int idx) const { + Type type = ore::ResMetaData::DataType::Invalid(); + + const ore::ResMetaData* metadata; + const MetaDataPack* metadata_pack; + const VariablePack* variable_pack; + const auto param_name = GetParamName(idx); + const auto real_name = + TrackBackArgument(&metadata, &metadata_pack, &variable_pack, nullptr, param_name); + + if (metadata) { + const int entry_idx = metadata->dictionary.Get()->FindIndex(real_name); + if (entry_idx == -1) + return ore::ResMetaData::DataType::Invalid(); + type = (&metadata->value.container + entry_idx)->Get()->type; + } else if (variable_pack) { + type = variable_pack->GetVariableType(real_name); + } else if (metadata_pack) { + type = metadata_pack->GetType(real_name); + } + + if (type == ore::ResMetaData::DataType::Invalid()) + return ore::ResMetaData::DataType::Invalid(); + + return type; +} + +ore::StringView ParamAccessor::TrackBackArgument(const ore::ResMetaData** out_metadata, + const MetaDataPack** out_metadata_pack, + const VariablePack** out_variable_pack, + FlowchartObj** out_obj, + const ore::StringView& argument) const { + *out_metadata = nullptr; + *out_metadata_pack = nullptr; + *out_variable_pack = nullptr; + if (out_obj) + *out_obj = nullptr; + + if (m_node_idx == -1) { + *out_metadata = m_metadata; + return argument; + } + + auto ret = argument; + + for (int i = m_node_idx; i != 0xffff; i = m_context->GetNode(i).GetNextNodeIdx()) { + const auto& node = m_context->GetNode(i); + const auto* variable_pack = node.GetVariablePack(); + const auto* events = node.GetObj()->GetFlowchart()->events.Get(); + const auto& event = events[node.GetEventIdx()]; + + if (!((event.type == ResEvent::EventType::kAction && i == m_node_idx) || + (event.type == ResEvent::EventType::kSwitch && i == m_node_idx) || + event.type == ResEvent::EventType::kSubFlow)) { + continue; + } + + const auto* params = event.params.Get(); + if (!params) + return {}; + + const auto* param = params->Get(ret, Type::kArgument); + if (param) { + ret = *param->value.str.Get(); + if (variable_pack && variable_pack->Contains(ret)) { + *out_variable_pack = variable_pack; + return ret; + } + continue; + } + + *out_metadata = params; + if (out_obj) + *out_obj = node.GetObj(); + return ret; + } + + *out_metadata_pack = m_context->GetMetaDataPack(); + if (*out_metadata_pack == nullptr) + return {}; + return ret; +} + +int ParamAccessor::GetInt(int idx) const { + int value; + FindInt(&value, GetParamName(idx)); + return value; +} + +bool ParamAccessor::FindInt(int* value, const ore::StringView& name) const { + const ore::ResMetaData* metadata; + const MetaDataPack* metadata_pack; + const VariablePack* variable_pack; + const auto real_name = + TrackBackArgument(&metadata, &metadata_pack, &variable_pack, nullptr, name); + + if (metadata) { + const auto* entry = metadata->Get(real_name, Type::kInt); + if (entry != nullptr) { + *value = entry->value.i; + return true; + } + } + + if (variable_pack && variable_pack->FindInt(value, real_name)) + return true; + + if (metadata_pack && metadata_pack->FindInt(value, real_name)) + return true; + + return false; +} + +bool ParamAccessor::GetBool(int idx) const { + bool value; + FindBool(&value, GetParamName(idx)); + return value; +} + +bool ParamAccessor::FindBool(bool* value, const ore::StringView& name) const { + const ore::ResMetaData* metadata; + const MetaDataPack* metadata_pack; + const VariablePack* variable_pack; + const auto real_name = + TrackBackArgument(&metadata, &metadata_pack, &variable_pack, nullptr, name); + + if (metadata) { + const auto* entry = metadata->Get(real_name, Type::kBool); + if (entry != nullptr) { + *value = entry->value.i != 0; + return true; + } + } + + if (variable_pack && variable_pack->FindBool(value, real_name)) + return true; + + if (metadata_pack && metadata_pack->FindBool(value, real_name)) + return true; + + return false; +} + +float ParamAccessor::GetFloat(int idx) const { + float value; + FindFloat(&value, GetParamName(idx)); + return value; +} + +bool ParamAccessor::FindFloat(float* value, const ore::StringView& name) const { + const ore::ResMetaData* metadata; + const MetaDataPack* metadata_pack; + const VariablePack* variable_pack; + const auto real_name = + TrackBackArgument(&metadata, &metadata_pack, &variable_pack, nullptr, name); + + if (metadata) { + const auto* entry = metadata->Get(real_name, Type::kFloat); + if (entry != nullptr) { + *value = entry->value.f; + return true; + } + } + + if (variable_pack && variable_pack->FindFloat(value, real_name)) + return true; + + if (metadata_pack && metadata_pack->FindFloat(value, real_name)) + return true; + + return false; +} + +ore::StringView ParamAccessor::GetString(int idx) const { + ore::StringView value; + FindString(&value, GetParamName(idx)); + return value; +} + +bool ParamAccessor::FindString(ore::StringView* value, const ore::StringView& name) const { + const ore::ResMetaData* metadata; + const MetaDataPack* metadata_pack; + const VariablePack* variable_pack; + const auto real_name = + TrackBackArgument(&metadata, &metadata_pack, &variable_pack, nullptr, name); + + if (metadata) { + const auto* entry = metadata->Get(real_name, Type::kString); + if (entry) { + *value = *entry->value.str.Get(); + return true; + } + return false; + } + + if (metadata_pack) + return metadata_pack->FindString(value, real_name); + + return false; +} + +ore::WStringView ParamAccessor::GetWString(int idx) const { + ore::WStringView value; + FindWString(&value, GetParamName(idx)); + return value; +} + +bool ParamAccessor::FindWString(ore::WStringView* value, const ore::StringView& name) const { + const ore::ResMetaData* metadata; + const MetaDataPack* metadata_pack; + const VariablePack* variable_pack; + const auto real_name = + TrackBackArgument(&metadata, &metadata_pack, &variable_pack, nullptr, name); + + if (metadata) { + const auto* entry = metadata->Get(real_name, Type::kWString); + if (entry) { + *value = *entry->value.wstr.Get(); + return true; + } + return false; + } + + if (metadata_pack) + return metadata_pack->FindWString(value, real_name); + + return false; +} + +ParamAccessor::IntRange ParamAccessor::GetIntArray(int idx) const { + IntRange value; + FindIntArray(&value, GetParamName(idx)); + return value; +} + +bool ParamAccessor::FindIntArray(ParamAccessor::IntRange* value, + const ore::StringView& name) const { + const ore::ResMetaData* metadata; + const MetaDataPack* metadata_pack; + const VariablePack* variable_pack; + const auto real_name = + TrackBackArgument(&metadata, &metadata_pack, &variable_pack, nullptr, name); + + if (metadata) { + const auto* entry = metadata->Get(real_name, Type::kIntArray); + if (entry) { + *value = IntRange{&entry->value.i, entry->num_items}; + return true; + } + } + + if (variable_pack) { + ore::DynArrayList* list; + if (variable_pack->FindIntList(&list, real_name)) { + *value = IntRange{*list}; + return true; + } + } + + return false; +} + +ParamAccessor::FloatRange ParamAccessor::GetFloatArray(int idx) const { + FloatRange value; + FindFloatArray(&value, GetParamName(idx)); + return value; +} + +bool ParamAccessor::FindFloatArray(ParamAccessor::FloatRange* value, + const ore::StringView& name) const { + const ore::ResMetaData* metadata; + const MetaDataPack* metadata_pack; + const VariablePack* variable_pack; + const auto real_name = + TrackBackArgument(&metadata, &metadata_pack, &variable_pack, nullptr, name); + + if (metadata) { + const auto* entry = metadata->Get(real_name, Type::kFloatArray); + if (entry) { + *value = FloatRange{&entry->value.f, entry->num_items}; + return true; + } + } + + if (variable_pack) { + ore::DynArrayList* list; + if (variable_pack->FindFloatList(&list, real_name)) { + *value = FloatRange{*list}; + return true; + } + } + + return false; +} + +ParamAccessor::StringRange ParamAccessor::GetStringArray(int idx) const { + StringRange value; + FindStringArray(&value, GetParamName(idx)); + return value; +} + +bool ParamAccessor::FindStringArray(ParamAccessor::StringRange* value, + const ore::StringView& name) const { + const ore::ResMetaData* metadata; + const MetaDataPack* metadata_pack; + const VariablePack* variable_pack; + const auto real_name = + TrackBackArgument(&metadata, &metadata_pack, &variable_pack, nullptr, name); + + if (metadata) { + const auto* entry = metadata->Get(real_name, Type::kStringArray); + if (entry) { + *value = StringRange{&entry->value.str, entry->num_items}; + return true; + } + } + + return false; +} + +ParamAccessor::WStringRange ParamAccessor::GetWStringArray(int idx) const { + WStringRange value; + FindWStringArray(&value, GetParamName(idx)); + return value; +} + +bool ParamAccessor::FindWStringArray(ParamAccessor::WStringRange* value, + const ore::StringView& name) const { + const ore::ResMetaData* metadata; + const MetaDataPack* metadata_pack; + const VariablePack* variable_pack; + const auto real_name = + TrackBackArgument(&metadata, &metadata_pack, &variable_pack, nullptr, name); + + if (metadata) { + const auto* entry = metadata->Get(real_name, Type::kWStringArray); + if (entry) { + *value = WStringRange{&entry->value.wstr, entry->num_items}; + return true; + } + } + + return false; +} + +VariablePack::VariableType VariablePack::GetVariableType(const ore::StringView& name) const { + if (!Contains(name)) + return ore::ResMetaData::DataType::Invalid(); + return GetVariableEntry(name)->type; +} + +bool VariablePack::FindInt(int* value, const ore::StringView& name) const { + if (GetVariableType(name) != ore::ResMetaData::DataType::kInt) + return false; + *value = GetVariableEntry(name)->value.i; + return true; +} + +bool VariablePack::FindBool(bool* value, const ore::StringView& name) const { + if (GetVariableType(name) != ore::ResMetaData::DataType::kBool) + return false; + *value = GetVariableEntry(name)->value.i; + return true; +} + +bool VariablePack::FindFloat(float* value, const ore::StringView& name) const { + if (GetVariableType(name) != ore::ResMetaData::DataType::kFloat) + return false; + *value = GetVariableEntry(name)->value.f; + return true; +} + +bool VariablePack::FindIntList(ore::DynArrayList** value, const ore::StringView& name) const { + if (GetVariableType(name) != ore::ResMetaData::DataType::kIntArray) + return false; + *value = GetVariableEntry(name)->value.int_array; + return true; +} + +bool VariablePack::FindFloatList(ore::DynArrayList** value, + const ore::StringView& name) const { + if (GetVariableType(name) != ore::ResMetaData::DataType::kFloatArray) + return false; + *value = GetVariableEntry(name)->value.float_array; + return true; +} + +bool ParamAccessor::FindActorIdentifier(ore::StringView* actor_name, + ore::StringView* actor_sub_name, + const ore::StringView& name) const { + const ore::ResMetaData* metadata; + const MetaDataPack* metadata_pack; + const VariablePack* variable_pack; + const auto real_name = + TrackBackArgument(&metadata, &metadata_pack, &variable_pack, nullptr, name); + + if (metadata) { + const auto* entry = metadata->Get(real_name, Type::kActorIdentifier); + if (entry) { + *actor_name = *entry->value.actor.name.Get(); + *actor_sub_name = *entry->value.actor.sub_name.Get(); + return true; + } + } + + return false; +} + +bool VariablePack::Contains(const ore::StringView& name) const { + return m_names->FindIndex(name) != -1; +} + +VariablePack::VariablePack() = default; + +VariablePack::~VariablePack() { + Dispose(); +} + +void VariablePack::Dispose() { + auto* variables = m_variables.data(); + if (!variables) + return; + + for (auto& variable : m_variables) { + switch (variable.type) { + case ore::ResMetaData::DataType::kIntArray: + if (variable.value.int_array) + GetAllocator()->DeleteAndNull(variable.value.int_array); + break; + case ore::ResMetaData::DataType::kFloatArray: + if (variable.value.float_array) + GetAllocator()->DeleteAndNull(variable.value.float_array); + break; + default: + break; + } + } + GetAllocator()->FreeImpl(variables); +} + +void VariablePack::Init(AllocateArg arg, const ResEntryPoint* entry_point) { + Dispose(); + m_names = entry_point->variable_defs_names.Get(); + m_allocator = evfl::EvflAllocator{arg}; + m_variables.ConstructElements(m_names->num_entries, GetAllocator()); + + const ResVariableDef* def = entry_point->variable_defs.Get(); + for (auto& variable : m_variables) { + variable.type = def->type; + variable.value = {}; + switch (variable.type) { + case ore::ResMetaData::DataType::kArgument: + case ore::ResMetaData::DataType::kContainer: + break; + case ore::ResMetaData::DataType::kInt: + case ore::ResMetaData::DataType::kBool: + variable.value.i = def->value.i; + break; + case ore::ResMetaData::DataType::kFloat: + variable.value.f = def->value.f; + break; + case ore::ResMetaData::DataType::kString: + case ore::ResMetaData::DataType::kWString: + break; + case ore::ResMetaData::DataType::kIntArray: { + variable.value.int_array = GetAllocator()->New>(); + variable.value.int_array->Init(GetAllocator(), 2); + ore::Array values{def->value.int_array.Get(), def->num}; + variable.value.int_array->OverwriteWith(values.begin(), values.end()); + break; + } + case ore::ResMetaData::DataType::kBoolArray: + break; + case ore::ResMetaData::DataType::kFloatArray: { + variable.value.float_array = GetAllocator()->New>(); + variable.value.float_array->Init(GetAllocator(), 2); + ore::Array values{def->value.float_array.Get(), def->num}; + variable.value.float_array->OverwriteWith(values.begin(), values.end()); + break; + } + case ore::ResMetaData::DataType::kStringArray: + case ore::ResMetaData::DataType::kWStringArray: + case ore::ResMetaData::DataType::kActorIdentifier: + break; + } + ++def; + } +} + +const VariablePack::Entry* VariablePack::GetVariableEntry(const ore::StringView& name) const { + return &m_variables[m_names->FindIndex(name)]; +} + +ore::StringView VariablePack::GetVariableName(int idx) const { + return *m_names->GetEntries()[1 + idx].name.Get(); +} + +int VariablePack::GetVariableCount() const { + return m_names->num_entries; +} + +VariablePack::Entry* VariablePack::GetVariableEntry(const ore::StringView& name) { + return &m_variables[m_names->FindIndex(name)]; +} + +void VariablePack::SetInt(const ore::StringView& name, int value) { + m_variables[m_names->FindIndex(name)].value.i = value; +} + +void VariablePack::SetFloat(const ore::StringView& name, float value) { + m_variables[m_names->FindIndex(name)].value.f = value; +} + +void VariablePack::SetBool(const ore::StringView& name, bool value) { + m_variables[m_names->FindIndex(name)].value.i = value; +} + +int VariablePack::GetInt(const ore::StringView& name) const { + int value; + FindInt(&value, name); + return value; +} + +bool VariablePack::GetBool(const ore::StringView& name) const { + bool value; + FindBool(&value, name); + return value; +} + +float VariablePack::GetFloat(const ore::StringView& name) const { + float value; + FindFloat(&value, name); + return value; +} + +ore::DynArrayList* VariablePack::GetIntList(const ore::StringView& name) const { + ore::DynArrayList* value; + FindIntList(&value, name); + return value; +} + +ore::DynArrayList* VariablePack::GetFloatList(const ore::StringView& name) const { + ore::DynArrayList* value; + FindFloatList(&value, name); + return value; +} + +} // namespace evfl diff --git a/lib/EventFlow/src/evfl/ResActor.cpp b/lib/EventFlow/src/evfl/ResActor.cpp new file mode 100644 index 00000000..053ec21e --- /dev/null +++ b/lib/EventFlow/src/evfl/ResActor.cpp @@ -0,0 +1,89 @@ +#include +#include +#include +#include + +namespace evfl { + +void ActorBinding::Register(const ResAction* action) { + if (GetAction(*action->name.Get()) != m_actions.end()) + return; + + Action entry; + entry.res_action = action; + m_actions.emplace_back(entry); +} + +void ActorBinding::Register(const ResQuery* query) { + if (GetQuery(*query->name.Get()) != m_queries.end()) + return; + + Query entry; + entry.res_query = query; + m_queries.emplace_back(entry); +} + +ActorBinding::Action* ActorBinding::GetAction(const ore::StringView& name) { + return std::find_if(m_actions.begin(), m_actions.end(), [name](const Action& action) { + return name == *action.res_action->name.Get(); + }); +} + +const ActorBinding::Action* ActorBinding::GetAction(const ore::StringView& name) const { + return std::find_if(m_actions.begin(), m_actions.end(), [name](const Action& action) { + return name == *action.res_action->name.Get(); + }); +} + +ActorBinding::Query* ActorBinding::GetQuery(const ore::StringView& name) { + return std::find_if(m_queries.begin(), m_queries.end(), [name](const Query& query) { + return name == *query.res_query->name.Get(); + }); +} + +const ActorBinding::Query* ActorBinding::GetQuery(const ore::StringView& name) const { + return std::find_if(m_queries.begin(), m_queries.end(), [name](const Query& query) { + return name == *query.res_query->name.Get(); + }); +} + +bool ActBinder::Builder::Build(evfl::ActBinder* binder, ore::Allocator* allocator, + ore::IterRange actors) { + binder->m_event_used_actor_count = 0; + binder->m_allocator = allocator; + binder->m_bindings.ConstructElements(actors.size(), allocator); + + auto it = actors.begin(); + for (int i = 0; i < actors.size(); ++i) { + auto& binding = binder->m_bindings[i]; + binding.m_actor = it; + binding.m_actions.Init(binder->m_allocator); + binding.m_queries.Init(binder->m_allocator); + ++it; + } + + return true; +} + +const ore::Array* ActBinder::GetUsedResActors() const { + return &m_bindings; +} + +void SwapEndian(ore::ResEndian* endian, ResActor* actor) { + using ore::SwapEndian; + if (endian->is_serializing) { + if (auto* params = actor->params.ToPtr(endian->base)) + SwapEndian(endian, params); + SwapEndian(&actor->num_actions); + SwapEndian(&actor->num_queries); + SwapEndian(&actor->entry_point_idx); + } else { + SwapEndian(&actor->num_actions); + SwapEndian(&actor->num_queries); + SwapEndian(&actor->entry_point_idx); + if (auto* params = actor->params.ToPtr(endian->base)) + SwapEndian(endian, params); + } +} + +} // namespace evfl diff --git a/lib/EventFlow/src/evfl/ResEventFlowFile.cpp b/lib/EventFlow/src/evfl/ResEventFlowFile.cpp new file mode 100644 index 00000000..4fac653c --- /dev/null +++ b/lib/EventFlow/src/evfl/ResEventFlowFile.cpp @@ -0,0 +1,112 @@ +#include +#include +#include +#include +#include +#include +#include +#include +#include + +namespace evfl { + +using ore::SwapEndian; + +template +constexpr T MakeMagic(std::string_view magic) { + T result = 0; + for (size_t i = 0; i < magic.length(); ++i) + result |= T(magic[i]) << (8 * i); + return result; +} + +bool ResEventFlowFile::IsValid(void* data) { + return static_cast(data)->IsValid(MakeMagic("BFEVFL"), 0, 3, 0, 0); +} + +ResEventFlowFile* ResEventFlowFile::ResCast(void* data) { + auto* file = static_cast(data); + file->Relocate(); + return file; +} + +void ResEventFlowFile::Relocate() { + if (header.IsRelocated()) + return; + + auto* table = header.GetRelocationTable(); + table->Relocate(); + header.SetRelocated(true); +} + +void ResEventFlowFile::Unrelocate() { + if (!header.IsRelocated()) + return; + + auto* table = header.GetRelocationTable(); + table->Unrelocate(); + header.SetRelocated(false); +} + +static void SwapEndian(ore::ResEndian* endian, ore::StringPool* pool) { + ore::BinString* str = pool->GetFirstString(); + const int num_strings = pool->GetLength(); + if (endian->is_serializing) { + for (int i = 0; i < num_strings; ++i) { + auto* next = str->NextString(); + SwapEndian(&str->length); + str = next; + } + } else { + for (int i = 0; i < num_strings; ++i) { + SwapEndian(&str->length); + str = str->NextString(); + } + } +} + +template +static void SwapEndian(ore::ResEndian* endian, ore::BinTPtr* ptr) { + if (auto* value = ptr->ToPtr(endian->base)) + SwapEndian(endian, value); +} + +static void SwapEndianForFileData(ore::ResEndian* endian, ResEventFlowFile* file) { + ore::Array> flowcharts{file->flowcharts.ToPtr(endian->base), + file->num_flowcharts}; + for (auto& flowchart : flowcharts) + SwapEndian(endian, &flowchart); + + if (auto* flowchart_names = file->flowchart_names.ToPtr(endian->base)) + SwapEndian(endian, flowchart_names); + + ore::Array> timelines{file->timelines.ToPtr(endian->base), + file->num_timelines}; + for (auto& timeline : timelines) + SwapEndian(endian, &timeline); + + if (auto* timeline_names = file->timeline_names.ToPtr(endian->base)) + SwapEndian(endian, timeline_names); + + auto* string_pool = + static_cast(file->header.FindFirstBlock(MakeMagic("STR "))); + SwapEndian(endian, string_pool); +} + +void SwapEndian(ore::ResEndian* endian, ResEventFlowFile* file) { + const auto swap_fields = [&] { + SwapEndian(&file->header.bom); + SwapEndian(&file->num_flowcharts); + SwapEndian(&file->num_timelines); + }; + + if (endian->is_serializing) { + SwapEndianForFileData(endian, file); + swap_fields(); + } else { + swap_fields(); + SwapEndianForFileData(endian, file); + } +} + +} // namespace evfl diff --git a/lib/EventFlow/src/evfl/ResFlowchart.cpp b/lib/EventFlow/src/evfl/ResFlowchart.cpp new file mode 100644 index 00000000..da23e457 --- /dev/null +++ b/lib/EventFlow/src/evfl/ResFlowchart.cpp @@ -0,0 +1,191 @@ +#include +#include +#include +#include +#include +#include + +namespace evfl { + +using ore::SwapEndian; + +static void SwapEndianForFlowchartData(ore::ResEndian* endian, ResFlowchart* flowchart) { + ore::Array actors{flowchart->actors.ToPtr(endian->base), flowchart->num_actors}; + for (auto& actor : actors) + SwapEndian(endian, &actor); + + ore::Array events{flowchart->events.ToPtr(endian->base), flowchart->num_events}; + for (auto& event : events) + SwapEndian(endian, &event); + + if (auto* names = flowchart->entry_point_names.ToPtr(endian->base)) + SwapEndian(endian, names); + + ore::Array entry_points{flowchart->entry_points.ToPtr(endian->base), + flowchart->num_entry_points}; + for (auto& entry : entry_points) + SwapEndian(endian, &entry); +} + +static void SwapEndianForFlowchartFields(ore::ResEndian* endian, ResFlowchart* flowchart) { + SwapEndian(&flowchart->num_actors); + SwapEndian(&flowchart->num_actions); + SwapEndian(&flowchart->num_queries); + SwapEndian(&flowchart->num_events); + SwapEndian(&flowchart->num_entry_points); +} + +void SwapEndian(ore::ResEndian* endian, ResFlowchart* flowchart) { + if (endian->is_serializing) { + SwapEndianForFlowchartData(endian, flowchart); + SwapEndianForFlowchartFields(endian, flowchart); + } else { + SwapEndianForFlowchartFields(endian, flowchart); + SwapEndianForFlowchartData(endian, flowchart); + } +} + +int ResFlowchart::CountEvent(ResEvent::EventType::Type type) const { + ore::Array array{events.Get(), num_events}; + return std::count_if(array.begin(), array.end(), + [type](const ResEvent& event) { return event.type == type; }); +} + +void SwapEndian(ore::ResEndian* endian, ResCase* case_) { + SwapEndian(&case_->event_idx); + SwapEndian(&case_->value); +} + +static void SwapEndianForEventData(ore::ResEndian* endian, ResEvent* event) { + switch (event->type) { + case ResEvent::EventType::kAction: + if (auto* params = event->params.ToPtr(endian->base)) + SwapEndian(endian, params); + break; + case ResEvent::EventType::kSwitch: { + ore::Array cases{event->cases.ToPtr(endian->base), event->num_cases}; + for (auto& case_ : cases) + SwapEndian(endian, &case_); + if (auto* params = event->params.ToPtr(endian->base)) + SwapEndian(endian, params); + break; + } + case ResEvent::EventType::kFork: { + ore::Array forks{event->fork_event_indices.ToPtr(endian->base), event->num_forks}; + for (auto& fork : forks) + SwapEndian(&fork); + break; + } + case ResEvent::EventType::kJoin: + break; + case ResEvent::EventType::kSubFlow: + if (auto* params = event->params.ToPtr(endian->base)) + SwapEndian(endian, params); + break; + } +} + +static void SwapEndianForEventFields(ore::ResEndian* endian, ResEvent* event) { + switch (event->type) { + case ResEvent::EventType::kAction: + SwapEndian(&event->next_event_idx); + SwapEndian(&event->actor_idx); + SwapEndian(&event->actor_action_idx); + break; + case ResEvent::EventType::kSwitch: + SwapEndian(&event->next_event_idx); + SwapEndian(&event->actor_idx); + SwapEndian(&event->actor_query_idx); + break; + case ResEvent::EventType::kFork: + SwapEndian(&event->num_forks); + SwapEndian(&event->join_event_idx); + break; + case ResEvent::EventType::kJoin: + case ResEvent::EventType::kSubFlow: + SwapEndian(&event->next_event_idx); + break; + } +} + +void SwapEndian(ore::ResEndian* endian, ResEvent* event) { + if (endian->is_serializing) { + SwapEndianForEventData(endian, event); + SwapEndianForEventFields(endian, event); + } else { + SwapEndianForEventFields(endian, event); + SwapEndianForEventData(endian, event); + } +} + +static void SwapEndianImpl(ore::ResEndian* endian, ResEntryPoint* entry) { + ore::Array sub_flow_event_indices{entry->sub_flow_event_indices.ToPtr(endian->base), + entry->num_sub_flow_event_indices}; + for (auto& x : sub_flow_event_indices) + SwapEndian(&x); + + auto* variable_def_names = entry->variable_defs_names.ToPtr(endian->base); + if (variable_def_names) + SwapEndian(endian, variable_def_names); + + ore::Array variable_defs{entry->variable_defs.ToPtr(endian->base), + entry->num_variable_defs}; + for (auto& def : variable_defs) + SwapEndian(endian, &def); +} + +void SwapEndian(ore::ResEndian* endian, ResEntryPoint* entry) { + if (endian->is_serializing) { + SwapEndianImpl(endian, entry); + SwapEndian(&entry->main_event_idx); + SwapEndian(&entry->num_sub_flow_event_indices); + SwapEndian(&entry->num_variable_defs); + } else { + SwapEndian(&entry->main_event_idx); + SwapEndian(&entry->num_sub_flow_event_indices); + SwapEndian(&entry->num_variable_defs); + SwapEndianImpl(endian, entry); + } +} + +static void SwapEndianImpl(ore::ResEndian* endian, ResVariableDef* def) { + switch (def->type) { + case ore::ResMetaData::DataType::kIntArray: { + const auto num = def->num; + ore::Array array{def->value.int_array.ToPtr(endian->base), num}; + for (auto& x : array) + SwapEndian(&x); + break; + } + case ore::ResMetaData::DataType::kFloatArray: { + const auto num = def->num; + ore::Array array{def->value.float_array.ToPtr(endian->base), num}; + for (auto& x : array) + SwapEndian(reinterpret_cast(&x)); + break; + } + default: + break; + } +} + +static bool IsScalarVariableDef(ResVariableDef* def) { + using Type = ore::ResMetaData::DataType::Type; + return def->type == Type::kInt || def->type == Type::kBool || def->type == Type::kFloat; +} + +void SwapEndian(ore::ResEndian* endian, ResVariableDef* def) { + if (endian->is_serializing) { + SwapEndianImpl(endian, def); + SwapEndian(&def->num); + if (IsScalarVariableDef(def)) + SwapEndian(&def->value.i); + } else { + SwapEndian(&def->num); + if (IsScalarVariableDef(def)) + SwapEndian(&def->value.i); + SwapEndianImpl(endian, def); + } +} + +} // namespace evfl diff --git a/lib/EventFlow/src/evfl/ResTimeline.cpp b/lib/EventFlow/src/evfl/ResTimeline.cpp new file mode 100644 index 00000000..a81c9bf1 --- /dev/null +++ b/lib/EventFlow/src/evfl/ResTimeline.cpp @@ -0,0 +1,118 @@ +#include +#include +#include +#include +#include + +namespace evfl { + +using ore::SwapEndian; + +void SwapEndian(ore::ResEndian* endian, ResTrigger* trigger) { + SwapEndian(&trigger->clip_index); +} + +void SwapEndian(ore::ResEndian* endian, ResCut* cut) { + if (endian->is_serializing) { + if (auto* params = cut->params.ToPtr(endian->base)) + SwapEndian(endian, params); + SwapEndian(&cut->start_time); + } else { + SwapEndian(&cut->start_time); + if (auto* params = cut->params.ToPtr(endian->base)) + SwapEndian(endian, params); + } +} + +void SwapEndian(ore::ResEndian* endian, ResClip* clip) { + const auto swap_fields = [&] { + SwapEndian(&clip->start_time); + SwapEndian(&clip->duration); + SwapEndian(&clip->actor_index); + SwapEndian(&clip->actor_action_index); + }; + + const auto swap_params = [&] { + if (auto* params = clip->params.ToPtr(endian->base)) + SwapEndian(endian, params); + }; + + if (endian->is_serializing) { + swap_params(); + swap_fields(); + } else { + swap_fields(); + swap_params(); + } +} + +void SwapEndian(ore::ResEndian* endian, ResOneshot* oneshot) { + const auto swap_fields = [&] { + SwapEndian(&oneshot->time); + SwapEndian(&oneshot->actor_index); + SwapEndian(&oneshot->actor_action_index); + }; + + const auto swap_params = [&] { + if (auto* params = oneshot->params.ToPtr(endian->base)) + SwapEndian(endian, params); + }; + + if (endian->is_serializing) { + swap_params(); + swap_fields(); + } else { + swap_fields(); + swap_params(); + } +} + +void SwapEndian(ore::ResEndian* endian, ResSubtimeline* subtimeline) {} + +static void SwapEndianForTimelineData(ore::ResEndian* endian, ResTimeline* timeline) { + ore::Array clips{timeline->clips.ToPtr(endian->base), timeline->num_clips}; + for (auto& clip : clips) + SwapEndian(endian, &clip); + + ore::Array oneshots{timeline->oneshots.ToPtr(endian->base), timeline->num_oneshots}; + for (auto& oneshot : oneshots) + SwapEndian(endian, &oneshot); + + ore::Array actors{timeline->actors.ToPtr(endian->base), timeline->num_actors}; + for (auto& actor : actors) + SwapEndian(endian, &actor); + + const int num_triggers = timeline->num_clips * 2; + ore::Array triggers{timeline->triggers.ToPtr(endian->base), num_triggers}; + for (auto& trigger : triggers) + SwapEndian(endian, &trigger); + + ore::Array cuts{timeline->cuts.ToPtr(endian->base), timeline->num_cuts}; + for (auto& cut : cuts) + SwapEndian(endian, &cut); + + if (auto* params = timeline->params.ToPtr(endian->base)) + SwapEndian(endian, params); +} + +void SwapEndian(ore::ResEndian* endian, ResTimeline* timeline) { + const auto swap_fields = [&] { + SwapEndian(&timeline->duration); + SwapEndian(&timeline->num_actors); + SwapEndian(&timeline->num_actions); + SwapEndian(&timeline->num_clips); + SwapEndian(&timeline->num_oneshots); + SwapEndian(&timeline->num_subtimelines); + SwapEndian(&timeline->num_cuts); + }; + + if (endian->is_serializing) { + SwapEndianForTimelineData(endian, timeline); + swap_fields(); + } else { + swap_fields(); + SwapEndianForTimelineData(endian, timeline); + } +} + +} // namespace evfl diff --git a/lib/EventFlow/src/evfl/TimelineObj.cpp b/lib/EventFlow/src/evfl/TimelineObj.cpp new file mode 100644 index 00000000..14e89d8b --- /dev/null +++ b/lib/EventFlow/src/evfl/TimelineObj.cpp @@ -0,0 +1,235 @@ +#include +#include +#include +#include +#include + +namespace evfl { + +int TimelineObj::s_GlobalPlayCounter{}; + +// NON_MATCHING: didn't bother matching, clearly equivalent +TimelineObj::TimelineObj() = default; + +void TimelineObj::Calc() { + CalcImpl(); + for (auto* timeline : m_sub_timelines) { + if (timeline) + timeline->Calc(); + } +} + +void TimelineObj::Reset() { + m_play_counter = ++s_GlobalPlayCounter; + m_started = false; + m_state = TimelineState::kNotStarted; + for (auto* timeline : m_sub_timelines) { + if (timeline) + timeline->Reset(); + } +} + +void TimelineObj::SetState(TimelineState::Type state) { + m_state = state; +} + +void TimelineObj::Start(float start_time) { + if (m_started) + return; + + m_started = true; + m_state = TimelineState::kPlaying; + m_time = -1.0; + m_last_trigger_idx = -1; + m_last_oneshot_idx = -1; + JumpTimeTo(start_time); + Calc(); + + for (auto* timeline : m_sub_timelines) { + if (timeline && !timeline->m_started) + timeline->Start(start_time); + } +} + +void TimelineObj::JumpTimeTo(float time) { + JumpTimeToImpl(time); +} + +void TimelineObj::AdvanceTimeTo(float time) { + AdvanceTimeToImpl(time); +} + +namespace { + +TriggerType::Type ReverseTriggerType(TriggerType::Type clip_trigger_type) { + switch (clip_trigger_type) { + case TriggerType::kClipEnter: + return TriggerType::kClipLeave; + case TriggerType::kClipLeave: + return TriggerType::kClipEnter; + case TriggerType::kOneshot: + return TriggerType::kOneshot; + default: + return {}; + } +} + +float GetTriggerTime(TriggerType::Type type, const ResClip& clip) { + switch (type) { + case TriggerType::kEnter: + return clip.start_time; + case TriggerType::kLeave: + return clip.start_time + clip.duration; + default: + return 0.0; + } +} + +float GetTriggerTimeReverse(TriggerType::Type type, const ResClip& clip) { + switch (type) { + case TriggerType::kEnter: + return clip.start_time + clip.duration; + case TriggerType::kLeave: + return clip.start_time; + default: + return 0.0; + } +} + +} // namespace + +// NON_MATCHING: reorderings for the action binding stuff +void TimelineObj::CalcImpl() { + if (m_time == m_new_time) + return; + + const int direction = m_time < m_new_time ? 1 : -1; + const auto time_max = m_time < m_new_time ? m_new_time : m_time; + const auto time_min = m_time < m_new_time ? m_time : m_new_time; + + ore::Array triggers{m_timeline->triggers.Get(), 2 * m_timeline->num_clips}; + ore::Array clips{m_timeline->clips.Get(), m_timeline->num_clips}; + + for (int trigger_idx = (m_time < m_new_time) + m_last_trigger_idx; + u32(trigger_idx) < u32(triggers.size()); trigger_idx += direction) { + const auto& trigger = triggers[trigger_idx]; + const auto& clip = clips[trigger.clip_index]; + const auto trigger_type = TriggerType::Type(trigger.trigger_type); + + const float trigger_time = GetTriggerTime(trigger_type, clip); + if (trigger_time <= time_min || time_max < trigger_time) + break; + + m_last_trigger_idx = trigger_idx; + + if (m_jumped_time) { + const float rev_trigger_time = GetTriggerTimeReverse(trigger_type, clip); + if (time_min < rev_trigger_time && rev_trigger_time <= time_max) + continue; + } + + const auto actor_idx = clip.actor_index; + const auto& bindings = m_act_binder.GetBindings(); + const auto* actions = m_timeline->actors.Get()[actor_idx].actions.Get(); + const auto& binding = bindings[actor_idx]; + const ore::StringView name = *actions[clip.actor_action_index].name.Get(); + const auto* action = binding.GetAction(name); + + auto real_trigger_type = trigger_type; + if (m_jumped_time && direction < 0) + real_trigger_type = ReverseTriggerType(real_trigger_type); + + const ActionArg arg(&clip, binding.GetUserData(), action->user_data, + m_new_time - trigger_time, real_trigger_type, clip.params.Get()); + ActionDoneHandler handler{this}; + action->handler(arg, std::move(handler)); + } + + ore::Array oneshots{m_timeline->oneshots.Get(), m_timeline->num_oneshots}; + for (int oneshot_idx = (m_time < m_new_time) + m_last_oneshot_idx; + u32(oneshot_idx) < u32(oneshots.size()); oneshot_idx += direction) { + const auto& oneshot = oneshots[oneshot_idx]; + const auto trigger_time = oneshot.time; + if (trigger_time < time_min || time_max < trigger_time) + break; + + m_last_oneshot_idx = oneshot_idx; + + if (m_jumped_time && trigger_time != m_new_time) + continue; + + const auto actor_idx = oneshot.actor_index; + const auto& bindings = m_act_binder.GetBindings(); + const auto& binding = bindings[actor_idx]; + const auto* actions = m_timeline->actors.Get()[actor_idx].actions.Get(); + const ore::StringView name = *actions[oneshot.actor_action_index].name.Get(); + const auto* action = binding.GetAction(name); + + const ActionArg arg(&oneshot, binding.GetUserData(), action->user_data, + m_new_time - trigger_time, oneshot.params.Get()); + ActionDoneHandler handler{this}; + action->handler(arg, std::move(handler)); + } + + m_time = m_new_time; +} + +void TimelineObj::AdvanceTimeToImpl(float time) { + m_new_time = time; + m_jumped_time = false; + for (auto* timeline : m_sub_timelines) { + if (timeline) + timeline->AdvanceTimeToImpl(time); + } +} + +void TimelineObj::JumpTimeToImpl(float time) { + m_new_time = time; + m_jumped_time = true; + for (auto* timeline : m_sub_timelines) { + if (timeline) + timeline->JumpTimeToImpl(time); + } +} + +bool TimelineObj::RegisterSubtimeline(TimelineObj* obj) { + ore::Array subtimelines{m_timeline->subtimelines.Get(), + m_timeline->num_subtimelines}; + for (int i = 0; i < subtimelines.size(); ++i) { + if (ore::StringView(*obj->m_timeline->name.Get()) == *subtimelines[i].name.Get()) { + m_sub_timelines[i] = obj; + return true; + } + } + return false; +} + +// NON_MATCHING: std::fill using obj->m_sub_timelines.size() rather than the byte size +bool TimelineObj::Builder::Build(TimelineObj* obj, AllocateArg allocate_arg) { + if (!obj) + return false; + + if (!allocate_arg.alloc || !allocate_arg.free) + return false; + + obj->Finalize(); + + EvflAllocator allocator{allocate_arg}; + obj->m_allocator = allocator; + + m_act_binder_builder.Build(&obj->m_act_binder, &obj->m_allocator, + {m_timeline->actors.Get(), m_timeline->num_actors}); + + auto& bindings = obj->m_act_binder.GetBindings(); + for (auto it = bindings.begin(); it != bindings.end(); ++it) + it->SetIsUsed(true); + + obj->m_timeline = m_timeline; + obj->m_allocator = allocator; + obj->m_sub_timelines.ConstructElements(m_timeline->num_subtimelines, &allocator); + std::fill(obj->m_sub_timelines.begin(), obj->m_sub_timelines.end(), nullptr); + + return true; +} + +} // namespace evfl diff --git a/lib/EventFlow/src/ore/BinaryFile.cpp b/lib/EventFlow/src/ore/BinaryFile.cpp new file mode 100644 index 00000000..f705306b --- /dev/null +++ b/lib/EventFlow/src/ore/BinaryFile.cpp @@ -0,0 +1,182 @@ +#include +#include +#include + +namespace ore { + +bool BinaryFileHeader::IsValid(s64 magic_, int ver_major_, int ver_minor_, int ver_patch_, + int ver_sub_) const { + bool valid = true; + valid &= int(ver_major) == ver_major_ && int(ver_minor) == ver_minor_ && + magic == magic_ & int(ver_patch) <= ver_patch_; + valid &= IsEndianReverse() || IsEndianValid(); + valid &= IsAlignmentValid(); + return valid; +} + +bool BinaryFileHeader::IsSignatureValid(s64 magic_) const { + return magic == magic_; +} + +bool BinaryFileHeader::IsVersionValid(int major, int minor, int patch, int sub) const { + if (int(ver_major) != major) + return false; + if (int(ver_minor) != minor) + return false; + if (int(ver_patch) > patch) + return false; + return true; +} + +bool BinaryFileHeader::IsEndianReverse() const { + return bom == s16(0xFFFE); +} + +bool BinaryFileHeader::IsEndianValid() const { + return bom == s16(0xFEFF); +} + +bool BinaryFileHeader::IsAlignmentValid() const { + return (std::uintptr_t(this) & (GetAlignment() - 1)) == 0; +} + +int BinaryFileHeader::GetAlignment() const { + return 1 << alignment; +} + +static constexpr u32 FlagRelocated = 1 << 0; + +bool BinaryFileHeader::IsRelocated() const { + return relocation_flags & FlagRelocated; +} + +void BinaryFileHeader::SetRelocated(bool relocated) { + if (relocated) + relocation_flags |= FlagRelocated; + else + relocation_flags &= ~FlagRelocated; +} + +void BinaryFileHeader::SetByteOrderMark() { + bom = s16(0xFEFF); +} + +int BinaryFileHeader::GetFileSize() const { + return file_size; +} + +void BinaryFileHeader::SetFileSize(int size) { + file_size = size; +} + +void BinaryFileHeader::SetAlignment(int alignment_) { + alignment = CountTrailingZeros(u32(alignment_)); +} + +StringView BinaryFileHeader::GetFileName() const { + StringView name; + if (file_name_offset != 0) + name = reinterpret_cast(this) + file_name_offset; + return name; +} + +void BinaryFileHeader::SetFileName(const StringView& name) { + if (name.empty()) { + file_name_offset = 0; + } else { + file_name_offset = int(intptr_t(name.data()) - intptr_t(this)); +#ifdef MATCHING_HACK_NX_CLANG + asm(""); +#endif + } +} + +RelocationTable* BinaryFileHeader::GetRelocationTable() { + if (relocation_table_offset == 0) + return nullptr; + return reinterpret_cast(reinterpret_cast(this) + + relocation_table_offset); +} + +void BinaryFileHeader::SetRelocationTable(RelocationTable* table) { + if (table == nullptr) { + relocation_table_offset = 0; + } else { + relocation_table_offset = int(intptr_t(table) - intptr_t(this)); +#ifdef MATCHING_HACK_NX_CLANG + asm(""); +#endif + } +} + +BinaryBlockHeader* BinaryFileHeader::GetFirstBlock() { + if (first_block_offset == 0) + return nullptr; + return reinterpret_cast(reinterpret_cast(this) + first_block_offset); +} + +const BinaryBlockHeader* BinaryFileHeader::GetFirstBlock() const { + if (first_block_offset == 0) + return nullptr; + return reinterpret_cast(reinterpret_cast(this) + + first_block_offset); +} + +BinaryBlockHeader* BinaryFileHeader::FindFirstBlock(int type) { + auto* block = GetFirstBlock(); + if (!block || block->magic == type) + return block; + return block->FindNextBlock(type); +} + +const BinaryBlockHeader* BinaryFileHeader::FindFirstBlock(int type) const { + auto* block = GetFirstBlock(); + if (!block || block->magic == type) + return block; + return block->FindNextBlock(type); +} + +void BinaryFileHeader::SetFirstBlock(BinaryBlockHeader* block) { + if (block == nullptr) + first_block_offset = 0; + else + first_block_offset = int(intptr_t(block) - intptr_t(this)); +} + +BinaryBlockHeader* BinaryBlockHeader::FindNextBlock(int type) { + auto* block = this; + do + block = block->GetNextBlock(); + while (block && block->magic != type); + return block; +} + +const BinaryBlockHeader* BinaryBlockHeader::FindNextBlock(int type) const { + auto* block = this; + do + block = block->GetNextBlock(); + while (block && block->magic != type); + return block; +} + +BinaryBlockHeader* BinaryBlockHeader::GetNextBlock() { + if (next_block_offset == 0) + return nullptr; + return reinterpret_cast(reinterpret_cast(this) + next_block_offset); +} + +const BinaryBlockHeader* BinaryBlockHeader::GetNextBlock() const { + if (next_block_offset == 0) + return nullptr; + return reinterpret_cast(reinterpret_cast(this) + + next_block_offset); +} + +void BinaryBlockHeader::SetNextBlock(BinaryBlockHeader* block) { + if (block == nullptr) + next_block_offset = 0; + else + next_block_offset = int(intptr_t(block) - intptr_t(this)); +} + +} // namespace ore diff --git a/lib/EventFlow/src/ore/BitUtils.cpp b/lib/EventFlow/src/ore/BitUtils.cpp new file mode 100644 index 00000000..e392bd13 --- /dev/null +++ b/lib/EventFlow/src/ore/BitUtils.cpp @@ -0,0 +1,115 @@ +#include + +namespace ore { + +void BitArray::SetAllOn() { + const int num = m_num_bits >> ShiftAmount; + Fill(num, Word(-1)); + + u32 remainder = u32(m_num_bits) % NumBitsPerWord; + if (remainder != 0) + m_words[num] = (1ul << remainder) - 1; +} + +void BitArray::SetAllOff() { + Fill(GetNumWords(), Word(0)); +} + +BitArray::TestIter BitArray::BeginTest() const { + return TestIter(m_words, m_words + GetNumWords()); +} + +BitArray::TestIter BitArray::EndTest() const { + return TestIter(nullptr, nullptr); +} + +BitArray::TestClearIter BitArray::BeginTestClear() { + return TestClearIter(m_words, m_words + GetNumWords()); +} + +BitArray::TestClearIter BitArray::EndTestClear() { + return TestClearIter(nullptr, nullptr); +} + +BitArray::TestIter::TestIter(const BitArray::Word* start, const BitArray::Word* end) { + for (auto* it = start; it != end; ++it) { + if (*it != 0) { + auto idx = CountTrailingZeros(*it); + idx += 8 * int(intptr_t(it) - intptr_t(start)) & ClearMask; + m_bit = idx; + m_current_word = it; + m_last_word = end; + m_next = *it & (*it - 1); + return; + } + } + + SetInvalid(); +} + +BitArray::TestIter& BitArray::TestIter::operator++() { + m_bit &= ClearMask; + + // Fast path: we still have bits in the current word + if (m_next != 0) { + m_bit += CountTrailingZeros(m_next); + m_next &= m_next - 1; + return *this; + } + + // Find the next nonzero word and the first set bit in it + ++m_current_word; + for (; m_current_word != m_last_word; ++m_current_word) { + m_bit += NumBitsPerWord; + if (*m_current_word == 0) + continue; + m_bit += CountTrailingZeros(*m_current_word); + m_next = *m_current_word & (*m_current_word - 1); + return *this; + } + + SetInvalid(); + return *this; +} + +BitArray::TestClearIter::TestClearIter(BitArray::Word* start, BitArray::Word* end) { + for (auto* it = start; it != end; ++it) { + if (*it != 0) { + auto idx = CountTrailingZeros(*it); + idx += 8 * int(intptr_t(it) - intptr_t(start)) & ClearMask; + m_bit = idx; + m_current_word = it; + m_last_word = end; + m_next = *it & (*it - 1); + return; + } + } + + SetInvalid(); +} + +BitArray::TestClearIter& BitArray::TestClearIter::operator++() { + m_bit &= ClearMask; + + if (m_next != 0) { + m_bit += CountTrailingZeros(m_next); + m_next &= m_next - 1; + return *this; + } + + *m_current_word = 0; + ++m_current_word; + for (; m_current_word != m_last_word; *m_current_word = 0, ++m_current_word) { + m_bit += NumBitsPerWord; + if (*m_current_word == 0) + continue; + m_bit += CountTrailingZeros(*m_current_word); + m_next = *m_current_word & (*m_current_word - 1); + return *this; + } + + SetInvalid(); + return *this; +} + +} // namespace ore diff --git a/lib/EventFlow/src/ore/EnumUtil.cpp b/lib/EventFlow/src/ore/EnumUtil.cpp new file mode 100644 index 00000000..71c1cc95 --- /dev/null +++ b/lib/EventFlow/src/ore/EnumUtil.cpp @@ -0,0 +1,13 @@ +#include +#include + +namespace ore { + +int detail::EnumUtil::FindIndex(int value, const IterRange& values) { + auto it = std::find_if(values.begin(), values.end(), [value](int x) { return value == x; }); + if (it == values.end()) + return -1; + return static_cast(it - values.begin()); +} + +} // namespace ore diff --git a/lib/EventFlow/src/ore/RelocationTable.cpp b/lib/EventFlow/src/ore/RelocationTable.cpp new file mode 100644 index 00000000..b58625fb --- /dev/null +++ b/lib/EventFlow/src/ore/RelocationTable.cpp @@ -0,0 +1,106 @@ +#include +#include + +namespace ore { + +namespace { + +struct BitFlag32 { + explicit BitFlag32(u32 flags) : m_flags(flags) {} + bool operator[](int idx) const { return m_flags & (1 << idx); } + + u32 m_flags{}; +}; + +} // namespace + +void RelocationTable::Section::SetPtr(void* ptr_) { + ptr = reinterpret_cast(ptr_); +} + +void* RelocationTable::Section::GetPtr() const { + return reinterpret_cast(ptr); +} + +void* RelocationTable::Section::GetPtrInFile(void* base) const { + return static_cast(base) + offset; +} + +void* RelocationTable::Section::GetBasePtr(void* base) const { + if (ptr) + base = reinterpret_cast(ptr - offset); + return base; +} + +u32 RelocationTable::Section::GetSize() const { + return size; +} + +void RelocationTable::Relocate() { + char* const table_base = reinterpret_cast(this) - table_start_offset; + const auto* entries = GetEntries(); + const int num = num_sections; + + for (int section_idx = 0; section_idx < num; ++section_idx) { + const auto& section = GetSections()[section_idx]; + + auto* base = static_cast(section.GetBasePtr(table_base)); + const int idx0 = section.first_entry_idx; + const int end = idx0 + section.num_entries; + + for (int idx = idx0; idx < end; ++idx) { + const auto& entry = entries[idx]; + const auto pointers_offset = entry.pointers_offset; + const BitFlag32 mask{entry.mask}; + + auto* pointer_ptr = reinterpret_cast(table_base + pointers_offset); + for (int i = 0; i < 32; ++i, ++pointer_ptr) { + if (!mask[i]) + continue; + const auto offset = static_cast(*pointer_ptr); + void* ptr = offset == 0 ? nullptr : reinterpret_cast(base + offset); + std::memcpy(pointer_ptr, &ptr, sizeof(ptr)); + } + } + } +} + +void RelocationTable::Unrelocate() { + char* const table_base = reinterpret_cast(this) - table_start_offset; + const auto* entries = GetEntries(); + const int num = num_sections; + + for (int section_idx = 0; section_idx < num; ++section_idx) { + auto& section = GetSections()[section_idx]; + + auto* base = static_cast(section.GetBasePtr(table_base)); + section.SetPtr(nullptr); + const int idx0 = section.first_entry_idx; + const int end = idx0 + section.num_entries; + + for (int idx = idx0; idx < end; ++idx) { + const auto& entry = entries[idx]; + const auto pointers_offset = entry.pointers_offset; + const BitFlag32 mask{entry.mask}; + + auto* pointer_ptr = reinterpret_cast(table_base + pointers_offset); + for (int i = 0; i < 32; ++i, ++pointer_ptr) { + if (!mask[i]) + continue; + void* ptr = *pointer_ptr; + u64 offset = static_cast(ptr == nullptr ? 0 : intptr_t(ptr) - intptr_t(base)); + std::memcpy(pointer_ptr, &offset, sizeof(offset)); + } + } + } +} + +int RelocationTable::CalcSize(int num_sections, int num_entries) { + int size = 0; + size += offsetof(RelocationTable, sections); + size += sizeof(Section) * num_sections; + size += sizeof(Section::Entry) * num_entries; + return size; +} + +} // namespace ore diff --git a/lib/EventFlow/src/ore/ResDic.cpp b/lib/EventFlow/src/ore/ResDic.cpp new file mode 100644 index 00000000..019ffe61 --- /dev/null +++ b/lib/EventFlow/src/ore/ResDic.cpp @@ -0,0 +1,50 @@ +#include +#include +#include + +namespace ore { + +int ResDic::FindRefBit(const StringView& str1, const StringView& str2) { + const auto len1 = str1.size(); + const auto len2 = str2.size(); + const auto len = std::max(len1, len2); + + for (int bit_idx = 0; bit_idx < 8 * len; ++bit_idx) { + const int idx = bit_idx >> 3; + + int bit1 = 0; + if (len1 > idx) + bit1 = str1[len1 + -(idx + 1)] >> (bit_idx % 8) & 1; + + int bit2 = 0; + if (len2 > idx) + bit2 = str2[len2 + -(idx + 1)] >> (bit_idx % 8) & 1; + + if (bit1 != bit2) + return bit_idx; + } + + return -1; +} + +void SwapEndian(ResEndian* endian, ResDic* dic) { + const auto swap_entries = [&] { + const int num_entries = dic->num_entries + 1; + for (int i = 0; i < num_entries; ++i) { + ResDicEntry& entry = dic->GetEntries()[i]; + SwapEndian(&entry.compact_bit_idx); + SwapEndian(&entry.next_indices[0]); + SwapEndian(&entry.next_indices[1]); + } + }; + + if (endian->is_serializing) { + swap_entries(); + SwapEndian(&dic->num_entries); + } else { + SwapEndian(&dic->num_entries); + swap_entries(); + } +} + +} // namespace ore diff --git a/lib/EventFlow/src/ore/ResMetaData.cpp b/lib/EventFlow/src/ore/ResMetaData.cpp new file mode 100644 index 00000000..2587f3d6 --- /dev/null +++ b/lib/EventFlow/src/ore/ResMetaData.cpp @@ -0,0 +1,89 @@ +#include +#include +#include + +namespace ore { + +static void SwapEndianImpl(ResEndian* endian, ResMetaData* res) { + auto* dictionary = res->dictionary.ToPtr(endian->base); + if (dictionary) + SwapEndian(endian, dictionary); + + switch (res->type) { + case ResMetaData::DataType::kArgument: + case ResMetaData::DataType::kString: + case ResMetaData::DataType::kStringArray: + case ResMetaData::DataType::kActorIdentifier: { + if (res->num_items == 0) + break; + BinString* str = res->value.str.ToPtr(endian->base); + if (endian->is_serializing) { + for (int i = 0, n = res->num_items; i < n; ++i) { + auto* next = str->NextString(); + SwapEndian(&str->length); + str = next; + } + } else { + for (int i = 0, n = res->num_items; i < n; ++i) { + SwapEndian(&str->length); + str = str->NextString(); + } + } + break; + } + case ResMetaData::DataType::kContainer: { + for (int i = 0, n = res->num_items; i < n; ++i) { + ResMetaData* ptr = (&res->value.container + i)->ToPtr(endian->base); + if (ptr) + SwapEndian(endian, ptr); + } + break; + } + case ResMetaData::DataType::kInt: + case ResMetaData::DataType::kBool: + case ResMetaData::DataType::kFloat: + case ResMetaData::DataType::kIntArray: + case ResMetaData::DataType::kFloatArray: + for (int i = 0, n = res->num_items; i < n; ++i) { + SwapEndian(&res->value.i + i); + } + break; + case ResMetaData::DataType::kWString: + case ResMetaData::DataType::kWStringArray: { + if (res->num_items == 0) + break; + BinWString* str = res->value.wstr.ToPtr(endian->base); + if (endian->is_serializing) { + for (int i = 0, n = res->num_items; i < n; ++i) { + for (auto& c : *str) + c = static_cast(SwapEndian(static_cast(c))); + auto* next = str->NextString(); + SwapEndian(&str->length); + str = next; + } + } else { + for (int i = 0, n = res->num_items; i < n; ++i) { + SwapEndian(&str->length); + for (auto& c : *str) + c = static_cast(SwapEndian(static_cast(c))); + str = str->NextString(); + } + } + break; + } + case ResMetaData::DataType::kBoolArray: + break; + } +} + +void SwapEndian(ResEndian* endian, ResMetaData* res) { + if (endian->is_serializing) { + SwapEndianImpl(endian, res); + SwapEndian(&res->num_items); + } else { + SwapEndian(&res->num_items); + SwapEndianImpl(endian, res); + } +} + +} // namespace ore diff --git a/lib/EventFlow/src/ore/StringPool.cpp b/lib/EventFlow/src/ore/StringPool.cpp new file mode 100644 index 00000000..6b45338a --- /dev/null +++ b/lib/EventFlow/src/ore/StringPool.cpp @@ -0,0 +1,13 @@ +#include + +namespace ore { + +int StringPool::GetLength() const { + return length; +} + +void StringPool::SetLength(int len) { + length = len; +} + +} // namespace ore diff --git a/lib/NintendoSDK b/lib/NintendoSDK deleted file mode 160000 index dea2e24d..00000000 --- a/lib/NintendoSDK +++ /dev/null @@ -1 +0,0 @@ -Subproject commit dea2e24df14973b3c80901c34766b87f89f708b0 diff --git a/lib/NintendoSDK/.clang-format b/lib/NintendoSDK/.clang-format new file mode 100644 index 00000000..ef862606 --- /dev/null +++ b/lib/NintendoSDK/.clang-format @@ -0,0 +1,74 @@ +--- +Language: Cpp +AccessModifierOffset: -4 +AlignAfterOpenBracket: Align +AlignConsecutiveAssignments: false +AlignConsecutiveDeclarations: false +AlignOperands: true +AlignTrailingComments: true +AllowAllParametersOfDeclarationOnNextLine: true +AllowShortBlocksOnASingleLine: Never +AllowShortCaseLabelsOnASingleLine: false +AllowShortFunctionsOnASingleLine: Inline +AllowShortIfStatementsOnASingleLine: Never +AllowShortLoopsOnASingleLine: false +AlwaysBreakAfterDefinitionReturnType: None +AlwaysBreakAfterReturnType: None +AlwaysBreakBeforeMultilineStrings: false +AlwaysBreakTemplateDeclarations: Yes +BinPackArguments: true +BinPackParameters: true +BreakBeforeBinaryOperators: None +BreakBeforeBraces: Attach +BreakBeforeTernaryOperators: false +BreakConstructorInitializersBeforeComma: false +ColumnLimit: 100 +CommentPragmas: '^ (IWYU pragma:|NOLINT)' +ConstructorInitializerAllOnOneLineOrOnePerLine: false +ConstructorInitializerIndentWidth: 4 +ContinuationIndentWidth: 4 +Cpp11BracedListStyle: true +DerivePointerAlignment: false +DisableFormat: false +ForEachMacros: [] +IncludeCategories: + - Regex: '^<[Ww]indows\.h>$' + Priority: 1 + - Regex: '^<' + Priority: 2 + - Regex: '^"' + Priority: 3 +IndentCaseLabels: false +IndentWidth: 4 +IndentWrappedFunctionNames: false +KeepEmptyLinesAtTheStartOfBlocks: false +MacroBlockBegin: '' +MacroBlockEnd: '' +MaxEmptyLinesToKeep: 1 +NamespaceIndentation: None +ObjCBlockIndentWidth: 4 +ObjCSpaceAfterProperty: false +ObjCSpaceBeforeProtocolList: true +PenaltyBreakBeforeFirstCallParameter: 19 +PenaltyBreakComment: 300 +PenaltyBreakFirstLessLess: 120 +PenaltyBreakString: 1000 +PenaltyExcessCharacter: 1000000 +PenaltyReturnTypeOnItsOwnLine: 60 +PointerAlignment: Left +ReflowComments: true +SortIncludes: true +SpaceAfterCStyleCast: false +SpaceBeforeAssignmentOperators: true +SpaceBeforeParens: ControlStatements +SpaceInEmptyParentheses: false +SpacesBeforeTrailingComments: 2 +SpacesInAngles: false +SpacesInContainerLiterals: true +SpacesInCStyleCastParentheses: false +SpacesInParentheses: false +SpacesInSquareBrackets: false +Standard: c++17 +TabWidth: 4 +UseTab: Never +... diff --git a/lib/NintendoSDK/.gitrepo b/lib/NintendoSDK/.gitrepo new file mode 100644 index 00000000..cff1dc74 --- /dev/null +++ b/lib/NintendoSDK/.gitrepo @@ -0,0 +1,12 @@ +; DO NOT EDIT (unless you know what you are doing) +; +; This subdirectory is a git "subrepo", and this file is maintained by the +; git-subrepo command. See https://github.com/git-commands/git-subrepo#readme +; +[subrepo] + remote = https://github.com/open-ead/nnheaders + branch = master + commit = 9ee21399ff05176c98b0651be3851fba3f70ceda + parent = ffcc7f659ebc9bc9d149e52bec553b906bb47369 + method = merge + cmdver = 0.4.3 diff --git a/lib/NintendoSDK/CMakeLists.txt b/lib/NintendoSDK/CMakeLists.txt new file mode 100644 index 00000000..a9c1a02e --- /dev/null +++ b/lib/NintendoSDK/CMakeLists.txt @@ -0,0 +1,129 @@ +project(NintendoSDK CXX ASM) + +add_library(NintendoSDK OBJECT + include/nvn/nvn_types.h + include/nvn/nvn.h + include/nvn/nvn_api.h + include/nn/types.h + include/nn/os.h + include/nn/nifm.h + include/nn/prepo.h + include/nn/vfx/Config.h + include/nn/vfx/System.h + include/nn/vfx/Heap.h + include/nn/socket.h + include/nn/aoc.h + include/nn/fs.h + include/nn/ro.h + include/nn/oe.h + include/nn/util.h + include/nn/image.h + include/nn/util/Float2.h + include/nn/ui2d/detail/TexCoordArray.h + include/nn/ui2d/Layout.h + include/nn/ui2d/Parts.h + include/nn/ui2d/Pane.h + include/nn/ui2d/Material.h + include/nn/g3d/ResMaterialAnim.h + include/nn/g3d/ResShapeAnim.h + include/nn/g3d/ResLightAnim.h + include/nn/g3d/ResSkeletalAnim.h + include/nn/g3d/ResSceneAnim.h + include/nn/g3d/BindFuncTable.h + include/nn/g3d/ResFile.h + include/nn/g3d/ResMaterial.h + include/nn/g3d/ResFogAnim.h + include/nn/g3d/ResModel.h + include/nn/nn.h + include/nn/settings.h + include/nn/hid.h + include/nn/atk/detail/StreamSoundRuntime.h + include/nn/atk/detail/BasicSound.h + include/nn/atk/detail/WaveSoundRuntime.h + include/nn/atk/detail/SequenceSoundRuntime.h + include/nn/atk/detail/SoundArchiveManager.h + include/nn/atk/detail/AdvancedWaveSoundRuntime.h + include/nn/atk/SoundArchivePlayer.h + include/nn/atk/SoundPlayer.h + include/nn/atk/SoundDataManager.h + include/nn/nex/client.h + include/nn/nex/RootObject.h + include/nn/nex/socket.h + include/nn/nex/key.h + include/nn/nex/checksum.h + include/nn/nex/reference.h + include/nn/nex/pseudo.h + include/nn/nex/string.h + include/nn/nex/instance.h + include/nn/nex/ddl.h + include/nn/nex/encryption.h + include/nn/nex/cache.h + include/nn/nex/time.h + include/nn/nex/plugin.h + include/nn/nex/dynamic.h + include/nn/nex/data.h + include/nn/nex/auth.h + include/nn/nex/buffer.h + include/nn/nex/system.h + include/nn/nex/hash.h + include/nn/time.h + include/nn/diag.h + include/nn/init.h + include/nn/crypto.h + include/nn/ssl.h + include/nn/gfx/detail/pool.h + include/nn/gfx/detail/deviceimpl.h + include/nn/gfx/detail/bufferimpl.h + include/nn/gfx/device.h + include/nn/gfx/memory.h + include/nn/gfx/buffer.h + include/nn/gfx/api.h + include/nn/vi.h + include/nn/account.h + include/nn/audio.h + include/nn/friends.h + include/nn/mem.h + include/nv.h + include/vapours/results.hpp + include/vapours/results/sf_results.hpp + include/vapours/results/capsrv_results.hpp + include/vapours/results/pgl_results.hpp + include/vapours/results/lr_results.hpp + include/vapours/results/spl_results.hpp + include/vapours/results/pm_results.hpp + include/vapours/results/settings_results.hpp + include/vapours/results/debug_results.hpp + include/vapours/results/cal_results.hpp + include/vapours/results/i2c_results.hpp + include/vapours/results/results_common.hpp + include/vapours/results/time_results.hpp + include/vapours/results/vi_results.hpp + include/vapours/results/ns_results.hpp + include/vapours/results/fs_results.hpp + include/vapours/results/hipc_results.hpp + include/vapours/results/os_results.hpp + include/vapours/results/ro_results.hpp + include/vapours/results/loader_results.hpp + include/vapours/results/err_results.hpp + include/vapours/results/ncm_results.hpp + include/vapours/results/svc_results.hpp + include/vapours/results/nim_results.hpp + include/vapours/results/exosphere_results.hpp + include/vapours/results/creport_results.hpp + include/vapours/results/erpt_results.hpp + include/vapours/results/kvdb_results.hpp + include/vapours/results/dmnt_results.hpp + include/vapours/results/updater_results.hpp + include/vapours/results/fatal_results.hpp + include/vapours/results/sm_results.hpp + include/vapours/results/psc_results.hpp + + modules/nvn/nvnInit.cpp +) + +target_include_directories(NintendoSDK PUBLIC include/) +target_compile_options(NintendoSDK PRIVATE -fno-strict-aliasing) +target_compile_options(NintendoSDK PRIVATE -Wall -Wextra) +target_compile_options(NintendoSDK PRIVATE -Wno-invalid-offsetof) + +target_link_libraries(NintendoSDK PUBLIC) diff --git a/lib/NintendoSDK/README.md b/lib/NintendoSDK/README.md new file mode 100644 index 00000000..a4100cf9 --- /dev/null +++ b/lib/NintendoSDK/README.md @@ -0,0 +1,10 @@ +# nnheaders +Repository of user created nnsdk headers. + +The header files contained herewithin are entirely user created via Reverse Engineering or publicly available sources (non stripped binaries containing symbols). + +Do not ask for or PR any copyrighted material to this repo. You will be ignored. + +# Credits + - [Shadow](https://github.com/shadowninja108/) - For [Skyline](https://github.com/shadowninja108/Skyline), which was the primary inspiration and use case for this repo. + - [Shibbo](https://github.com/shibbo) - For [OdysseyReversed](https://github.com/shibbo/OdysseyReversed/), which most of these headers came from. diff --git a/lib/NintendoSDK/include/nn/account.h b/lib/NintendoSDK/include/nn/account.h new file mode 100644 index 00000000..739c9c05 --- /dev/null +++ b/lib/NintendoSDK/include/nn/account.h @@ -0,0 +1,57 @@ +/** + * @file account.h + * @brief Account service implementation. + */ + +#pragma once + +#include +#include + +namespace nn { +namespace account { +typedef char Nickname[0x21]; +typedef u64 NetworkServiceAccountId; + +class AsyncContext; + +class Uid { +public: + bool IsValid() const { return m_Storage[0] != 0 || m_Storage[1] != 0; } + + u64 m_Storage[2]; +}; + +class UserHandle { +public: + Uid m_Uid; + void* m_Handle; +}; + +void Initialize(); +Result ListAllUsers(s32*, Uid*, s32 numUsers); +Result OpenUser(UserHandle*, Uid const&); +Result IsNetworkServiceAccountAvailable(bool* out, UserHandle const&); +void CloseUser(UserHandle const&); + +Result EnsureNetworkServiceAccountAvailable(UserHandle const& userHandle); +Result EnsureNetworkServiceAccountIdTokenCacheAsync(AsyncContext*, UserHandle const&); +Result LoadNetworkServiceAccountIdTokenCache(u64*, char*, u64, UserHandle const&); + +Result GetLastOpenedUser(Uid*); +Result GetNickname(Nickname* nickname, Uid const& userID); + +Result GetUserId(Uid* uid, const UserHandle& handle); +Result OpenPreselectedUser(UserHandle* handle); + +class AsyncContext { +public: + AsyncContext(); + + Result HasDone(bool*); + Result GetResult(); + Result Cancel(); + Result GetSystemEvent(nn::os::SystemEvent*); +}; +}; // namespace account +}; // namespace nn diff --git a/lib/NintendoSDK/include/nn/aoc.h b/lib/NintendoSDK/include/nn/aoc.h new file mode 100644 index 00000000..623e3fa4 --- /dev/null +++ b/lib/NintendoSDK/include/nn/aoc.h @@ -0,0 +1,9 @@ +#pragma once + +#include + +namespace nn::aoc { + +int ListAddOnContent(int*, int, int); + +} // namespace nn::aoc diff --git a/lib/NintendoSDK/include/nn/atk/SoundArchivePlayer.h b/lib/NintendoSDK/include/nn/atk/SoundArchivePlayer.h new file mode 100644 index 00000000..e8a35a47 --- /dev/null +++ b/lib/NintendoSDK/include/nn/atk/SoundArchivePlayer.h @@ -0,0 +1,37 @@ +/** + * @file SoundArchivePlayer.h + * @brief Basic sound player from a sound archive. + */ + +#pragma once + +#include +#include +#include +#include +#include + +namespace nn { +namespace atk { +class SoundArchivePlayer { +public: + SoundArchivePlayer(); + + virtual ~SoundArchivePlayer(); + + bool IsAvailable() const; + void Finalize(); + void StopAllSound(s32, bool); + void DisposeInstances(); + + nn::atk::detail::SoundArchiveManager mArchiveManager; // _8 + nn::atk::detail::SequenceSoundRuntime mSeqSoundRuntime; // _50 + nn::atk::detail::WaveSoundRuntime mWaveSoundRuntime; // _130 + nn::atk::detail::AdvancedWaveSoundRuntime mAdvancedWaveSound; // _1B0 + nn::atk::detail::StreamSoundRuntime mStreamSoundRuntime; // _1E0 + u64 _290; + u32 _298; + u8 _29C[0x2E8 - 0x29C]; +}; +}; // namespace atk +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/atk/SoundDataManager.h b/lib/NintendoSDK/include/nn/atk/SoundDataManager.h new file mode 100644 index 00000000..f3dbc73d --- /dev/null +++ b/lib/NintendoSDK/include/nn/atk/SoundDataManager.h @@ -0,0 +1,25 @@ +/** + * @file SoundDataManager.h + * @brief Sound data management implementation. + */ + +#pragma once + +#include + +namespace nn { +namespace atk { +class SoundDataManager { +public: + SoundDataManager(); + virtual ~SoundDataManager(); + + virtual void InvalidateData(void const*, void const*); + virtual void SetFileAddressToTable(u32, void const*); + virtual u64 GetFileAddressFromTable(u32) const; + virtual u32 GetFileAddressImpl(u32) const; + + u8 _0[0x240]; +}; +}; // namespace atk +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/atk/SoundPlayer.h b/lib/NintendoSDK/include/nn/atk/SoundPlayer.h new file mode 100644 index 00000000..fc908296 --- /dev/null +++ b/lib/NintendoSDK/include/nn/atk/SoundPlayer.h @@ -0,0 +1,56 @@ +/** + * @file SoundPlayer.h + * @brief Sound player. + */ + +#pragma once + +#include + +namespace nn { +namespace atk { +enum PauseMode { + +}; + +class SoundPlayer { +public: + SoundPlayer(); + ~SoundPlayer(); + + void StopAllSound(s32); + void Update(); + void DoFreePlayerHeap(); + void detail_SortPriorityList(bool); + void PauseAllSound(s32, bool); + void PauseAllSound(bool, s32, nn::atk::PauseMode); + void SetVolume(f32 vol); + void SetLowPassFilterFrequency(f32 filterFreq); + void SetBiquadFilter(s32 filterType, f32 baseFreq); + void SetDefaultOutputLine(u32 line); + + void detail_SetPlayableSoundLimit(s32 limit); + bool CanPlaySound(s32); + + u64 _0; + u64 _8; + u64 _10; + u64 _18; + u64 _20; + u64 _28; + u64 _30; + u64 _38; + s32 _40; + s32 mPlayableSoundCount; // _44 + s32 _48; + f32 mVolume; // _4C + f32 mLowPassFreq; // _50 + s32 mFilterType; // _54 + f32 mBaseFreq; // _58 + u32 mDefaultOutputLine; // _5C + f32 mOutputVolume; // _60 + u64 _64; + u64 _6C; +}; +}; // namespace atk +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/atk/detail/AdvancedWaveSoundRuntime.h b/lib/NintendoSDK/include/nn/atk/detail/AdvancedWaveSoundRuntime.h new file mode 100644 index 00000000..de45e9e1 --- /dev/null +++ b/lib/NintendoSDK/include/nn/atk/detail/AdvancedWaveSoundRuntime.h @@ -0,0 +1,28 @@ +/** + * @file AdvancedWaveSoundRuntime.h + * @brief Runtime wave sound api. + */ + +#pragma once + +#include + +namespace nn { +namespace atk { +namespace detail { +class AdvancedWaveSoundRuntime { +public: + AdvancedWaveSoundRuntime(); + ~AdvancedWaveSoundRuntime(); + + void Initialize(s32, void**, void const*); + void Finalize(); + s32 GetActiveCount() const; + void SetupUserParam(void**, u64); + void Update(); + + u8 _0[0x30]; +}; +}; // namespace detail +}; // namespace atk +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/atk/detail/BasicSound.h b/lib/NintendoSDK/include/nn/atk/detail/BasicSound.h new file mode 100644 index 00000000..1f7667a5 --- /dev/null +++ b/lib/NintendoSDK/include/nn/atk/detail/BasicSound.h @@ -0,0 +1,137 @@ +/** + * @file BasicSound.h + * @brief A basic sound. + */ + +#pragma once + +#include + +namespace nn { +namespace atk { +class SoundActor; + +enum MixMode { + +}; + +namespace detail { +class PlayerHeap; +class ExternalSoundPlayer; + +class BasicSound { +public: + BasicSound(); + virtual ~BasicSound(); + + virtual void Initialize(); + virtual void Finalize(); + virtual bool IsPrepared() const = 0; + virtual bool IsAttachedTempSpecialHandle() = 0; + virtual void DetachTempSpecialHandle() = 0; + virtual void OnUpdatePlayerPriority(); + virtual void UpdateMoveValue(); + virtual void OnUpdateParam(); + + void SetPriority(s32, s32); + void GetPriority(s32*, s32*) const; + void ClearIsFinalizedForCannotAllocatedResourceFlag(); + void SetId(u32 newID); + bool IsAttachedGeneralHandle(); + void DetachGeneralHandle(); + bool IsAttachedTempGeneralHandle(); + void DetachTempGeneralHandle(); + void StartPrepared(); + void Stop(s32); + void SetPlayerPriority(s32); + void ForceStop(); + void Pause(bool, s32); + void Mute(bool, s32); + void SetAutoStopCounter(s32); + void FadeIn(s32); + bool IsPause() const; + bool IsMute() const; + void Update(); + void UpdateParam(); + void UpdateMoveValue(); + void CalculateVolume() const; + f32 CalculatePitch() const; + f32 CalculateLpfFrequency() const; + u32 CalculateOutLineFlag() const; + void CalculateBiquadFilter(s32*, f32*) const; + void AttachPlayerHeap(nn::atk::detail::PlayerHeap*); + void DetachPlayerHeap(nn::atk::detail::PlayerHeap*); + void AttachSoundPlayer(nn::atk::SoundPlayer*); + void DetachSoundPlayer(nn::atk::SoundPlayer*); + void AttachSoundActor(nn::atk::SoundActor*); + void DetachSoundActor(nn::atk::SoundActor*); + void AttachExternalSoundPlayer(nn::atk::detail::ExternalSoundPlayer*); + void DetachExternalSoundPlayer(nn::atk::detail::ExternalSoundPlayer*); + u32 GetRemainingFadeFrames() const; + u32 GetRemainingPauseFadeFrames() const; + u32 GetRemainingMuteFadeFrames() const; + void SetInitialVolume(f32 vol); + f32 GetInitialVolume() const; + void SetVolume(f32, s32); + s32 GetVolume() const; + void SetPitch(f32); + f32 GetPitch() const; + void SetLpfFreq(f32); + f32 GetLpfFreq() const; + void SetBiquadFilter(s32, f32); + void GetBiquadFilter(s32*, f32*) const; + void SetOutputLine(u32); + u32 GetOutputLine() const; + void ResetOutputLine(); + void SetMixMode(nn::atk::MixMode); + nn::atk::MixMode GetMixMode(); + void SetPan(f32); + f32 GetPan() const; + void SetSurroundPan(f32); + f32 GetSurroundPan() const; + void SetMainSend(f32); + f32 GetMainSend() const; + + u64* _8; // nn::atk::detail::PlayerHeap* + u64* _10; // nn::atk::SoundHandle* + u64* _18; // nn::atk::SoundHandle* + nn::atk::SoundPlayer* mSoundPlayer; // _20 + u64* _28; // nn::atk::SoundActor* + u64* _30; // nn::atk::detail::ExternalSoundPlayer* + u64* _38; // nn::atk::SoundArchive* + u8 _40[0xF0 - 0x40]; + s32 mPriority; // _F0 + u32 _F4; + u32 _F8; + s32 mAutoStopCounter; // _FC + u64 _100; + u32 mID; // _108 + u32 _10C; + u32 _110; + u32 _114; + f32 mInitialVolume; // _118 + f32 mPitch; // _11C + f32 mLpfFreq; // _120 + f32 _124; + u32 mOutputLine; // _128 + f32 _12C; + f32 mVolume; // _130 + u32 _134; + u32 _138; + nn::atk::MixMode mMixMode; // _13C + f32 mPan; // _140 + f32 mSurroundPan; // _144 + f32 mMainSend; // _148 + u8 _14C[0x158 - 0x14C]; + f32 mOutputVol; // _158 + u8 _15C[0x190 - 0x15C]; + f32 mOutputPan; // _190 + f32 mOutputSurroundPan; // _194 + f32 mOutputMainSend; // _198 + f32 mOutputFxSend; // _19C + + static u64 g_LastInstanceId; +}; +}; // namespace detail +}; // namespace atk +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/atk/detail/SequenceSoundRuntime.h b/lib/NintendoSDK/include/nn/atk/detail/SequenceSoundRuntime.h new file mode 100644 index 00000000..c4d23ae5 --- /dev/null +++ b/lib/NintendoSDK/include/nn/atk/detail/SequenceSoundRuntime.h @@ -0,0 +1,37 @@ +/** + * @file SequenceSoundRuntime.h + * @brief Sequenced Sound Runtime Info + */ + +#pragma once + +#include + +namespace nn { +namespace atk { +namespace detail { +class SoundArchiveManager; + +class SequenceSoundRuntime { +public: + SequenceSoundRuntime(); + ~SequenceSoundRuntime(); + + void Initialize(s32, void**, void const*); + void Finalize(); + void SetupSequenceTrack(s32, void**, void const*); + void SetupUserParam(void**, u64); + bool IsSoundArchiveAvailable() const; + s32 GetActiveCount() const; + s32 GetFreeCount() const; + void SetSequenceSkipIntervalTick(s32 tick); + s32 GetSequenceSkipIntervalTick(); + void Update(); + + u8 _0[0xD0]; + nn::atk::detail::SoundArchiveManager* mArchiveManager; // _D0 + u64 _D8; +}; +}; // namespace detail +}; // namespace atk +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/atk/detail/SoundArchiveManager.h b/lib/NintendoSDK/include/nn/atk/detail/SoundArchiveManager.h new file mode 100644 index 00000000..0aa50668 --- /dev/null +++ b/lib/NintendoSDK/include/nn/atk/detail/SoundArchiveManager.h @@ -0,0 +1,42 @@ +/** + * @file SoundArchiveManager.h + * @brief Sound archive manager implementation. + */ + +#pragma once + +#include + +namespace nn { +namespace atk { +class SoundHandle; +class SoundArchive; +class SoundDataManager; + +namespace detail { +class AddonSoundArchiveContainer; + +class SoundArchiveManager { +public: + SoundArchiveManager(); + + virtual ~SoundArchiveManager(); + + void Initialize(nn::atk::SoundArchive const*, nn::atk::SoundDataManager const*); + void ChangeTargetArchive(char const*); + void Finalize(); + bool IsAvailable() const; + nn::atk::detail::AddonSoundArchiveContainer* GetAddonSoundArchive(char const*) const; + + u64 _8; + u64* _10; + nn::atk::detail::AddonSoundArchiveContainer* _18; + u64* _20; + nn::atk::SoundArchive* mSoundArchive; // _28 + u64 _30; + u64 _38; + u64 _40; +}; +}; // namespace detail +}; // namespace atk +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/atk/detail/StreamSoundRuntime.h b/lib/NintendoSDK/include/nn/atk/detail/StreamSoundRuntime.h new file mode 100644 index 00000000..11a24d61 --- /dev/null +++ b/lib/NintendoSDK/include/nn/atk/detail/StreamSoundRuntime.h @@ -0,0 +1,22 @@ +/** + * @file StreamSoundRuntime.h + * @brief Stream sound runtime information. + */ + +#pragma once + +#include + +namespace nn { +namespace atk { +namespace detail { +class StreamSoundRuntime { +public: + StreamSoundRuntime(); + ~StreamSoundRuntime(); + + u8 _0[0xB0]; +}; +}; // namespace detail +}; // namespace atk +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/atk/detail/WaveSoundRuntime.h b/lib/NintendoSDK/include/nn/atk/detail/WaveSoundRuntime.h new file mode 100644 index 00000000..501d50a3 --- /dev/null +++ b/lib/NintendoSDK/include/nn/atk/detail/WaveSoundRuntime.h @@ -0,0 +1,29 @@ +/** + * @file WaveSoundRuntime.h + * @brief Wave sound runtime info. + */ + +#pragma once + +#include + +namespace nn { +namespace atk { +namespace detail { +class WaveSoundRuntime { +public: + WaveSoundRuntime(); + ~WaveSoundRuntime(); + + void Initialize(s32, void**, void const*); + void Finalize(); + s32 GetActiveCount() const; + s32 GetFreeWaveSoundCount() const; + void SetupUserParam(void**, u64); + void Update(); + + u8 _0[0x80]; +}; +}; // namespace detail +}; // namespace atk +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/audio.h b/lib/NintendoSDK/include/nn/audio.h new file mode 100644 index 00000000..e45e1358 --- /dev/null +++ b/lib/NintendoSDK/include/nn/audio.h @@ -0,0 +1,344 @@ +/** + * @file audio.h + * @brief Audio implementation. + */ + +#pragma once + +#include +#include + +namespace nn { +namespace audio { +// Common audio +struct AudioDeviceName { + char raw_name[0x100]; +}; + +static_assert(sizeof(AudioDeviceName) == 0x100); + +void AcquireAudioDeviceSwitchNotification(nn::os::SystemEvent* event); +s32 ListAudioDeviceName(nn::audio::AudioDeviceName* buffer, s32 bufferCount); +Result SetAudioDeviceOutputVolume(nn::audio::AudioDeviceName const* device, float volume); +u32 GetActiveChannelCount(); + +struct AudioRendererConfig { + u64* _0; + u64* _8; + u64* _10; + u64* _18; + u64* _20; + u64* _28; + u64* _30; + u64* _38; + u64* _40; + u64* _48; + u64* _50; +}; + +enum AudioRendererRenderingDevice : u32 { + AudioRendererRenderingDevice_Cpu, + AudioRendererRenderingDevice_Dsp +}; + +enum AudioRendererExecutionMode : u32 { + AudioRendererExecutionMode_Manual, + AudioRendererExecutionMode_Auto, +}; + +enum SampleFormat : u32 { + SampleFormat_Invalid, + SampleFormat_PcmInt8, + SampleFormat_PcmInt16, + SampleFormat_PcmInt24, + SampleFormat_PcmInt32, + SampleFormat_PcmFloat, + SampleFormat_Adpcm, +}; + +enum MemoryPoolState : u32 { + MemoryPoolState_Invalid, + MemoryPoolState_New, + MemoryPoolState_RequestDetach, + MemoryPoolState_Detached, + MemoryPoolState_RequestAttach, + MemoryPoolState_Attached, + MemoryPoolState_Released, +}; + +struct AudioRendererParameter { + u32 sampleRate; + u32 sampleCount; + u32 mixBufferCount; + u32 subMixCount; + u32 voiceCount; + u32 sinkCount; + u32 effectCount; + u32 performanceFrameCount; + bool isVoiceDropEnabled; + u32 splitterCount; + u32 splitterSendChannelCount; + AudioRendererRenderingDevice renderingDevice; + AudioRendererExecutionMode executionMode; + u32 _34; + u32 revision; +}; + +static_assert(sizeof(AudioRendererParameter) == 0x3C); + +struct BiquadFilterParameter { + bool enabled; + s16 numerator[3]; + s16 denominator[2]; +}; + +static_assert(sizeof(BiquadFilterParameter) == 0xC); + +struct WaveBuffer { + void* buffer; + size_t bufferSize; + s32 startSampleOffset; + s32 endSampleOffset; + bool shouldLoop; + bool isEndOfStream; + void* context; + size_t contextSize; +}; + +static_assert(sizeof(WaveBuffer) == 0x30); + +struct AudioRendererHandle { + u64* _0; + u64* _8; +}; + +struct MemoryPoolType { + u64* _0; +}; + +struct CircularBufferSinkType { + u64* _0; +}; + +struct AuxType { + u64* _0; +}; + +struct DelayType { + u64* _0; +}; + +struct FinalMixType { + u64* _0; +}; + +struct SubMixType { + u64* _0; +}; + +struct VoiceType { + u64* _0; + + enum PlayState : u32 { + PlayState_Start, + PlayState_Stop, + PlayState_Pause, + }; +}; + +struct DeviceSinkType { + u64* _0; +}; + +// Audio Renderer base APIs +void InitializeAudioRendererParameter(nn::audio::AudioRendererParameter* inParameter); +bool IsValidAudioRendererParameter(nn::audio::AudioRendererParameter const& inParameter); +size_t GetAudioRendererWorkBufferSize(nn::audio::AudioRendererParameter const& inParameter); +size_t GetAudioRendererConfigWorkBufferSize(nn::audio::AudioRendererParameter const& inParameter); +Result InitializeAudioRendererConfig(nn::audio::AudioRendererConfig* outConfig, + nn::audio::AudioRendererParameter const& inParameter, + void* buffer, size_t bufferSize); +Result OpenAudioRenderer(nn::audio::AudioRendererHandle* outHandle, + nn::audio::AudioRendererParameter const& inParameter, void* workBuffer, + size_t workBufferSize); +void CloseAudioRenderer(nn::audio::AudioRendererHandle handle); +Result StartAudioRenderer(nn::audio::AudioRendererHandle handle); +Result StopAudioRenderer(nn::audio::AudioRendererHandle handle); +Result RequestUpdateAudioRenderer(nn::audio::AudioRendererHandle handle, + nn::audio::AudioRendererConfig const* config); + +// Audio Renderer MemoryPool APIs +bool IsMemoryPoolAttached(nn::audio::MemoryPoolType const* pool); +bool RequestAttachMemoryPool(nn::audio::MemoryPoolType* pool); +bool RequestDetachMemoryPool(nn::audio::MemoryPoolType* pool); +bool AcquireMemoryPool(nn::audio::AudioRendererConfig* config, nn::audio::MemoryPoolType* outPool, + void* address, size_t size); +void ReleaseMemoryPool(nn::audio::AudioRendererConfig* config, nn::audio::MemoryPoolType* pool); +void* GetMemoryPoolAddress(nn::audio::MemoryPoolType const* pool); +size_t GetMemoryPoolSize(nn::audio::MemoryPoolType const* pool); +MemoryPoolState GetMemoryPoolState(nn::audio::MemoryPoolType const* pool); + +// Audio Renderer Effect APIs +void SetDelayInputOutput(nn::audio::DelayType* delay, s8 const* input, s8 const* output, s32 count); +void* RemoveDelay(nn::audio::AudioRendererConfig* config, nn::audio::DelayType* delay, + nn::audio::FinalMixType* mix); +void* RemoveDelay(nn::audio::AudioRendererConfig* config, nn::audio::DelayType* delay, + nn::audio::SubMixType* mix); +bool IsDelayRemovable(nn::audio::DelayType* delay); + +size_t GetRequiredBufferSizeForAuxSendReturnBuffer(nn::audio::AudioRendererParameter const* config, + s32 mixBufferFrameCount, s32 channelCount); +Result AddAux(nn::audio::AudioRendererConfig* config, nn::audio::AuxType* aux, + nn::audio::FinalMixType* mix, void* sendBuffer, void* returnBuffer, + size_t bufferSize); +Result AddAux(nn::audio::AudioRendererConfig* config, nn::audio::AuxType* aux, + nn::audio::SubMixType* mix, void* sendBuffer, void* returnBuffer, size_t bufferSize); +void RemoveAux(nn::audio::AudioRendererConfig* config, nn::audio::AuxType* aux, + nn::audio::FinalMixType* mix); +void RemoveAux(nn::audio::AudioRendererConfig* config, nn::audio::AuxType* aux, + nn::audio::SubMixType* mix); +void SetAuxEnabled(nn::audio::AuxType* aux, bool enable); +void SetAuxInputOutput(nn::audio::AuxType* aux, s8 const* input, s8 const* output, s32 count); +bool IsAuxRemovable(nn::audio::AuxType* aux); +s32 GetAuxSampleCount(nn::audio::AuxType const* aux); +s32 GetAuxSampleRate(nn::audio::AuxType const* aux); +s32 ReadAuxSendBuffer(nn::audio::AuxType* aux, s32* buffer, s32 count); +s32 WriteAuxReturnBuffer(nn::audio::AuxType* aux, s32 const* buffer, s32 count); + +// Audio Renderer Performance APIs +size_t +GetRequiredBufferSizeForPerformanceFrames(nn::audio::AudioRendererParameter const& inParameter); +void* SetPerformanceFrameBuffer(nn::audio::AudioRendererConfig* config, void* buffer, + size_t bufferSize); + +enum PerformanceEntryType : u8 { + PerformanceEntryType_Invalid, + PerformanceEntryType_Voice, + PerformanceEntryType_SubMix, + PerformanceEntryType_FinalMix, + PerformanceEntryType_Sink +}; + +struct PerformanceEntry { + s32 nodeId; + s32 startTime; + s32 processingTime; + PerformanceEntryType entryType; +}; + +static_assert(sizeof(PerformanceEntry) == 0x10); + +enum PerformanceDetailType : u8 { + PerformanceDetailType_Unknown, + PerformanceDetailType_PcmInt16, + PerformanceDetailType_Adpcm, + PerformanceDetailType_VolumeRamp, + PerformanceDetailType_BiquadFilter, + PerformanceDetailType_Mix, + PerformanceDetailType_Delay, + PerformanceDetailType_Aux, + PerformanceDetailType_Reverb, + PerformanceDetailType_Reverb3d, + PerformanceDetailType_PcmFloat +}; + +struct PerformanceDetail { + s32 nodeId; + s32 startTime; + s32 processingTime; + PerformanceDetailType detailType; + PerformanceEntryType entryType; +}; + +static_assert(sizeof(PerformanceDetail) == 0x10); + +class PerformanceInfo { +public: + PerformanceInfo(); + ~PerformanceInfo(); + + bool SetBuffer(void const* buffer, size_t bufferSize); + bool MoveToNextFrame(); + s32 GetTotalProcessingTime(); + PerformanceEntry GetEntries(s32* count); + PerformanceDetail GetDetails(s32* count); + +private: + void* buffer; + size_t bufferSize; + void* header; + PerformanceEntry* entries; + PerformanceDetail* details; +}; + +static_assert(sizeof(PerformanceInfo) == 0x28); + +// Audio Renderer Sink APIs +Result AddDeviceSink(nn::audio::AudioRendererConfig* config, nn::audio::DeviceSinkType* sink, + nn::audio::FinalMixType* mix, s8 const* input, s32 inputCount, + char const* deviceName); +void RemoveDeviceSink(nn::audio::AudioRendererConfig* config, nn::audio::DeviceSinkType* sink, + nn::audio::FinalMixType* mix); +u32 GetSinkNodeId(nn::audio::DeviceSinkType const* sink); + +Result AddCircularBufferSink(nn::audio::AudioRendererConfig* config, + nn::audio::CircularBufferSinkType* sink, nn::audio::FinalMixType* mix, + s8 const* input, s32 inputCount, void* buffer, size_t bufferSize, + nn::audio::SampleFormat sampleFormat); +void RemoveCircularBufferSink(nn::audio::AudioRendererConfig* config, + nn::audio::CircularBufferSinkType* sink, + nn::audio::FinalMixType* mix); +size_t ReadCircularBufferSink(nn::audio::CircularBufferSinkType* sink, void* buffer, + size_t buffer_size); +u32 GetSinkNodeId(nn::audio::CircularBufferSinkType const* sink); +size_t +GetRequiredBufferSizeForCircularBufferSink(nn::audio::AudioRendererParameter const* inParameter, + s32 inputCount, s32 frameCount, + nn::audio::SampleFormat sampleFormat); + +// Audio Renderer Mix APIs +bool AcquireFinalMix(nn::audio::AudioRendererConfig* config, nn::audio::FinalMixType* mix, + s32 bufferCount); +bool AcquireSubMix(nn::audio::AudioRendererConfig* config, nn::audio::SubMixType* mix, + s32 sampleRate, s32 bufferCount); +void ReleaseSubMix(nn::audio::AudioRendererConfig* config, nn::audio::SubMixType* mix); +void SetSubMixDestination(nn::audio::AudioRendererConfig* config, nn::audio::SubMixType* source, + nn::audio::FinalMixType* destination); +void SetSubMixDestination(nn::audio::AudioRendererConfig* config, nn::audio::SubMixType* source, + nn::audio::SubMixType* destination); +void SetSubMixMixVolume(nn::audio::SubMixType* source, nn::audio::FinalMixType* destination, + float volume, s32 sourceIndex, s32 destinationIndex); +void SetSubMixMixVolume(nn::audio::SubMixType* source, nn::audio::SubMixType* destination, + float volume, s32 sourceIndex, s32 destinationIndex); +u32 GetSubMixNodeId(nn::audio::SubMixType const* mix); + +// Audio Renderer Voice APIs +Result AcquireVoiceSlot(nn::audio::AudioRendererConfig* config, nn::audio::VoiceType* voice, + s32 sampleRate, s32 channelCount, nn::audio::SampleFormat sampleFormat, + s32 priority, void const* buffer, size_t bufferSize); +void ReleaseVoiceSlot(nn::audio::AudioRendererConfig* config, nn::audio::VoiceType* voice); +bool IsVoiceValid(nn::audio::VoiceType const* voice); +bool IsVoiceDroppedFlagOn(nn::audio::VoiceType const* voice); +void ResetVoiceDroppedFlag(nn::audio::VoiceType* voice); +void SetVoiceDestination(nn::audio::AudioRendererConfig* config, nn::audio::VoiceType* voice, + nn::audio::FinalMixType* mix); +void SetVoiceDestination(nn::audio::AudioRendererConfig* config, nn::audio::VoiceType* voice, + nn::audio::SubMixType* mix); +void SetVoiceVolume(nn::audio::VoiceType* config, float volume); +void SetVoicePitch(nn::audio::VoiceType* config, float pitch); +void SetVoicePlayState(nn::audio::VoiceType* voice, nn::audio::VoiceType::PlayState state); +void SetVoicePriority(nn::audio::VoiceType* voice, s32 priority); +void SetVoiceBiquadFilterParameter(nn::audio::VoiceType* voice, s32 index, + nn::audio::BiquadFilterParameter const& biquadFilterParameter); +void SetVoiceMixVolume(nn::audio::VoiceType* voice, nn::audio::FinalMixType* mix, float volume, + int sourceIndex, int destinationIndex); +void SetVoiceMixVolume(nn::audio::VoiceType* voice, nn::audio::SubMixType* mix, float volume, + int sourceIndex, int destinationIndex); +nn::audio::VoiceType::PlayState GetVoicePlayState(nn::audio::VoiceType const* voice); +s32 GetVoicePriority(nn::audio::VoiceType const* voice); +u64 GetVoicePlayedSampleCount(nn::audio::VoiceType const* voice); +u32 GetVoiceNodeId(nn::audio::VoiceType const* voice); +bool AppendWaveBuffer(nn::audio::VoiceType* voice, nn::audio::WaveBuffer const* waveBuffer); +nn::audio::WaveBuffer* GetReleasedWaveBuffer(nn::audio::VoiceType* voice); +}; // namespace audio +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/bcat.h b/lib/NintendoSDK/include/nn/bcat.h new file mode 100644 index 00000000..a47c06c0 --- /dev/null +++ b/lib/NintendoSDK/include/nn/bcat.h @@ -0,0 +1,112 @@ +/** + * @file bcat.h + * @brief BCAT service implementation. + */ + +#pragma once + +#include +#include + +namespace nn { + +namespace bcat { + +struct DirectoryName { + void isValid(); +}; + +struct FileName { + void isValid(); +}; + +class DeliveryCacheDirectory { +public: + DeliveryCacheDirectory(); + ~DeliveryCacheDirectory(); + Result Open(nn::bcat::DirectoryName const&); + Result GetCount(); + Result Close(); +}; + +class DeliveryCacheFile { +public: + DeliveryCacheFile(); + ~DeliveryCacheFile(); + Result Open(nn::bcat::DirectoryName const&, nn::bcat::FileName const&); + Result Read(size_t file1, s64, void*, size_t file2); + Result GetSize(); + Result GetDigest(); + Result Close(); +}; + +class DeliveryCacheProgress { +public: + DeliveryCacheProgress(); + ~DeliveryCacheProgress(); + Result Detach(); + Result Update(); + Result GetStatus(); + Result GetCurrentDirectoryName(); + Result GetCurrentFileName(); + Result GetCurrentDownloaded(); + Result GetCurrentTotale(); + Result GetWholeDownloaded(); + Result GetWholeTotal(); + Result GetResult(); + // void Attach(nn::bcat::detail::ipc::IDeliveryCacheProgressService*); +}; + +namespace detail { + +namespace DeliveryCacheProgressImpl { +Result Clear(); +Result NotifyStartConnect(); +Result NotifyStartProcessList(); +Result SetWholeDownloadSize(s64); +Result SetDownloadProgress(s64, nn::bcat::DirectoryName const&, nn::bcat::FileName const&, s64); +Result NotifyStartDownloadFile(nn::bcat::DirectoryName const&, nn::bcat::FileName const&, s64); +Result UpdateDownloadFileProgress(s64); +Result NotifyStartCommitDirectory(nn::bcat::DirectoryName const&); +Result NotifyDone(nn::Result); + +} // namespace DeliveryCacheProgressImpl +class ShimLibraryGlobal { +public: + ShimLibraryGlobal(); + ~ShimLibraryGlobal(); + Result Initialize(); + Result GetSession(); + Result MountDeliveryCacheStorage(); + Result IsDeliveryCacheStorageMounted(); + Result UnmountDeliveryCacheStorage(); + // void CreateFileService(nn::bcat::detail::ipc::IDeliveryCacheFileService**); + // void CreateDirectoryService(nn::bcat::detail::ipc::IDeliveryCacheDirectoryService**) + Result IncrementDeliveryCacheFileCount(); + Result DecrementDeliveryCacheFileCount(); + Result IncrementDeliveryCacheDirectoryCount(); + Result DecrementDeliveryCacheFileCount(); + Result EnumerateDeliveryCacheDirectory(int*, nn::bcat::DirectoryName*, int); +}; + +namespace ipc { +Result Initialize(); +// void CreateBcatService(nn::bcat::detail::ipc::IBcatService**); +Result Finalize(); +// void CreateBcatService(nn::bcat::detail::ipc::IBcatService**); +// void CreateDeliveryCacheStorageService(nn::bcat::detail::ipc::IDeliveryCacheStorageService**); +// void CreateDeliveryCacheStorageService(nn::bcat::detail::ipc::IDeliveryCacheStorageService**, +// nn::ApplicationId); + +} // namespace ipc +} // namespace detail + +Result Initialize(); +Result MountDeliveryCacheStorage(); +Result UnmountDeliveryCacheStorage(); +Result EnumerateDeliveryCacheDirectory(int*, nn::bcat::DirectoryName*, int); +Result RequestSyncDeliveryCache(nn::bcat::DeliveryCacheProgress*); +Result EnumerateDeliveryCacheDirectory(int*, nn::bcat::DirectoryName*, int); + +} // namespace bcat +} // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/crypto.h b/lib/NintendoSDK/include/nn/crypto.h new file mode 100644 index 00000000..872bb0cf --- /dev/null +++ b/lib/NintendoSDK/include/nn/crypto.h @@ -0,0 +1,86 @@ +/** + * @file crypto.h + * @brief Crypto service implementation. + */ + +#pragma once + +#include + +namespace nn { +namespace crypto { +void GenerateSha256Hash(void*, ulong, void const*, ulong); + +class Sha256Context; + +void DecryptAes128Cbc(void*, u64, void const*, u64, void const*, u64, void const*, u64); +void EncryptAes128Cbc(void*, u64, void const*, u64, void const*, u64, void const*, u64); +void DecryptAes128Ccm(void*, u64, void*, u64, void const*, u64, void const*, u64, void const*, u64, + void const*, u64, u64); + +namespace detail { +class Md5Impl { +public: + void Initialize(); + void Update(void const*, u64 dataSize); + void ProcessBlock(); + void GetHash(void*, u64 hashSize); + void ProcessLastBlock(); + + u32 _x0; + u32 _x4; + u32 _x8; + u32 _xC; + u8 _x10[0x50 - 0x10]; + u64 _x50; + u32 _x58; +}; + +class Sha1Impl { +public: + void Initialize(); + void Update(void const*, u64); + void ProcessBlock(void const*); + void GetHash(void* destHash, u64); + void ProcessLastBlock(); + + u64 _x0; + u64 _x8; + u32 _x10; + u128 _x14; + u128 _x24; + u128 _x34; + u32 _x44; + u64 _x48; + u64 _x50; + u64 _x58; + u64 _x60; +}; + +class Sha256Impl { +public: + void Initialize(); + void Update(void const*, u64); + void ProcessBlocks(u8 const*, u64); + void GetHash(void* destHash, u64); + void ProcessLastBlock(); + void InitializeWithContext(nn::crypto::Sha256Context const*); + void GetContext(nn::crypto::Sha256Context*) const; + + u64 _x0; + u64 _x8; + u32 _x10; + u128 _x14; + u128 _x24; + u128 _x34; + u32 _x44; + u64 _x48; + u64 _x50; + u64 _x58; + u64 _x60; + u64 _x68; + u32 _x70; +}; +}; // namespace detail +}; // namespace crypto +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/diag.h b/lib/NintendoSDK/include/nn/diag.h new file mode 100644 index 00000000..a2791a90 --- /dev/null +++ b/lib/NintendoSDK/include/nn/diag.h @@ -0,0 +1,33 @@ +/** + * @file diag.h + * @brief Module, logging, and symbol operations. + */ + +#pragma once + +#include + +namespace nn { +namespace diag { +struct LogMetaData; + +struct ModuleInfo { + char* mPath; + u64 mBaseAddr; + u64 mSize; +}; + +namespace detail { +// LOG +void LogImpl(nn::diag::LogMetaData const&, char const*, ...); +void AbortImpl(char const*, char const*, char const*, s32); +void AbortImpl(char const*, char const*, char const*, int, Result); +}; // namespace detail + +// MODULE / SYMBOL +u32* GetSymbolName(char* name, u64 nameSize, u64 addr); +u64 GetRequiredBufferSizeForGetAllModuleInfo(); +s32 GetAllModuleInfo(nn::diag::ModuleInfo** out, void* buffer, u64 bufferSize); +u64 GetSymbolSize(u64 addr); +}; // namespace diag +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/err.h b/lib/NintendoSDK/include/nn/err.h new file mode 100644 index 00000000..1635bb02 --- /dev/null +++ b/lib/NintendoSDK/include/nn/err.h @@ -0,0 +1,31 @@ +#pragma once + +#include + +namespace nn { +namespace err { +enum ErrorCodeCategoryType : u32 { + unk1, + unk2, +}; + +class ApplicationErrorArg { +public: + ApplicationErrorArg(); + ApplicationErrorArg(u32 error_code, const char* dialog_message, const char* fullscreen_message, + const nn::settings::LanguageCode& languageCode); + void SetApplicationErrorCodeNumber(u32 error_code); + void SetDialogMessage(const char* message); + void SetFullScreenMessage(const char* message); + + u64 unk; + u32 error_code; + nn::settings::LanguageCode language_code; + char dialog_message[2048]; + char fullscreen_message[2048]; +}; + +u32 MakeErrorCode(ErrorCodeCategoryType err_category_type, u32 errorCodeNumber); +void ShowApplicationError(const ApplicationErrorArg& arg); +} // namespace err +} // namespace nn diff --git a/lib/NintendoSDK/include/nn/friends.h b/lib/NintendoSDK/include/nn/friends.h new file mode 100644 index 00000000..e8c097b1 --- /dev/null +++ b/lib/NintendoSDK/include/nn/friends.h @@ -0,0 +1,42 @@ +/** + * @file friends.h + * @brief Friend implementation. + */ + +#pragma once + +#include +#include + +namespace nn { +namespace friends { +typedef char Url[0xA0]; + +class AsyncContext; +class Profile; + +void Initialize(); +Result GetProfileList(nn::friends::AsyncContext* context, nn::friends::Profile* profiles, + nn::account::Uid const& userID, + nn::account::NetworkServiceAccountId const* accountIDs, s32 numAccounts); + +class Profile { +public: + Profile(); + + nn::account::NetworkServiceAccountId GetAccountId() const; + nn::account::Nickname& GetNickname() const; + bool IsValid() const; + Result GetProfileImageUrl(nn::friends::Url*, s32); +}; + +class AsyncContext { +public: + AsyncContext(); + ~AsyncContext(); + + Result GetSystemEvent(nn::os::SystemEvent*); + Result GetResult() const; +}; +}; // namespace friends +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/fs.h b/lib/NintendoSDK/include/nn/fs.h new file mode 100644 index 00000000..9e60bca9 --- /dev/null +++ b/lib/NintendoSDK/include/nn/fs.h @@ -0,0 +1,132 @@ +/** + * @file fs.h + * @brief Filesystem implementation. + */ + +#pragma once + +#include +#include + +namespace nn { +typedef u64 ApplicationId; + +namespace fs { +using namespace ams::fs; + +typedef u64 UserId; + +struct DirectoryEntry { + char name[0x300 + 1]; + char _x302[3]; + u8 type; + char _x304; + s64 fileSize; +}; + +struct FileHandle { + void* handle; +}; + +struct DirectoryHandle { + void* handle; +}; + +enum DirectoryEntryType { DirectoryEntryType_Directory, DirectoryEntryType_File }; + +enum OpenMode { + OpenMode_Read = 1 << 0, + OpenMode_Write = 1 << 1, + OpenMode_Append = 1 << 2, + + OpenMode_ReadWrite = OpenMode_Read | OpenMode_Write +}; + +enum OpenDirectoryMode { + OpenDirectoryMode_Directory = 1 << 0, + OpenDirectoryMode_File = 1 << 1, + OpenDirectoryMode_All = OpenDirectoryMode_Directory | OpenDirectoryMode_File, +}; + +struct ReadOption { + u32 value; + + static const ReadOption None; +}; +inline constexpr const ReadOption ReadOption::None = {0}; + +enum WriteOptionFlag { + WriteOptionFlag_Flush = 1 << 0, +}; + +struct WriteOption { + int flags; + + static WriteOption CreateOption(int flags) { + WriteOption op; + op.flags = flags; + return op; + } +}; + +// ROM +Result QueryMountRomCacheSize(size_t* size); +Result QueryMountRomCacheSize(size_t* size, nn::ApplicationId); +Result QueryMountAddOnContentCacheSize(size_t* size, int id); +Result MountRom(char const* name, void* cache, size_t cache_size); +Result MountAddOnContent(char const* name, int id, void* cache, size_t cache_size); +bool CanMountRomForDebug(); +Result CanMountRom(nn::ApplicationId); +Result QueryMountRomOnFileCacheSize(u64*, nn::fs::FileHandle); +Result MountRomOnFile(char const*, nn::fs::FileHandle, void*, u64); + +// SAVE +Result EnsureSaveData(nn::account::Uid const&); +Result MountSaveData(char const*, nn::fs::UserId); +Result MountSaveDataForDebug(char const*); +Result CommitSaveData(const char* path); + +// FILE +Result GetEntryType(nn::fs::DirectoryEntryType* type, char const* path); +Result CreateFile(char const* filepath, s64 size); +Result OpenFile(nn::fs::FileHandle*, char const* path, s32); +Result SetFileSize(FileHandle fileHandle, s64 filesize); +void CloseFile(FileHandle fileHandle); +Result FlushFile(FileHandle fileHandle); +Result DeleteFile(char const* filepath); +Result ReadFile(u64* outSize, nn::fs::FileHandle handle, s64 offset, void* buffer, u64 bufferSize, + const ReadOption& option); +Result ReadFile(u64* outSize, nn::fs::FileHandle handle, s64 offset, void* buffer, u64 bufferSize); +Result ReadFile(nn::fs::FileHandle handle, s64 offset, void* buffer, u64 bufferSize); +Result WriteFile(FileHandle handle, s64 fileOffset, void const* buff, u64 size, + WriteOption const& option); +Result GetFileSize(s64* size, FileHandle fileHandle); + +// DIRECTORY +// there are three open modes; dir, file, all +Result OpenDirectory(DirectoryHandle* handle, char const* path, s32 openMode); +void CloseDirectory(DirectoryHandle directoryHandle); +Result ReadDirectory(s64*, DirectoryEntry*, DirectoryHandle directoryHandle, s64); +Result CreateDirectory(char const* directorypath); +Result GetDirectoryEntryCount(s64*, DirectoryHandle); + +// SD +Result MountSdCard(char const*); +Result MountSdCardForDebug(char const*); +bool IsSdCardInserted(); +Result FormatSdCard(); +Result FormatSdCardDryRun(); +bool IsExFatSupported(); + +Result MountHost(char const* mount, char const* path); +Result MountHostRoot(); +Result UnmountHostRoot(); + +Result Unmount(char const* mount); + +// BCAT +Result MountBcatSaveData(char const*, ApplicationId); +Result CreateBcatSaveData(ApplicationId, s64); + +}; // namespace fs +}; // namespace nn diff --git a/lib/NintendoSDK/include/nn/g3d/BindFuncTable.h b/lib/NintendoSDK/include/nn/g3d/BindFuncTable.h new file mode 100644 index 00000000..3f0da76d --- /dev/null +++ b/lib/NintendoSDK/include/nn/g3d/BindFuncTable.h @@ -0,0 +1,31 @@ +#pragma once + +#include + +namespace nn { +namespace g3d { +struct DDLDeclarations { + u64 _0; + u32 _8; + u32 DDLDeclarations_xC; + u64 _10; + u64 _18; +}; + +class BindFuncTable { + struct StringLength { + size_t length; + const char* content; + }; + struct EntryPointer { + void* something_0; + nn::g3d::BindFuncTable::StringLength* string; + }; + +private: + int lengths[4]; + nn::g3d::BindFuncTable::EntryPointer strings[4]; +}; + +}; // namespace g3d +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/g3d/ResFile.h b/lib/NintendoSDK/include/nn/g3d/ResFile.h new file mode 100644 index 00000000..ed7c865c --- /dev/null +++ b/lib/NintendoSDK/include/nn/g3d/ResFile.h @@ -0,0 +1,75 @@ +/** + * @file ResFile.h + * @brief Resource file for models. + */ + +#pragma once + +#include +#include +#include +#include + +namespace nn { + +namespace gfx { +template +class TDevice; +} + +namespace g3d { +class ResModel; +class ResMaterialAnim; +class ResShapeAnim; +class ResSceneAnim; +typedef void* TextureRef; + +class ResFile : public nn::util::BinaryFileHeader { +public: + static bool IsValid(void const* modelSrc); + void Relocate(); + void Unrelocate(); + static nn::g3d::ResFile* ResCast(void*); + s32 BindTexture(nn::g3d::TextureRef (*ref)(char const*, void*), void*); + void ReleaseTexture(); + void + Setup(nn::gfx::TDevice, nn::gfx::ApiVersion<8>>>*); + void + Setup(nn::gfx::TDevice, nn::gfx::ApiVersion<8>>>*, + nn::gfx::TMemoryPool, nn::gfx::ApiVersion<8>>>*, + s64, u64); + void + Cleanup(nn::gfx::TDevice, nn::gfx::ApiVersion<8>>>*); + void Reset(); + + u64 mFileNameLength; // _20 + nn::g3d::ResModel* mModels; // _28 + u64 mModelDictOffset; // _30 + u64 mSkeleAnimOffset; // _38 + u64 mSkeleAnimDictOffset; // _40 + nn::g3d::ResMaterialAnim* mMatAnims; // _48 + u64 mMatAnimsDictOffset; // _50 + u64 mBoneVisiOffset; // _58 + u64 mBoneVisiDictOffset; // _60 + nn::g3d::ResShapeAnim* mShapeAnims; // _68 + u64 mShapeAnimDictOffset; // _70 + nn::g3d::ResSceneAnim* mSceneAnims; // _78 + u64 mSceneAnimDictOffset; // _80 + u64 mMemoryPool; // _88 + u64 mBufferSection; // _90 + u64 mEmbeddedFilesOffset; // _98 + u64 mEmbeddedFilesDictOffset; // _A0 + u64 mPadding; // _A8 + u64 mStrTableOffset; // _B0 + u32 mStrTableSize; // _B8 + u16 mModelCount; // _BC + u16 mSkeleAnimCount; // _BE + u16 mMatAnimCount; // _C0 + u16 mBoneAnimCount; // _C2 + u16 mShapeAnimCount; // _C4 + u16 mSceneAnimCount; // _C6 + u16 mExternalFileCount; // _C8 + u8 mPad[0x6]; // _CA +}; +}; // namespace g3d +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/g3d/ResFogAnim.h b/lib/NintendoSDK/include/nn/g3d/ResFogAnim.h new file mode 100644 index 00000000..e55846f7 --- /dev/null +++ b/lib/NintendoSDK/include/nn/g3d/ResFogAnim.h @@ -0,0 +1,21 @@ +#pragma once + +#include + +namespace nn { +namespace g3d { +class ResFogAnim { +public: + char mMagic[4]; // _0 + u16 mFlags; // _4 + u16 mPad; // _6 + s32 mNumFrames; // _8 + u8 mNumCurves; // _C + u8 mIdxDistanceAttnFunc; // _D + u16 mNumUserData; // _E + u32 mSizeBaked; // _10 + u64 mNameOffset; // _14 + u64 mFuncNameOffset; // _1C +}; +}; // namespace g3d +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/g3d/ResLightAnim.h b/lib/NintendoSDK/include/nn/g3d/ResLightAnim.h new file mode 100644 index 00000000..46cd6c30 --- /dev/null +++ b/lib/NintendoSDK/include/nn/g3d/ResLightAnim.h @@ -0,0 +1,12 @@ +#pragma once + +#include + +namespace nn { +namespace g3d { +class ResLightAnim { +public: + s32 Bind(nn::g3d::BindFuncTable const&); +}; +}; // namespace g3d +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/g3d/ResMaterial.h b/lib/NintendoSDK/include/nn/g3d/ResMaterial.h new file mode 100644 index 00000000..60dcea72 --- /dev/null +++ b/lib/NintendoSDK/include/nn/g3d/ResMaterial.h @@ -0,0 +1,29 @@ +/** + * @file ResMaterial.h + * @brief Resource material for models. + */ + +#pragma once + +#include + +namespace nn { +namespace g3d { +typedef void* TextureRef; + +class ResMaterial { +public: + u64 BindTexture(nn::g3d::TextureRef (*)(char const*, void*), void*); + void ForceBindTexture(nn::g3d::TextureRef const&, char const*); + void ReleaseTexture(); + void + Setup(nn::gfx::TDevice, nn::gfx::ApiVersion<4>>>*); + void + Cleanup(nn::gfx::TDevice, nn::gfx::ApiVersion<8>>>*); + void Reset(); + void Reset(u32); + + u8 _0[0xB4]; +}; +}; // namespace g3d +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/g3d/ResMaterialAnim.h b/lib/NintendoSDK/include/nn/g3d/ResMaterialAnim.h new file mode 100644 index 00000000..6556628c --- /dev/null +++ b/lib/NintendoSDK/include/nn/g3d/ResMaterialAnim.h @@ -0,0 +1,19 @@ +/** + * @file ResMaterialAnim.h + * @brief Resource file for material animations. + */ + +#pragma once + +namespace nn { +namespace g3d { +typedef void* TextureRef; + +class ResMaterialAnim { +public: + void ReleaseTexture(); + s32 BindTexture(nn::g3d::TextureRef (*)(char const*, void*), void*); + void Reset(); +}; +}; // namespace g3d +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/g3d/ResModel.h b/lib/NintendoSDK/include/nn/g3d/ResModel.h new file mode 100644 index 00000000..8c473806 --- /dev/null +++ b/lib/NintendoSDK/include/nn/g3d/ResModel.h @@ -0,0 +1,32 @@ +/** + * @file ResModel.h + * @brief Resource model. + */ + +#pragma once + +#include + +namespace nn { +namespace g3d { +class ResMaterial; + +typedef void* TextureRef; + +class ResModel { +public: + u64 BindTexture(nn::g3d::TextureRef (*)(char const*, void*), void*); + void ForceBindTexture(nn::g3d::TextureRef const&, char const*); + void ReleaseTexture(); + void + Setup(nn::gfx::TDevice, nn::gfx::ApiVersion<8>>>*); + void + Cleanup(nn::gfx::TDevice, nn::gfx::ApiVersion<8>>>*); + void Reset(); + void Reset(u32); + nn::g3d::ResMaterial* FindMaterial(char const* materialName) const; + + u8 _0[0x70]; +}; +}; // namespace g3d +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/g3d/ResSceneAnim.h b/lib/NintendoSDK/include/nn/g3d/ResSceneAnim.h new file mode 100644 index 00000000..0f45a9fc --- /dev/null +++ b/lib/NintendoSDK/include/nn/g3d/ResSceneAnim.h @@ -0,0 +1,41 @@ +/** + * @file ResSceneAnim.h + * @brief Resource file for scene animations. + */ + +#pragma once + +#include + +namespace nn { +namespace g3d { +class ResLightAnim; +class ResFogAnim; +struct BindFuncTable; + +class ResSceneAnim { +public: + s32 Bind(nn::g3d::BindFuncTable const&); + void Release(); + void Reset(); + + char mMagic[4]; // _0 + s32 mBlockOffset; // _4 + u64 mBlockSize; // _8 + u64 mNameOffset; // _10 + u64 mPathOffset; // _18 + u64 mCameraAnimOffset; // _20 + u64 mCameraAnimDictOffset; // _28 + nn::g3d::ResLightAnim* mLightAnims; // _30 + u64 mLightAnimDictOffset; // _38 + nn::g3d::ResFogAnim* mFogAnims; // _40 + u64 mFogAnimDictOffset; // _48 + u64 mUserDataOffset; // _50 + u64 mUserDataDictOffset; // _58 + u16 mUserDataCount; // _60 + u16 mCameraAnimCount; // _62 + u16 mLightAnimCount; // _64 + u16 mFogAnimCount; // _66 +}; +}; // namespace g3d +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/g3d/ResShapeAnim.h b/lib/NintendoSDK/include/nn/g3d/ResShapeAnim.h new file mode 100644 index 00000000..45355e8f --- /dev/null +++ b/lib/NintendoSDK/include/nn/g3d/ResShapeAnim.h @@ -0,0 +1,15 @@ +/** + * @file ResShapeAnim.h + * @brief Resource file for shape animations. + */ + +#pragma once + +namespace nn { +namespace g3d { +class ResShapeAnim { +public: + void Reset(); +}; +}; // namespace g3d +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/g3d/ResSkeletalAnim.h b/lib/NintendoSDK/include/nn/g3d/ResSkeletalAnim.h new file mode 100644 index 00000000..52168511 --- /dev/null +++ b/lib/NintendoSDK/include/nn/g3d/ResSkeletalAnim.h @@ -0,0 +1,15 @@ +/** + * @file ResSkeletalAnim.h + * @brief Resource file for skeletal animations. + */ + +#pragma once + +namespace nn { +namespace g3d { +class ResSkeletalAnim { +public: + void Reset(); +}; +}; // namespace g3d +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/gfx/api.h b/lib/NintendoSDK/include/nn/gfx/api.h new file mode 100644 index 00000000..4aa5398a --- /dev/null +++ b/lib/NintendoSDK/include/nn/gfx/api.h @@ -0,0 +1,22 @@ +/** + * @file api.h + * @brief GFX API version and typing. + */ + +#pragma once + +namespace nn { +namespace gfx { +// passes both ApiType<4> and ApiVersion<8> +template +class ApiVariation {}; + +// usually passed as just a 4 +template +class ApiType {}; + +// usually passed as just a 8 +template +class ApiVersion {}; +}; // namespace gfx +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/gfx/buffer.h b/lib/NintendoSDK/include/nn/gfx/buffer.h new file mode 100644 index 00000000..791fa54e --- /dev/null +++ b/lib/NintendoSDK/include/nn/gfx/buffer.h @@ -0,0 +1,28 @@ +/** + * @file buffer.h + * @brief GFX Buffers. + */ + +#pragma once + +#include + +namespace nn { +namespace gfx { +class BufferInfo { +public: + void SetDefault(); + + u64 mInfo; // _0 +}; + +class BufferTextureViewInfo { +public: + void SetDefault(); + + u64 _0; + u64 _8; + u64 _10; +}; +}; // namespace gfx +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/gfx/detail/bufferimpl.h b/lib/NintendoSDK/include/nn/gfx/detail/bufferimpl.h new file mode 100644 index 00000000..a437b338 --- /dev/null +++ b/lib/NintendoSDK/include/nn/gfx/detail/bufferimpl.h @@ -0,0 +1,55 @@ +/** + * @file bufferimpl.h + * @brief Buffer implementation for GFX. + */ + +#pragma once + +namespace nn { +namespace gfx { +class GpuAddress; +class BufferInfo; + +namespace detail { +template +class MemoryPoolImpl; +template +class DeviceImpl; + +template +class BufferImpl { +public: + BufferImpl(); + ~BufferImpl(); + + void Initialize(nn::gfx::detail::DeviceImpl< + nn::gfx::ApiVariation, nn::gfx::ApiVersion<8>>>*, + nn::gfx::BufferInfo const&, + nn::gfx::detail::MemoryPoolImpl< + nn::gfx::ApiVariation, nn::gfx::ApiVersion<8>>>*, + s64, u64); + void Finalize(nn::gfx::detail::DeviceImpl< + nn::gfx::ApiVariation, nn::gfx::ApiVersion<8>>>*); + void* Map() const; + void Unmap() const; + void FlushMappedRange(s64, u64) const; + void InvalidateMappedRange(s64, u64) const; + void GetGpuAddress(nn::gfx::GpuAddress*) const; + + T* mBuff; // _0 +}; + +template +class CommandBufferImpl { +public: + CommandBufferImpl(); + ~CommandBufferImpl(); + + void Reset(); + void Begin(); + void End(); + void Dispatch(s32, s32, s32); +}; +}; // namespace detail +}; // namespace gfx +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/gfx/detail/deviceimpl.h b/lib/NintendoSDK/include/nn/gfx/detail/deviceimpl.h new file mode 100644 index 00000000..569d6dc4 --- /dev/null +++ b/lib/NintendoSDK/include/nn/gfx/detail/deviceimpl.h @@ -0,0 +1,24 @@ +/** + * @file deviceimpl.h + * @brief Device implementation for GFX. + */ + +#pragma once + +namespace nn { +namespace gfx { +class DeviceInfo; + +namespace detail { +template +class DeviceImpl { +public: + DeviceImpl(); + ~DeviceImpl(); + + void Initialize(nn::gfx::DeviceInfo const& deviceInfo); + void Finalize(); +}; +}; // namespace detail +}; // namespace gfx +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/gfx/detail/pool.h b/lib/NintendoSDK/include/nn/gfx/detail/pool.h new file mode 100644 index 00000000..a332ab97 --- /dev/null +++ b/lib/NintendoSDK/include/nn/gfx/detail/pool.h @@ -0,0 +1,41 @@ +#pragma once + +#include + +namespace nn { +namespace gfx { +struct MemoryPoolInfo; +template +struct DeviceImpl; + +namespace detail { +class MemoryPoolData { +public: + void SetDefault(); + + s32 _0; // set to 0x88 + s32 _4; + u64 _8; +}; + +template +class MemoryPoolImpl { +public: + MemoryPoolImpl(); + ~MemoryPoolImpl(); + + void Initialize(nn::gfx::detail::DeviceImpl< + nn::gfx::ApiVariation, nn::gfx::ApiVersion<8>>>*, + nn::gfx::MemoryPoolInfo const&); + void Finalize(nn::gfx::detail::DeviceImpl< + nn::gfx::ApiVariation, nn::gfx::ApiVersion<8>>>*); + void* Map() const; + void Unmap() const; + void FlushMappedRange(s64, u64) const; + void InvalidateMappedRange(s64, u64) const; + + u8 _0[0x120]; // pool data +}; +}; // namespace detail +}; // namespace gfx +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/gfx/device.h b/lib/NintendoSDK/include/nn/gfx/device.h new file mode 100644 index 00000000..7c00621c --- /dev/null +++ b/lib/NintendoSDK/include/nn/gfx/device.h @@ -0,0 +1,20 @@ +/** + * @file device.h + * @brief Device implementation for GFX. + */ + +#pragma once + +#include + +namespace nn { +namespace gfx { +class DeviceInfo { +public: + u64 mInfo; // _0 +}; + +template +class TDevice {}; +}; // namespace gfx +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/gfx/memory.h b/lib/NintendoSDK/include/nn/gfx/memory.h new file mode 100644 index 00000000..9404a1e7 --- /dev/null +++ b/lib/NintendoSDK/include/nn/gfx/memory.h @@ -0,0 +1,14 @@ +/** + * @file memory.h + * @brief GFX Memory Pool. + */ + +#pragma once + +namespace nn { +namespace gfx { +// todo: finish me! +template +class TMemoryPool {}; +}; // namespace gfx +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/hid.h b/lib/NintendoSDK/include/nn/hid.h new file mode 100644 index 00000000..76ebd9df --- /dev/null +++ b/lib/NintendoSDK/include/nn/hid.h @@ -0,0 +1,43 @@ +/** + * @file hid.h + * @brief Functions that help process gamepad inputs. + */ + +#pragma once + +#include +#include + +namespace nn { +namespace hid { +struct NpadHandheldState; +struct NpadStyleTag; + +struct ControllerSupportArg { + u8 mMinPlayerCount; + u8 mMaxPlayerCount; + u8 mTakeOverConnection; + bool mLeftJustify; + bool mPermitJoyconDual; + bool mSingleMode; + bool mUseColors; + sead::Color4u8 mColors[4]; + u8 mUsingControllerNames; + char mControllerNames[4][0x81]; +}; + +struct ControllerSupportResultInfo { + int mPlayerCount; + int mSelectedId; +}; + +void InitializeNpad(); +void SetSupportedNpadIdType(u32 const*, u64); +void SetSupportedNpadStyleSet(nn::util::BitFlagSet<32, nn::hid::NpadStyleTag>); +void GetNpadStyleSet(u32 const&); +void GetNpadStates(nn::hid::NpadHandheldState*, s32, u32 const&); +static int ShowControllerSupport(nn::hid::ControllerSupportResultInfo*, + ControllerSupportArg const&); + +}; // namespace hid +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/image.h b/lib/NintendoSDK/include/nn/image.h new file mode 100644 index 00000000..44e50bd8 --- /dev/null +++ b/lib/NintendoSDK/include/nn/image.h @@ -0,0 +1,50 @@ +/** + * @file image.h + * @brief JPEG decoding library. + */ + +#pragma once + +#include + +namespace nn { +namespace image { +// there's probably more +enum JpegStatus { + OK = 0, + INVALID_FORMAT = -32, + UNSUPPORTED_FORMAT = -33, + OUT_OF_MEMORY = -64, +}; + +enum PixelFormat { RGBA32, RGB24 }; + +enum ProcessStage { UNREGISTERED = 0, REGISTERED = 1, ANALYZED = 2 }; + +struct Dimension { + f32 width; + f32 height; +}; + +class JpegDecoder { +public: + JpegDecoder(); + virtual ~JpegDecoder(); + + void SetImageData(void const* source, u64 size); + nn::image::JpegStatus Analyze(); + nn::image::Dimension GetAnalyzedDimension() const; + s64 GetAnalyzedWorkBufferSize() const; + JpegStatus Decode(void* out, s64, s32 alignment, void*, s64); + + nn::image::ProcessStage mProcessStage; // _8 + void* mData; // _C + s64 mSize; // _14 + s32 _18; + nn::image::PixelFormat mFormat; // _1C + Dimension mImgDimensions; // _20 + s64 _28; + // rest is related to EXIF processing +}; +}; // namespace image +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/init.h b/lib/NintendoSDK/include/nn/init.h new file mode 100644 index 00000000..2f849106 --- /dev/null +++ b/lib/NintendoSDK/include/nn/init.h @@ -0,0 +1,21 @@ +/** + * @file init.h + * @brief Initialization functions for OS related functions. + */ + +#pragma once + +#include +#include + +namespace nn { +namespace init { +void InitializeAllocator(void* addr, u64 size); +nn::mem::StandardAllocator* GetAllocator(); + +namespace detail { +void* DefaultAllocatorForThreadLocal(u64, u64); +void* DefaultDeallocatorForThreadLocal(void*, u64); +}; // namespace detail +} // namespace init +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/mem.h b/lib/NintendoSDK/include/nn/mem.h new file mode 100644 index 00000000..5cb59744 --- /dev/null +++ b/lib/NintendoSDK/include/nn/mem.h @@ -0,0 +1,30 @@ +/** + * @file mem.h + * @brief Memory allocation functions. + */ + +#pragma once + +#include +#include + +namespace nn { +namespace mem { +class StandardAllocator { +public: + StandardAllocator(); + + void Initialize(void* address, u64 size); + void Finalize(); + void* Reallocate(void* address, u64 newSize); + void* Allocate(u64 size); + void Free(void* address); + void Dump(); + + bool mIsInitialized; // _0 + bool mIsEnabledThreadCache; // _1 + u16 _2; + u64* mAllocAddr; // _4 +}; +}; // namespace mem +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/nex/RootObject.h b/lib/NintendoSDK/include/nn/nex/RootObject.h new file mode 100644 index 00000000..68e96490 --- /dev/null +++ b/lib/NintendoSDK/include/nn/nex/RootObject.h @@ -0,0 +1,30 @@ +/** + * @file RootObject.h + * @brief RootObject for NEX. + */ + +#pragma once + +#include + +namespace nn { +namespace nex { +class RootObject { +public: + enum TargetPool {}; + + virtual ~RootObject(); + + void* operator new(u64); + void operator delete(void*); + void* operator new(u64, char const*, u32); + void* operator new[](u64); + void* operator new[](u64, char const*, u32); + void operator delete[](void*); + void operator delete(void*, char const*, u32); + void operator delete[](void*, char const*, u32); + void* operator new(u64, nn::nex::RootObject::TargetPool); + void* operator new(u64, nn::nex::RootObject::TargetPool, char const*, u32); +}; +}; // namespace nex +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/nex/auth.h b/lib/NintendoSDK/include/nn/nex/auth.h new file mode 100644 index 00000000..30676b46 --- /dev/null +++ b/lib/NintendoSDK/include/nn/nex/auth.h @@ -0,0 +1,20 @@ +/** + * @file auth.h + * @brief Authorization for DDL. + */ + +#pragma once + +#include + +namespace nn { +namespace nex { +class NintendoAuthenticationDDLDeclarations : public nn::nex::DDLDeclarations { +public: + virtual ~NintendoAuthenticationDDLDeclarations(); + virtual void Init(); + + void Register(); +}; +}; // namespace nex +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/nex/buffer.h b/lib/NintendoSDK/include/nn/nex/buffer.h new file mode 100644 index 00000000..eab8d2ac --- /dev/null +++ b/lib/NintendoSDK/include/nn/nex/buffer.h @@ -0,0 +1,25 @@ +/** + * @file buffer.h + * @brief NEX buffer implementation. + */ + +#pragma once + +#include + +namespace nn { +namespace nex { +class String; +// todo +class Buffer { +public: + Buffer(nn::nex::Buffer const&); + Buffer(nn::nex::Buffer&&); + Buffer(nn::nex::String const&); + + void FreeDataBuffer(u8*, u64); + + virtual ~Buffer(); +}; +}; // namespace nex +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/nex/cache.h b/lib/NintendoSDK/include/nn/nex/cache.h new file mode 100644 index 00000000..c94285da --- /dev/null +++ b/lib/NintendoSDK/include/nn/nex/cache.h @@ -0,0 +1,33 @@ +/** + * @file cache.h + * @brief NEX Cache Mangement. + */ + +#pragma once + +#include + +namespace nn { +namespace nex { +class String; +class BasicCache; + +class CacheManager { +public: + CacheManager(); + ~CacheManager(); + + nn::nex::BasicCache* GetCache(nn::nex::String const&); +}; + +class BasicCache { +public: + BasicCache(nn::nex::String const&); + + virtual ~BasicCache(); + + u64 _8; + u8 _10; +}; +}; // namespace nex +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/nex/checksum.h b/lib/NintendoSDK/include/nn/nex/checksum.h new file mode 100644 index 00000000..44006cdd --- /dev/null +++ b/lib/NintendoSDK/include/nn/nex/checksum.h @@ -0,0 +1,61 @@ +/** + * @file checksum.h + * @brief NEX Checksum Implementation. + */ + +#pragma once + +#include + +namespace nn { +namespace nex { +class Buffer; + +class ChecksumAlgorithm : public nn::nex::RootObject { +public: + ChecksumAlgorithm(); + + virtual ~ChecksumAlgorithm(); + + virtual bool ComputeChecksum(nn::nex::Buffer const&, nn::nex::Buffer*) = 0; + // virtual bool ComputeChecksum(u8 const **, u64 const *, u64, nn::nex::SignatureBytes &) = 0; + virtual bool IsReady() const; + virtual void ComputeChecksumForTransport(u8 const*, u64); + virtual u32 ComputeChecksumForTransportArray(u8 const**, u64 const*, u64) = 0; + virtual u32 GetChecksumLength() = 0; + + u64 _8; + u8 _10; +}; + +class MD5Checksum : public nn::nex::ChecksumAlgorithm { +public: + MD5Checksum(); + + virtual ~MD5Checksum(); + + virtual bool ComputeChecksum(nn::nex::Buffer const&, nn::nex::Buffer*); + virtual u32 ComputeChecksumForTransportArray(u8 const**, u64 const*, u64); + virtual u32 GetChecksumLength(); +}; + +class CRC16Checksum : public nn::nex::ChecksumAlgorithm { +public: + CRC16Checksum(); + + virtual ~CRC16Checksum(); + + virtual bool ComputeChecksum(nn::nex::Buffer const&, nn::nex::Buffer*); + virtual u32 ComputeChecksumForTransportArray(u8 const**, u64 const*, u64); + virtual u32 GetChecksumLength(); +}; + +/* +this actually inherits some sort of KeyedChecksum thing. whatever +class HMACChecksum : public nn::nex::ChecksumAlgorithm +{ + +}; +*/ +}; // namespace nex +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/nex/client.h b/lib/NintendoSDK/include/nn/nex/client.h new file mode 100644 index 00000000..df00dd08 --- /dev/null +++ b/lib/NintendoSDK/include/nn/nex/client.h @@ -0,0 +1,111 @@ +/** + * @file client.h + * @brief Client implementations for NEX. + */ +#pragma once + +#include + +namespace nn { +namespace nex { +class Credentials; +class EndPoint; +class Message; +class ProtocolCallContext; +class ProtocolRequestBrokerInterface; + +class Protocol : public nn::nex::SystemComponent { +public: + enum _Command { Response, Request }; + + enum _Type { + Client, // implemented in nn::nex::ClientProtocol + Server // implemented in nn::nex::ServerProtocol + }; + + Protocol(u32); + + virtual ~Protocol(); + + virtual char* GetType() const; + virtual bool IsAKindOf(char const*) const; + virtual void EnforceDeclareSysComponentMacro(); + + virtual bool BeginInitialization(); + virtual bool BeginTermination(); + + virtual nn::nex::Protocol::_Type GetProtocolType() const = 0; + virtual void EndPointDisconnected(nn::nex::EndPoint*); + virtual void FaultDetected(nn::nex::EndPoint*, u32); + virtual nn::nex::Protocol* Clone() const; + virtual bool Reload(); + + nn::nex::EndPoint* GetOutgoingConnection() const; + void SetIncomingConnection(nn::nex::EndPoint*); + void SetProtocolID(u16); + void AddMethodID(nn::nex::Message*, u32); + void CopyMembers(nn::nex::Protocol const*); + void AssociateProtocolRequestBroker(nn::nex::ProtocolRequestBrokerInterface*); + void ClearFlag(u32 newFlag); + + static void ExtractProtocolKey(nn::nex::Message*, nn::nex::Protocol::_Command&, u16&); + static bool IsOldRVDDLVersion(nn::nex::EndPoint*); + + u16 mProtocolID; // _48 + u16 _4A; + u32 _4C; + nn::nex::EndPoint* mOutgoingConnection; // _50 + nn::nex::ProtocolRequestBrokerInterface* mBrokerInterface; // _58 + u32 mFlags; // _60 + u32 _64; + nn::nex::EndPoint* mIncomingConnection; // _68 + u32 mUseLoopback; // _70 (boolean) + u32 _74; + u64 _78; + u32 _80; + u32 _84; +}; + +class ClientProtocol : public nn::nex::Protocol { +public: + ClientProtocol(u32); + + virtual ~ClientProtocol(); + + virtual char* GetType() const; + virtual bool IsAKindOf(char const*) const; + virtual void EnforceDeclareSysComponentMacro(); + + virtual nn::nex::Protocol::_Type GetProtocolType() const = 0; + + virtual void ExtractCallSpecificResults(nn::nex::Message*, nn::nex::ProtocolCallContext*) = 0; + virtual nn::nex::ClientProtocol* CreateResponder() const = 0; + virtual void SetDefaultCredentials(nn::nex::Credentials*); + + bool SendOverLocalLoopback(nn::nex::ProtocolCallContext*, nn::nex::Message*); + bool SendRMCMessage(nn::nex::ProtocolCallContext*, nn::nex::Message*); + void ProcessResponse(nn::nex::Message*, nn::nex::EndPoint*); + + nn::nex::Credentials* mCredentials; // _88 +}; + +class ServerProtocol : public nn::nex::Protocol { +public: + ServerProtocol(u32); + + virtual ~ServerProtocol(); + + virtual char* GetType() const; + virtual bool IsAKindOf(char const*) const; + virtual void EnforceDeclareSysComponentMacro(); + + virtual nn::nex::Protocol::_Type GetProtocolType() const = 0; + + virtual void DispatchProtocolMessage(nn::nex::Message*, nn::nex::Message*, bool*, + nn::nex::EndPoint*) = 0; + virtual void DispatchProtocolMessageWithAttemptCount(u64, nn::nex::Message*, nn::nex::Message*, + bool*, int*, nn::nex::EndPoint*); + virtual bool UseAttemptCountMethod(); +}; +}; // namespace nex +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/nex/data.h b/lib/NintendoSDK/include/nn/nex/data.h new file mode 100644 index 00000000..2446fce5 --- /dev/null +++ b/lib/NintendoSDK/include/nn/nex/data.h @@ -0,0 +1,21 @@ +/** + * @file data.h + * @brief NEX Data. + */ + +#pragma once + +#include + +namespace nn { +namespace nex { +class Data : public nn::nex::RootObject { +public: + Data(); + + virtual ~Data(); + + u8 _8; +}; +}; // namespace nex +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/nex/ddl.h b/lib/NintendoSDK/include/nn/nex/ddl.h new file mode 100644 index 00000000..85ee927c --- /dev/null +++ b/lib/NintendoSDK/include/nn/nex/ddl.h @@ -0,0 +1,40 @@ +/** + * @file ddl.h + * @brief DDL Declaration Implementation. + */ + +#pragma once + +#include + +namespace nn { +namespace nex { +class DDLDeclarations : public nn::nex::RootObject { +public: + DDLDeclarations(bool); + + virtual ~DDLDeclarations(); + + virtual void Init() = 0; + + void RegisterIfRequired(); + void Unregister(); + static void UnregisterAll(); + void LoadAll(); + void Load(); + void UnloadAll(); + void Unload(); + void ResetDOClassIDs(); + + u32 mNumDecsLoaded; // _8 + u8 DDLDeclarations_xC; + u8 _D; // padding + u8 _E; // ^^ + u8 _F; // ^^ + u64 _10; + bool _18; + + static nn::nex::DDLDeclarations* s_pFirstDDLDecl; +}; +}; // namespace nex +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/nex/dynamic.h b/lib/NintendoSDK/include/nn/nex/dynamic.h new file mode 100644 index 00000000..b28da43d --- /dev/null +++ b/lib/NintendoSDK/include/nn/nex/dynamic.h @@ -0,0 +1,21 @@ +/** + * @file dynamic.h + * @brief NEX Dyamnic Runtime. + */ + +#pragma once + +#include + +namespace nn { +namespace nex { +class DynamicRunTimeInterface : public nn::nex::RootObject { +public: + DynamicRunTimeInterface(); + + virtual ~DynamicRunTimeInterface(); + + u64* GetInstance(); +}; +}; // namespace nex +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/nex/encryption.h b/lib/NintendoSDK/include/nn/nex/encryption.h new file mode 100644 index 00000000..f155d5df --- /dev/null +++ b/lib/NintendoSDK/include/nn/nex/encryption.h @@ -0,0 +1,61 @@ +/** + * @file encryption.h + * @brief NEX Encryption Algorithm. + */ + +#pragma once + +#include + +namespace nn { +namespace nex { +class Buffer; +class Key; + +class EncryptionAlgorithm : public nn::nex::RootObject { +public: + EncryptionAlgorithm(u32, u32); + + virtual ~EncryptionAlgorithm(); + + virtual bool Encrypt(nn::nex::Buffer const&, nn::nex::Buffer*) = 0; + virtual bool Encrypt(nn::nex::Buffer*); + virtual bool Decrypt(nn::nex::Buffer const&, nn::nex::Buffer*) = 0; + virtual bool Decrypt(nn::nex::Buffer*); + virtual bool GetErrorString(u32, char* destStr, u64 errLen); + virtual void KeyHasChanged(); + + bool SetKey(nn::nex::Key const& key); + + u64 _8; + u64 _10; + u64 _18; + u64 _20; + u64 _28; + u64 _30; + u64 _38; + u64 _40; +}; + +class RC4Encryption : public nn::nex::EncryptionAlgorithm { +public: + RC4Encryption(); + + virtual ~RC4Encryption(); + + virtual bool Encrypt(nn::nex::Buffer const&, nn::nex::Buffer*); + virtual bool Encrypt(nn::nex::Buffer*); + virtual bool Decrypt(nn::nex::Buffer const&, nn::nex::Buffer*); + virtual bool Decrypt(nn::nex::Buffer*); + + virtual void KeyHasChanged(); + + void GetDefaultKey(); + void PrepareEncryption(); + void ReinitStateArray(); + void SetReinitEverytime(bool); + + u8 _48[0x298 - 0x48]; +}; +}; // namespace nex +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/nex/hash.h b/lib/NintendoSDK/include/nn/nex/hash.h new file mode 100644 index 00000000..5da8b3f4 --- /dev/null +++ b/lib/NintendoSDK/include/nn/nex/hash.h @@ -0,0 +1,35 @@ +/** + * @file hash.h + * @brief NEX Hash Implementation. + */ + +#pragma once + +#include +#include + +namespace nn { +namespace nex { +class MD5 : public nn::crypto::detail::Md5Impl, public nn::nex::RootObject { +public: + MD5(); + + void init(); + void raw_digest(u8*); + void hex_digest(); + + u8 _5C[0x74 - 0x5C]; +}; + +class Sha1 : public nn::crypto::detail::Sha1Impl, public nn::nex::RootObject { +public: + Sha1(); + + void Update(void const*, u64); + void GetHash(void*, u64); + void GenerateHash(void*, u64, void const*, u64); + + u32 _68; +}; +}; // namespace nex +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/nex/instance.h b/lib/NintendoSDK/include/nn/nex/instance.h new file mode 100644 index 00000000..833419f6 --- /dev/null +++ b/lib/NintendoSDK/include/nn/nex/instance.h @@ -0,0 +1,46 @@ +/** + * @file instance.h + * @brief NEX Instance Controllers. + */ +#pragma once + +#include + +namespace nn { +namespace nex { +class InstanceTable; + +class InstanceControl : public nn::nex::RootObject { +public: + InstanceControl(u32, u32); + + u32 mInstanceContext; // _8 + u32 mInstanceType; // _C + void* mDelegateInstance; // _10 + bool mIsValidControl; // _18 + u8 _19; // probably padding + u8 _1A; + u8 _1B; + + static nn::nex::InstanceTable* s_oInstanceTable; +}; + +class InstanceTable : public nn::nex::RootObject { +public: + InstanceTable(); + + virtual ~InstanceTable(); + + bool AddInstance(nn::nex::InstanceControl*, u32, u32); + void DelInstance(nn::nex::InstanceControl*, u32, u32); + u32 CreateContext(); + bool DeleteContext(u32); + void AllocateExtraContexts(u64 size); + void FreeExtraContexts(); + u32 GetHighestID() const; + u32 FindInstanceContext(nn::nex::InstanceControl*, u32); + + u8 _0[0x94]; +}; +}; // namespace nex +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/nex/key.h b/lib/NintendoSDK/include/nn/nex/key.h new file mode 100644 index 00000000..359618d3 --- /dev/null +++ b/lib/NintendoSDK/include/nn/nex/key.h @@ -0,0 +1,39 @@ +/** + * @file key.h + * @brief NEX Key Implementation. + */ + +#pragma once + +#include + +namespace nn { +namespace nex { +class String; + +class Key : public nn::nex::RootObject { +public: + Key(); + Key(u8 const* src, u64 size); + Key(u64 size); + Key(nn::nex::Key const&); + Key(nn::nex::String const&); + + virtual ~Key(); + + u64* GetContentPtr(); + u64 GetLength() const; + nn::nex::Key& operator=(nn::nex::Key const&); + bool operator==(nn::nex::Key const&); + bool operator!=(nn::nex::Key const&); + void PrepareContentPtr(u64); + nn::nex::String* ToString(); + void ExtractToString(nn::nex::String*) const; + void Trace(u64) const; + void GenerateRandomKey(u64); + + u64* mContentPtrStart; // _10 + u64* mContentPtrEnd; // _18 +}; +}; // namespace nex +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/nex/plugin.h b/lib/NintendoSDK/include/nn/nex/plugin.h new file mode 100644 index 00000000..2e86ca8e --- /dev/null +++ b/lib/NintendoSDK/include/nn/nex/plugin.h @@ -0,0 +1,33 @@ +/** + * @file plugin.h + * @brief Plugin interface for NEX. + */ + +#pragma once + +#include + +namespace nn { +namespace nex { +class PluginObject : public nn::nex::RootObject {}; + +class Plugin : public nn::nex::RootObject { +public: + Plugin(); + + virtual ~Plugin(); + + // there's a bunch of pure virtual methods but nothing ever inherits this class... + virtual bool Initalize(); + virtual void ThreadAttach(); + virtual void ThreadDetach(); + virtual void Destroy(); + + void SetLibrary(void*); + + void* mLibrary; // _8s + + static nn::nex::Plugin* s_pInstance; +}; +}; // namespace nex +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/nex/pseudo.h b/lib/NintendoSDK/include/nn/nex/pseudo.h new file mode 100644 index 00000000..1fde1a79 --- /dev/null +++ b/lib/NintendoSDK/include/nn/nex/pseudo.h @@ -0,0 +1,80 @@ +/** + * @file psuedo.h + * @brief Psuedo variable implementation for NEX. + */ + +#pragma once + +#include +#include + +namespace nn { +namespace nex { +class PseudoGlobalVariableList; + +class PseudoGlobalVariableRoot : public nn::nex::RootObject { +public: + PseudoGlobalVariableRoot(); + + virtual ~PseudoGlobalVariableRoot(); + + virtual void AllocateExtraContexts() = 0; + virtual void FreeExtraContexts() = 0; + virtual void ResetContext(u32) = 0; + virtual PseudoGlobalVariableRoot* GetNext() = 0; + virtual void SetNext(PseudoGlobalVariableRoot* pNextVariable) = 0; + + static void ResetContextForAllVariables(u32); + static void AllocateExtraContextsForAllVariables(u64); + static void FreeExtraContextsForAllVariables(); + static s64 GetNbOfExtraContexts(); + + nn::nex::PseudoGlobalVariableRoot* mNextRoot; // _8 + + static s64 s_uiNbOfExtraContexts; + static PseudoGlobalVariableList s_oList; +}; + +class PseudoGlobalVariableList : public nn::nex::RootObject { +public: + PseudoGlobalVariableList(); + + virtual ~PseudoGlobalVariableList(); + + void AddVariable(nn::nex::PseudoGlobalVariableRoot*); + void RemoveVariable(nn::nex::PseudoGlobalVariableRoot*); + static nn::nex::PseudoGlobalVariableRoot* GetVariable(u32 idx); + static u32 FindVariableIndex(nn::nex::PseudoGlobalVariableRoot*); + void AllocateExtraContextsForAllVariables(); + void FreeExtraContextsForAllVariables(); + void ResetContextForAllVariables(u32); + static u32 GetNbOfVariables(); + + static PseudoGlobalVariableRoot* s_pVariableListHead; + static u32 m_uiNbOfVariables; +}; + +template +class PseudoGlobalVariable : public nn::nex::PseudoGlobalVariableRoot { +public: + PseudoGlobalVariable(); + + virtual ~PseudoGlobalVariable(); + + virtual void AllocateExtraContexts(); + virtual void FreeExtraContexts(); + virtual void ResetContext(u32); + virtual PseudoGlobalVariableRoot* GetNext(); + virtual void SetNext(PseudoGlobalVariableRoot* pNextVariable); +}; + +class PseudoSingleton : public nn::nex::InstanceControl { +public: + PseudoSingleton(u32); + + virtual ~PseudoSingleton(); + + static bool s_bUseInstantiationContext; +}; +}; // namespace nex +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/nex/reference.h b/lib/NintendoSDK/include/nn/nex/reference.h new file mode 100644 index 00000000..44c171e7 --- /dev/null +++ b/lib/NintendoSDK/include/nn/nex/reference.h @@ -0,0 +1,18 @@ +/** + * @file reference.h + * @brief Reference implementations for NEX. + */ +#pragma once + +#include + +namespace nn { +namespace nex { +class RefCountedObject : public nn::nex::RootObject { +public: + virtual ~RefCountedObject(); + + u32 _8; +}; +}; // namespace nex +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/nex/socket.h b/lib/NintendoSDK/include/nn/nex/socket.h new file mode 100644 index 00000000..660a8e4b --- /dev/null +++ b/lib/NintendoSDK/include/nn/nex/socket.h @@ -0,0 +1,73 @@ +#pragma once + +#include //FIXME requires proper musl-setup +#include +#include "RootObject.h" + +namespace nn { +namespace nex { +class TransportProtocol { +public: + enum Type { + Sock_Default = 0, + Sock_Stream = SOCK_STREAM, + Sock_DGram = SOCK_DGRAM, + Sock_Raw = SOCK_RAW, + Sock_SeqPacket = SOCK_SEQPACKET, + Sock_NonBlock = SOCK_NONBLOCK + }; +}; + +class SocketDriver : nn::nex::RootObject { +public: + typedef in_addr_t InetAddress; + + enum _SocketFlag : int32_t { + Msg_None = 0, + Msg_Oob = MSG_OOB, + Msg_Peek = MSG_PEEK, + Msg_DontRoute = MSG_DONTROUTE, + Msg_Eor = MSG_EOR, + Msg_Trunc = MSG_TRUNC, + Msg_CTrunc = MSG_CTRUNC, + Msg_WaitAll = MSG_WAITALL, + Msg_DontWait = MSG_DONTWAIT, + Msg_Eof = MSG_EOF, + Msg_Notification = MSG_NOTIFICATION, + Msg_Nbio = MSG_NBIO, + Msg_Compat = MSG_COMPAT, + // Msg_SoCallbck = MSG_SOCALLBCK, + // Msg_NoSignal = MSG_NOSIGNAL, + Msg_CMsg_CloExec = MSG_CMSG_CLOEXEC + }; + + class Socket { + virtual void Open(nn::nex::TransportProtocol::Type); + virtual void Close(); + virtual void Bind(ushort&); + virtual void RecvFrom(uchar*, ulong, InetAddress*, ulong*, + nn::nex::SocketDriver::_SocketFlag); + virtual void SendTo(uchar const*, ulong, nn::nex::SocketDriver::InetAddress const&, ulong*); + }; + + class PollInfo {}; + + virtual Socket* Create(); + virtual void Delete(Socket*); + virtual int Poll(PollInfo*, uint, uint); + virtual bool CanUseGetAllReceivableSockets(); + virtual void GetAllReceivableSockets(Socket**, ulong, uint); +}; + +class BerkelySocket : public SocketDriver::Socket {}; + +class BerkeleySocketDriver + : SocketDriver { // inherits SocketDriver and RootObject but not documented + virtual ~BerkeleySocketDriver(); +}; + +class ClientWebSocketDriver : SocketDriver { + class ClientWebSocket : Socket {}; +}; +}; // namespace nex +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/nex/string.h b/lib/NintendoSDK/include/nn/nex/string.h new file mode 100644 index 00000000..48151c5e --- /dev/null +++ b/lib/NintendoSDK/include/nn/nex/string.h @@ -0,0 +1,47 @@ +/** + * @file string.h + * @brief NEX String Implementation. + */ + +#pragma once + +#include + +namespace nn { +namespace nex { +class String : public nn::nex::RootObject { +public: + String(); + String(const char*); + String(const wchar_t*); + String(const char16_t*); + String(const String&); + String(String&&); + + String& operator=(String&&); + String& operator=(const char*); + String& operator=(const wchar_t*); + String& operator=(const String&); + String& operator=(const char16_t*); + String& operator+=(const String&); + String operator==(const String&); + bool operator<(nn::nex::String const&); + + void Truncate(u64) const; + u64 GetLength() const; + void Reserve(u64); + void SetBufferChar(char*); + void SetStringToPreReservedBuffer(char const*); + s32 GetWideCharLength() const; + void CopyString(char*, u64) const; + void CreateCopy(wchar_t**) const; + void ReleaseCopy(wchar_t*); + void ToUpper(); + void ToLower(); + void DeleteContent(); + + template + void Assign(T const*); +}; +}; // namespace nex +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/nex/system.h b/lib/NintendoSDK/include/nn/nex/system.h new file mode 100644 index 00000000..cd763de6 --- /dev/null +++ b/lib/NintendoSDK/include/nn/nex/system.h @@ -0,0 +1,66 @@ +/** + * @file system.h + * @brief System state / component interface for NEX. + */ + +#pragma once + +#include + +namespace nn { +namespace nex { +class String; + +class SystemComponent : public nn::nex::RefCountedObject { +public: + enum _State { + State_Uninitialized = 1 << 0, + State_Initializing = 1 << 1, + State_Ready = 1 << 2, + State_ReadyInUse = 1 << 3, + State_Terminating = 1 << 4, + State_TerminatingWhileInUse = 1 << 5, + State_Terminated = 1 << 6, + State_Faulty = 1 << 7, + State_Unknown = 1 << 8, + State_HighestState = 1 << 8 + }; + + SystemComponent(nn::nex::String const&); + + virtual ~SystemComponent(); + + virtual char* GetType() const; + virtual bool IsAKindOf(char const*) const; + virtual void EnforceDeclareSysComponentMacro() = 0; + virtual void StateTransition(nn::nex::SystemComponent::_State); + virtual void OnInitialize(); + virtual void OnTerminate(); + virtual bool BeginInitialization(); + virtual bool EndInitialization(); + virtual bool BeginTermination(); + virtual bool EndTermination(); + virtual bool ValidTransition(nn::nex::SystemComponent::_State); + virtual bool UseIsAllowed(); + virtual nn::nex::SystemComponent::_State TestState(); + virtual void DoWork(); + + nn::nex::SystemComponent::_State Initialize(); + nn::nex::SystemComponent::_State Terminate(); + + u8 SystemComponent_xC; + u8 _D; + u8 _E; + u8 _F; + u64 _10; + u64 _18; + u64 _20; + u32 _28; + u32 _2C; + u64 _30; + nn::nex::SystemComponent::_State mState; // _38 + u32 _3C; + u64 _40; +}; +}; // namespace nex +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/nex/time.h b/lib/NintendoSDK/include/nn/nex/time.h new file mode 100644 index 00000000..9ee36123 --- /dev/null +++ b/lib/NintendoSDK/include/nn/nex/time.h @@ -0,0 +1,49 @@ +/** + * @file time.h + * @brief NEX Time Library. + */ + +#pragma once + +#include + +namespace nn { +namespace nex { +class TimeProvider; + +class Time { +public: + static void Reset(); + static void RegisterTimeProvider(TimeProvider* provider); + + Time Multiply(f32) const; + Time Divide(f32) const; + Time Scale(f32) const; + + static Time ConvertTimeoutToDeadline(u32 timeout); + static u32 ConvertDeadlineToTimeout(Time deadline); + + u64 mCurTime; // _0 + + static u64* s_pfGetSessionTime; // some sort of callback? +}; + +class SystemClock { +public: + SystemClock(); + + virtual ~SystemClock(); + + static void RegisterTimeProvider(nn::nex::TimeProvider*, bool); + static void ApplyCorrection(Time curTime, Time newTime); + static Time ProtectedGetTime(); + static Time GetTimeImpl(bool); + static Time GetTimeImplCorrectless(); + static void Reset(); + + static nn::nex::TimeProvider* s_pTimeProvider; + static bool s_needCorrection; + static bool s_tiCorrection; +}; +}; // namespace nex +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/nifm.h b/lib/NintendoSDK/include/nn/nifm.h new file mode 100644 index 00000000..f79bf25e --- /dev/null +++ b/lib/NintendoSDK/include/nn/nifm.h @@ -0,0 +1,21 @@ +/** + * @file nifm.h + * @brief Network inferface module. + */ + +#pragma once + +#include + +namespace nn { +namespace nifm { +Result Initialize(); +void SetLocalNetworkMode(bool); +void SubmitNetworkRequestAndWait(); +bool IsNetworkAvailable(); +Result HandleNetworkRequestResult(); +void SubmitNetworkRequest(); +bool IsNetworkRequestOnHold(); +Result GetCurrentPrimaryIpAddress(u64* inAddr); +}; // namespace nifm +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/nn.h b/lib/NintendoSDK/include/nn/nn.h new file mode 100644 index 00000000..d367d9b8 --- /dev/null +++ b/lib/NintendoSDK/include/nn/nn.h @@ -0,0 +1,33 @@ +/** + * @file nn.h + * @brief Barebones NN functions, such as init and nnMain. + */ + +#pragma once + +#include + +namespace nn { +typedef u64 ApplicationId; +}; + +#ifdef __cplusplus +extern "C" { +#endif + +int main(int argc, char** argv); +void nninitStartup(); + +void _init(); +void _fini(); +void __nnDetailNintendoSdkRuntimeObjectFileRefer(); +void __nnDetailNintendoSdkRuntimeObjectFile(); +void __nnDetailNintendoSdkNsoFileRefer(); + +void __nnmusl_init_dso_0(); +void __nnmusl_fini_dso_0(); +void __nnDetailNintendoSdkNsoFile_0(); + +#ifdef __cplusplus +} +#endif \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/oe.h b/lib/NintendoSDK/include/nn/oe.h new file mode 100644 index 00000000..2199e71d --- /dev/null +++ b/lib/NintendoSDK/include/nn/oe.h @@ -0,0 +1,37 @@ +/** + * @file oe.h + * @brief Extenstions to OS functions. + */ + +#pragma once + +#include +#include + +namespace nn { +namespace oe { +typedef s32 FocusHandlingMode; +typedef s32 PerformanceMode; + +struct DisplayVersion { + char name[16]; +}; + +void Initialize(); +void SetPerformanceConfiguration(nn::oe::PerformanceMode, s32); +s32 GetOperationMode(); +s32 GetPerformanceMode(); +void SetResumeNotificationEnabled(bool); +void SetOperationModeChangedNotificationEnabled(bool); +void SetPerformanceModeChangedNotificationEnabled(bool); +void SetFocusHandlingMode(nn::oe::FocusHandlingMode); +bool TryPopNotificationMessage(u32*); +s32 GetCurrentFocusState(); +void EnableGamePlayRecording(void*, u64); +bool IsUserInactivityDetectionTimeExtended(); +void SetUserInactivityDetectionTimeExtended(bool); +void FinishStartupLogo(); +nn::settings::LanguageCode GetDesiredLanguage(); +void GetDisplayVersion(DisplayVersion*); +}; // namespace oe +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/os.h b/lib/NintendoSDK/include/nn/os.h new file mode 100644 index 00000000..d6e71161 --- /dev/null +++ b/lib/NintendoSDK/include/nn/os.h @@ -0,0 +1,272 @@ +/** + * @file os.h + * @brief Operating System implementations. + */ + +#pragma once + +#include + +#include +#include + +namespace nn { +namespace os { +namespace detail { +struct InternalCriticalSection { + u32 Image; +}; + +struct InternalConditionVariable { + u32 Image; +}; +} // namespace detail + +typedef u64 Tick; + +struct LightEventType { + std::aligned_storage_t<0xc, 4> storage; +}; + +// https://github.com/misson20000/nn-types/blob/master/nn_os.h +struct EventType { + nn::os::EventType* _x0; + nn::os::EventType* _x8; + bool isSignaled; + bool initiallySignaled; + bool shouldAutoClear; + bool isInit; + u32 signalCounter; + u32 signalCounter2; + nn::os::detail::InternalCriticalSection crit; + nn::os::detail::InternalConditionVariable condvar; +}; +typedef EventType Event; + +enum EventClearMode { EventClearMode_ManualClear, EventClearMode_AutoClear }; + +// https://github.com/misson20000/nn-types/blob/master/nn_os.h +struct ThreadType { + u64 field_8; + u64 field_10; + u64 field_18; + char field_20[32]; + uint32_t thread_status; + char field_41; + u16 field_42; + uint32_t thread_prio_shift; + uint64_t thread_stack_base_addr; + uint64_t thread_stack_base_addr_mirror; + uint64_t thread_stack_size; + uint64_t thread_param; + uint64_t thread_func; + u64 field_70; + u64 field_78; + u64 field_80; + char field_88[0x100]; + char thread_name[0x20]; + const char* thread_name_addr; + nn::os::detail::InternalCriticalSection crit; + nn::os::detail::InternalConditionVariable condvar; + u32 thread_handle; +}; +#ifdef SWITCH +static_assert(sizeof(ThreadType) == 0x1C0, "Wrong size"); +#endif + +struct MessageQueueType { + u64 _x0; + u64 _x8; + u64 _x10; + u64 _x18; + void* Buffer; + u32 MaxCount; + u32 Count; + u32 Offset; + bool Initialized; + detail::InternalCriticalSection _x38; + detail::InternalConditionVariable _x3C; + detail::InternalConditionVariable _x40; +}; + +struct ConditionVariableType {}; + +struct SemaphoreType { + std::aligned_storage_t<0x28, 8> storage; +}; + +struct SystemEvent; +struct SystemEventType; + +// ARG +void SetHostArgc(s32); +s32 GetHostArgc(); +void SetHostArgv(char**); +char** GetHostArgv(); + +// MEMORY +void InitializeVirtualAddressMemory(); +Result AllocateAddressRegion(u64*, u64); +Result AllocateMemory(u64*, u64); +Result AllocateMemoryPages(u64, u64); +void AllocateMemoryBlock(u64*, u64); +void FreeMemoryBlock(u64, u64); +void SetMemoryHeapSize(u64); + +// MUTEX +struct MutexType { + u8 _state; + bool _isRecursive; + int _lockLevel; + int _nestCount; + nn::os::ThreadType* _ownerThread; + union { + int32_t _mutexImage[1]; + nn::os::detail::InternalCriticalSection _mutex; + }; +}; + +void InitializeMutex(nn::os::MutexType*, bool, s32); +void FinalizeMutex(nn::os::MutexType*); +void LockMutex(nn::os::MutexType*); +bool TryLockMutex(nn::os::MutexType*); +void UnlockMutex(nn::os::MutexType*); +bool IsMutexLockedByCurrentThread(nn::os::MutexType const*); + +// QUEUE +void InitializeMessageQueue(nn::os::MessageQueueType*, u64* buf, u64 queueCount); +void FinalizeMessageQueue(nn::os::MessageQueueType*); + +bool TrySendMessageQueue(MessageQueueType*, u64); +void SendMessageQueue(MessageQueueType*, u64); +bool TimedSendMessageQueue(MessageQueueType*, u64, nn::TimeSpan); + +bool TryReceiveMessageQueue(u64* out, MessageQueueType*); +void ReceiveMessageQueue(u64* out, MessageQueueType*); +bool TimedReceiveMessageQueue(u64* out, MessageQueueType*, nn::TimeSpan); + +bool TryPeekMessageQueue(u64*, MessageQueueType const*); +void PeekMessageQueue(u64*, MessageQueueType const*); +bool TimedPeekMessageQueue(u64*, MessageQueueType const*); + +bool TryJamMessageQueue(nn::os::MessageQueueType*, u64); +void JamMessageQueue(nn::os::MessageQueueType*, u64); +bool TimedJamMessageQueue(nn::os::MessageQueueType*, u64, nn::TimeSpan); + +// CONDITION VARIABLE +void InitializeConditionVariable(ConditionVariableType*); +void FinalizeConditionVariable(ConditionVariableType*); + +void SignalConditionVariable(ConditionVariableType*); +void BroadcastConditionVariable(ConditionVariableType*); +void WaitConditionVariable(ConditionVariableType*); +u8 TimedWaitConditionVariable(ConditionVariableType*, MutexType*, nn::TimeSpan); + +// THREAD +Result CreateThread(nn::os::ThreadType*, void (*)(void*), void* arg, void* srcStack, u64 stackSize, + s32 priority, s32 coreNum); +Result CreateThread(nn::os::ThreadType*, void (*)(void*), void* arg, void* srcStack, u64 stackSize, + s32 priority); +void DestroyThread(nn::os::ThreadType*); +void StartThread(nn::os::ThreadType*); +void SetThreadName(nn::os::ThreadType*, char const* threadName); +void SetThreadNamePointer(nn::os::ThreadType*, char const*); +char* GetThreadNamePointer(nn::os::ThreadType const*); +nn::os::ThreadType* GetCurrentThread(); +void GetCurrentStackInfo(uintptr_t* stack_addr, size_t* stack_size); +s32 ChangeThreadPriority(nn::os::ThreadType* thread, s32 priority); +s32 GetThreadPriority(nn::os::ThreadType const* thread); +u64 GetThreadId(const nn::os::ThreadType* thread); +void YieldThread(); +void SuspendThread(nn::os::ThreadType*); +void ResumeThread(nn::os::ThreadType*); +void SleepThread(nn::TimeSpan); +void WaitThread(nn::os::ThreadType*); +void SetThreadCoreMask(nn::os::ThreadType*, int, u64 mask); + +// EVENTS +void InitializeEvent(EventType*, bool initiallySignaled, EventClearMode eventClearMode); +void FinalizeEvent(EventType*); +void SignalEvent(EventType*); +void WaitEvent(EventType*); +bool TryWaitEvent(EventType*); +bool TimedWaitEvent(EventType*, nn::TimeSpan); +void ClearEvent(EventType*); + +// LIGHT EVENTS +void InitializeLightEvent(LightEventType*, bool initiallySignaled, EventClearMode eventClearMode); +void FinalizeLightEvent(LightEventType*); +void SignalLightEvent(LightEventType*); +void WaitLightEvent(LightEventType*); +bool TimedWaitLightEvent(LightEventType*, nn::TimeSpan); +void ClearLightEvent(LightEventType*); + +TimeSpan ConvertToTimeSpan(Tick ticks); + +// SEMAPHORES +void InitializeSemaphore(SemaphoreType* semaphore, s32 initial_count, s32 max_count); +void FinalizeSemaphore(SemaphoreType* semaphore); +void AcquireSemaphore(SemaphoreType* semaphore); +bool TryAcquireSemaphore(SemaphoreType* semaphore); +void ReleaseSemaphore(SemaphoreType* semaphore); + +// EXCEPTION HANDLING +typedef union { + u64 x; ///< 64-bit AArch64 register view. + u32 w; ///< 32-bit AArch64 register view. + u32 r; ///< AArch32 register view. +} CpuRegister; +/// Armv8 NEON register. + +typedef union { + u128 v; ///< 128-bit vector view. + double d; ///< 64-bit double-precision view. + float s; ///< 32-bit single-precision view. +} FpuRegister; + +struct UserExceptionInfo { + u32 ErrorDescription; ///< See \ref ThreadExceptionDesc. + u32 pad[3]; + + CpuRegister CpuRegisters[29]; ///< GPRs 0..28. Note: also contains AArch32 registers. + CpuRegister FP; ///< Frame pointer. + CpuRegister LR; ///< Link register. + CpuRegister SP; ///< Stack pointer. + CpuRegister PC; ///< Program counter (elr_el1). + + u64 padding; + + FpuRegister FpuRegisters[32]; ///< 32 general-purpose NEON registers. + + u32 PState; ///< pstate & 0xFF0FFE20 + u32 AFSR0; + u32 AFSR1; + u32 ESR; + + CpuRegister FAR; ///< Fault Address Register. +}; +void SetUserExceptionHandler(void (*)(UserExceptionInfo*), void*, ulong, UserExceptionInfo*); + +// OTHER +void GenerateRandomBytes(void*, u64); +nn::os::Tick GetSystemTick(); +nn::os::Tick GetSystemTickFrequency(); +u64 GetThreadAvailableCoreMask(); +void SetMemoryHeapSize(u64 size); + +// Thread-local storage +struct TlsSlot { + u32 slot; +}; +Result AllocateTlsSlot(TlsSlot* slot_out, void (*)(u64)); +void FreeTlsSlot(TlsSlot slot); +u64 GetTlsValue(TlsSlot slot); +void SetTlsValue(TlsSlot slot, u64 value); +u32 GetCurrentCoreNumber(); + +namespace detail { +extern s32 g_CommandLineParameter; +extern char** g_CommandLineParameterArgv; +}; // namespace detail +}; // namespace os +}; // namespace nn diff --git a/lib/NintendoSDK/include/nn/prepo.h b/lib/NintendoSDK/include/nn/prepo.h new file mode 100644 index 00000000..0f927d33 --- /dev/null +++ b/lib/NintendoSDK/include/nn/prepo.h @@ -0,0 +1,62 @@ +#pragma once + +#include + +namespace nn::account { +class Uid; +} + +namespace nn::prepo { + +namespace detail { +class PlayReportGenerator { +public: + PlayReportGenerator() = default; + void Initialize(); + +private: + void* m_Data = nullptr; +}; +} // namespace detail + +enum class TransmissionStatus {}; + +class PlayReport { +public: + PlayReport(); + explicit PlayReport(const char* event_id); + + Result SetEventId(const char* event_id); + void SetBuffer(void* buffer, size_t size); + void Clear(); + + Result Add(const char* key, s64 value); + Result Add(const char* key, f64 value); + Result Add(const char* key, const char* value); + + Result Save(); + Result Save(const account::Uid& uid); + + s32 GetCount() const; + + static u32 CalcBufferSize(s32 num_entries) { return size_t(0x82) * num_entries + 3; } + +private: + char m_EventId[32]; + void* m_Buffer; + size_t m_BufferSize; + detail::PlayReportGenerator m_Generator; +}; + +void Initialize(); + +Result RequestImmediateTransmission(); +Result GetTransmissionStatus(TransmissionStatus* status); + +Result ClearStorage(); +Result SetOperationMode(s64 mode); +Result IsUserAgreementCheckEnabled(bool* enabled); +Result SetUserAgreementCheckEnabled(bool enabled); +Result GetStorageUsage(s64*, s64*); + +} // namespace nn::prepo diff --git a/lib/NintendoSDK/include/nn/ro.h b/lib/NintendoSDK/include/nn/ro.h new file mode 100644 index 00000000..92fe4f3b --- /dev/null +++ b/lib/NintendoSDK/include/nn/ro.h @@ -0,0 +1,115 @@ +/** + * @file ro.h + * @brief Dynamic module API. + */ + +#pragma once + +#include + +namespace nn { +namespace ro { + +namespace rtld { +struct ModuleObject; // TODO find this object and implement it. Original `#include` name: + // ModuleObject.hpp, full path name: nn::ro::rtld::ModuleObject +} + +class Module { +public: + rtld::ModuleObject* ModuleObject; + u32 State; + void* NroPtr; + void* BssPtr; + void* _x20; + void* SourceBuffer; + char Name[256]; /* Created by retype action */ + u8 _x130; + u8 _x131; + bool isLoaded; // bool +}; + +struct ModuleId { + u8 build_id[0x20]; +}; + +struct NroHeader { + u32 entrypoint_insn; + u32 mod_offset; + u8 _x8[0x8]; + u32 magic; + u8 _x14[0x4]; + u32 size; + u8 reserved_1C[0x4]; + u32 text_offset; + u32 text_size; + u32 ro_offset; + u32 ro_size; + u32 rw_offset; + u32 rw_size; + u32 bss_size; + u8 _x3C[0x4]; + ModuleId module_id; + u8 _x60[0x20]; +}; +static_assert(sizeof(NroHeader) == 0x80, "NroHeader definition!"); + +struct ProgramId { + u64 value; + + inline explicit operator u64() const { return this->value; } +}; + +struct NrrHeader { + u32 magic; + u8 _x4[0xC]; + u64 program_id_mask; + u64 program_id_pattern; + u8 _x20[0x10]; + u8 modulus[0x100]; + u8 fixed_key_signature[0x100]; + u8 nrr_signature[0x100]; + ProgramId program_id; + u32 size; + u8 type; /* 7.0.0+ */ + u8 _x33D[3]; + u32 hashes_offset; + u32 num_hashes; + u8 _x348[8]; +}; +static_assert(sizeof(NrrHeader) == 0x350, "NrrHeader definition!"); + +struct RegistrationInfo { + enum State { + State_Unregistered, + State_Registered, + }; + State state; + NrrHeader* nrrPtr; + u64 _x10; + u64 _x18; +}; + +enum BindFlag { + BindFlag_Now = BIT(0), + BindFlag_Lazy = BIT(1), +}; + +Result Initialize(); + +Result LookupSymbol(uintptr_t* pOutAddress, const char* name); + +Result LookupModuleSymbol(uintptr_t* pOutAddress, const Module* pModule, const char* name); +Result LoadModule(Module* pOutModule, const void* pImage, void* buffer, size_t bufferSize, + int flag); +// Result LoadModule(Module *pOutModule, const void *pImage, void *buffer, size_t bufferSize,int +// flag, bool isNotReferenced); +Result UnloadModule(Module*); +Result GetBufferSize(size_t*, const void*); + +Result RegisterModuleInfo(RegistrationInfo*, void const*); +Result RegisterModuleInfo(RegistrationInfo*, void const*, u32); +Result UnregisterModuleInfo(RegistrationInfo*, void const*); +}; // namespace ro + +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/settings.h b/lib/NintendoSDK/include/nn/settings.h new file mode 100644 index 00000000..6278e355 --- /dev/null +++ b/lib/NintendoSDK/include/nn/settings.h @@ -0,0 +1,31 @@ +#pragma once + +namespace nn { +namespace settings { +enum Language { + Language_Japanese, + Language_English, + Language_French, + Language_German, + Language_Italian, + Language_Spanish, + Language_Chinese, + Language_Korean, + Language_Dutch, + Language_Portuguese, + Language_Russian, + Language_Taiwanese, + Language_BritishEnglish, + Language_CanadianFrench, + Language_LatinAmericanSpanish +}; + +struct LanguageCode { + char code[0x8]; + + static LanguageCode Make(nn::settings::Language); +}; + +bool operator==(nn::settings::LanguageCode const&, nn::settings::LanguageCode const&); +}; // namespace settings +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/sf/hipc.h b/lib/NintendoSDK/include/nn/sf/hipc.h new file mode 100644 index 00000000..cafe910a --- /dev/null +++ b/lib/NintendoSDK/include/nn/sf/hipc.h @@ -0,0 +1,15 @@ +#pragma once + +#include + +namespace nn::sf::hipc { +void* GetMessageBufferOnTls(); + +Result InitializeHipcServiceResolution(); +Result ConnectToHipcService(svc::Handle*, const char*); +Result FinalizeHipcServiceResolution(); + +Result SendSyncRequest(svc::Handle, void*, u64); +Result CloseClientSessionHandle(svc::Handle); + +} // namespace nn::sf::hipc diff --git a/lib/NintendoSDK/include/nn/socket.h b/lib/NintendoSDK/include/nn/socket.h new file mode 100644 index 00000000..d11a1c4c --- /dev/null +++ b/lib/NintendoSDK/include/nn/socket.h @@ -0,0 +1,29 @@ +/** + * @file socket.h + * @brief Functions for opening sockets for wireless communication. + */ + +#pragma once + +#include +#include + +namespace nn { +namespace socket { +struct InAddr { + u32 addr; +}; + +Result Initialize(void* pool, ulong poolSize, ulong allocPoolSize, int concurLimit); +Result Finalize(); +s32 SetSockOpt(s32 socket, s32 socketLevel, s32 option, void const*, u32 len); +u64 Send(s32 socket, void const* buffer, u64 bufferLength, s32 flags); +s32 Socket(s32 domain, s32 type, s32 proto); +u16 InetHtons(u16); +u32 InetAton(const char* str, InAddr*); +u32 Connect(s32 socket, const sockaddr* addr, u32 addrLen); +u32 Bind(s32 socket, const sockaddr* addr, u32 addrLen); +u32 Listen(s32 socket, s32 backlog); +u32 Accept(s32 socket, sockaddr* addrOut, u32* addrLenOut); +} // namespace socket +} // namespace nn diff --git a/lib/NintendoSDK/include/nn/ssl.h b/lib/NintendoSDK/include/nn/ssl.h new file mode 100644 index 00000000..e2bb9e20 --- /dev/null +++ b/lib/NintendoSDK/include/nn/ssl.h @@ -0,0 +1,26 @@ +/** + * @file ssl.h + * @brief SSL implementation. + */ + +#pragma once + +#include + +namespace nn { +namespace ssl { +enum CertificateFormat { PEM = 0x01, DER = 0x02 }; + +class Context { +public: + enum SslVersion { Auto = 0x01, v10 = 0x08, v11 = 0x10, v12 = 0x20 }; + + Result Create(nn::ssl::Context::SslVersion version); + Result ImportServerPki(u64*, char const* certData, u32 certSize, + nn::ssl::CertificateFormat certFormat); +}; + +Result Initialize(); +Result Finalize(); +}; // namespace ssl +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/svc.h b/lib/NintendoSDK/include/nn/svc.h new file mode 100644 index 00000000..9d7f7ac9 --- /dev/null +++ b/lib/NintendoSDK/include/nn/svc.h @@ -0,0 +1,16 @@ +#pragma once + +#include + +namespace nn::svc { +struct Handle { + u32 handle; + + Handle(u32 h) { handle = h; } + + Handle() : Handle(0) {} + + operator u32() const { return handle; } +}; + +} // namespace nn::svc diff --git a/lib/NintendoSDK/include/nn/time.h b/lib/NintendoSDK/include/nn/time.h new file mode 100644 index 00000000..3d668fd5 --- /dev/null +++ b/lib/NintendoSDK/include/nn/time.h @@ -0,0 +1,82 @@ +/** + * @file time.h + * @brief Time implementation. + */ + +#pragma once + +#include + +namespace nn { +class TimeSpan { +public: + u64 nanoseconds; + + static TimeSpan FromNanoSeconds(u64 nanoSeconds) { + TimeSpan ret; + ret.nanoseconds = nanoSeconds; + return ret; + } + + static TimeSpan FromSeconds(u64 seconds) { + return FromNanoSeconds(seconds * 1000 * 1000 * 1000); + } + static TimeSpan FromMinutes(u64 minutes) { + return FromNanoSeconds(minutes * 1000 * 1000 * 1000 * 60); + } + static TimeSpan FromHours(u64 hours) { + return FromNanoSeconds(hours * 1000 * 1000 * 1000 * 60 * 60); + } + static TimeSpan FromDays(u64 days) { + return FromNanoSeconds(days * 1000 * 1000 * 1000 * 60 * 60 * 24); + } +}; + +namespace time { + +Result Initialize(); +bool IsInitialized(); + +struct CalendarTime { + s16 year; + s8 month; + s8 day; + s8 hour; + s8 minute; + s8 second; +}; + +enum DayOfTheWeek { Sunday, Monday, Tuesday, Wednesday, Thursday, Friday, Saturday }; + +struct TimeZone { + char standardTimeName[0x8]; + bool _9; // daylight savings or something? + s32 utcOffset; // in seconds +}; + +struct CalendarAdditionalInfo { + nn::time::DayOfTheWeek dayOfTheWeek; + s32 dayofYear; + nn::time::TimeZone timeZone; +}; + +struct PosixTime { + u64 time; +}; + +class StandardUserSystemClock { +public: + static Result GetCurrentTime(nn::time::PosixTime*); +}; + +struct TimeZoneRule; // shrug + +Result ToCalendarTime(nn::time::CalendarTime*, nn::time::CalendarAdditionalInfo*, + nn::time::PosixTime const&); +Result ToCalendarTime(nn::time::CalendarTime*, nn::time::CalendarAdditionalInfo*, + nn::time::PosixTime const&, nn::time::TimeZoneRule const&); +Result ToPosixTime(int*, PosixTime*, int, const CalendarTime&); +CalendarTime ToCalendarTimeInUtc(const PosixTime&); +PosixTime ToPosixTimeFromUtc(const CalendarTime&); +}; // namespace time +}; // namespace nn diff --git a/lib/NintendoSDK/include/nn/types.h b/lib/NintendoSDK/include/nn/types.h new file mode 100644 index 00000000..07457006 --- /dev/null +++ b/lib/NintendoSDK/include/nn/types.h @@ -0,0 +1,23 @@ +#pragma once + +#include +#include +#include + +using u8 = std::uint8_t; +using u16 = std::uint16_t; +using u32 = std::uint32_t; +using u64 = std::uint64_t; +using u128 = __uint128_t; + +using s8 = std::int8_t; +using s16 = std::int16_t; +using s32 = std::int32_t; +using s64 = std::int64_t; + +using f32 = float; +using f64 = double; + +using char16 = char16_t; +using size_t = std::size_t; +using ulong = u64; diff --git a/lib/NintendoSDK/include/nn/ui2d/Layout.h b/lib/NintendoSDK/include/nn/ui2d/Layout.h new file mode 100644 index 00000000..1ef4a5af --- /dev/null +++ b/lib/NintendoSDK/include/nn/ui2d/Layout.h @@ -0,0 +1,49 @@ +/** + * @file Layout.h + * @brief UI Layout implementation. + */ + +#pragma once + +#include + +namespace nn { +namespace ui2d { +class AnimTransform; +class Pane; + +class Layout { +public: + Layout(); + + virtual ~Layout(); + + virtual void DeleteAnimTransform(nn::ui2d::AnimTransform*); + virtual void BindAnimation(nn::ui2d::AnimTransform*); + virtual void UnbindAnimation(nn::ui2d::AnimTransform*); + virtual void UnbindAnimation(nn::ui2d::Pane*); + virtual void UnbindAllAnimation(); + + virtual void Animate(); + virtual void UpdateAnimFrame(f32 frame); + virtual void AnimateAndUpdateAnimFrame(f32 frame); + + void SetAllocator(void* (*)(u64, u64, void*), void (*)(void*, void*), void*); + void AllocateMemory(u64, u64); + void AllocateMemory(u64); + void FreeMemory(void* src); + + u64 _10; + u64 _18; + u64 _20; + u64 _28; + u64 _30; + + u64 _40; + u64 _48; + u64 _50; + u64 _58; + u64 _60; +}; +}; // namespace ui2d +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/ui2d/Material.h b/lib/NintendoSDK/include/nn/ui2d/Material.h new file mode 100644 index 00000000..d9db2d5f --- /dev/null +++ b/lib/NintendoSDK/include/nn/ui2d/Material.h @@ -0,0 +1,29 @@ +/** + * @file Material.h + * @brief UI Material implementation. + */ + +#pragma once + +#include + +namespace nn { +namespace ui2d { +class AnimTransform; +class BuildResultInformation; +struct UserShaderInformation; + +class Material { +public: + Material(); + + void Initialize(); + void ReserveMem(s32, s32, s32, s32, bool, s32, bool, s32, bool, bool); + void SetupUserShaderConstantBufferInformation(nn::ui2d::UserShaderInformation const&); + + virtual ~Material(); + virtual void BindAnimation(nn::ui2d::AnimTransform*); + virtual void UnbindAnimation(nn::ui2d::AnimTransform*); +}; +}; // namespace ui2d +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/ui2d/Pane.h b/lib/NintendoSDK/include/nn/ui2d/Pane.h new file mode 100644 index 00000000..54fc7a32 --- /dev/null +++ b/lib/NintendoSDK/include/nn/ui2d/Pane.h @@ -0,0 +1,75 @@ +/** + * @file Pane.h + * @brief Base UI panel. + */ + +#pragma once + +#include "sead/runtime.h" //FIXME this definitely is wrong +#include "types.h" + +namespace nn { +namespace ui2d { +class AnimTransform; +class Layout; + +class Pane { +public: + Pane(); + Pane(nn::ui2d::Pane const&); + + virtual ~Pane(); + + virtual sead::RuntimeTypeInfo::Interface* GetRuntimeTypeInfo() const; + virtual s32 GetVertexColor(s32); + virtual u8 GetColorElement(s32); + virtual void SetColorElement(u32, u8); + virtual u8 GetVertexColorElement(s32); + virtual void SetVertexColorElement(u32, u8); + virtual u32 GetMaterialCount() const; + virtual u64* GetMaterial(s32) const; + + virtual void BindAnimation(nn::ui2d::AnimTransform*, bool, bool); + virtual void UnbindAnimation(nn::ui2d::AnimTransform*, bool); + + void Initialize(); + void SetName(char const*); + void SetUserData(char const*); + void AppendChild(nn::ui2d::Pane*); + void PrependChild(nn::ui2d::Pane*); + void InsertChild(nn::ui2d::Pane*, nn::ui2d::Pane*); + void RemoveChild(nn::ui2d::Pane*); + void GetVertexPos() const; + + u64 _8; + u64 _10; + u64 _18; + u64 _20; + u64 _28; + u64 _30; + u64 _38; + u64 _40; + u32 _48; + u32 _4C; + u64 _50; + u16 _58; + u16 _5A; + u32 _5C; + u64 _60; + nn::ui2d::Layout* mLayout; // _68 + u128 _70; + u128 _80; + u128 _90; + u64 _A0; + u64 _A8; + u64 _B0; + u64 _B8; + u64 _C0; + u64 _C8; + u64 _D0; + u16 _D8; + u16 _DA; + u32 _DC; +}; +}; // namespace ui2d +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/ui2d/Parts.h b/lib/NintendoSDK/include/nn/ui2d/Parts.h new file mode 100644 index 00000000..11c3fa68 --- /dev/null +++ b/lib/NintendoSDK/include/nn/ui2d/Parts.h @@ -0,0 +1,29 @@ +/** + * @file Parts.h + * @brief Layout parts. + */ + +#pragma once + +#include + +namespace nn { +namespace ui2d { +struct BuildArgSet; +struct ResParts; + +class Parts : nn::ui2d::Pane { +public: + Parts(); + Parts(nn::ui2d::ResParts const*, nn::ui2d::ResParts const*, nn::ui2d::BuildArgSet const&); + Parts(nn::ui2d::Parts const&); + + virtual ~Parts(); + virtual sead::RuntimeTypeInfo::Interface* GetRuntimeTypeInfo() const; + + u64 _E0; + u64 _E8; + u32 _F0; +}; +}; // namespace ui2d +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/ui2d/detail/TexCoordArray.h b/lib/NintendoSDK/include/nn/ui2d/detail/TexCoordArray.h new file mode 100644 index 00000000..522b5838 --- /dev/null +++ b/lib/NintendoSDK/include/nn/ui2d/detail/TexCoordArray.h @@ -0,0 +1,38 @@ +/** + * @file TexCoordArray.h + * @brief Texture coordinate array implementation. + */ + +#pragma once + +#include + +namespace nn { + +namespace util { +struct Float2; +} + +namespace ui2d { +class Layout; + +namespace detail { +class TexCoordArray { +public: + void Initialize(); + void Free(); + void Reserve(s32); + void SetSize(s32 size); + void GetCoord(nn::util::Float2*, s32) const; + void SetCoord(s32, nn::util::Float2 const*); + void Copy(void const*, s32); + bool CompareCopiedInstanceTest(nn::ui2d::detail::TexCoordArray const&) const; + + u16 _0; + u16 _2; + u32 _4; // padding? + nn::ui2d::Layout* mLayout; // _8 +}; +}; // namespace detail +}; // namespace ui2d +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/util.h b/lib/NintendoSDK/include/nn/util.h new file mode 100644 index 00000000..9a1023be --- /dev/null +++ b/lib/NintendoSDK/include/nn/util.h @@ -0,0 +1,60 @@ +/** + * @file util.h + * @brief Helper functions for OS functionality. + */ + +#pragma once + +#include + +namespace nn { +namespace util { +struct Unorm8x4 { + u8 elements[0x4]; +}; + +enum CharacterEncodingResult { Success, BadLength, InvalidFormat }; + +CharacterEncodingResult PickOutCharacterFromUtf8String(char*, char const** str); +CharacterEncodingResult ConvertCharacterUtf8ToUtf32(u32* dest, char const* src); +CharacterEncodingResult ConvertStringUtf16NativeToUtf8(char*, s32, u16 const*, s32); +CharacterEncodingResult ConvertStringUtf8ToUtf16Native(u16*, s32, char const*, s32); + +class RelocationTable { +public: + void Relocate(); + void Unrelocate(); + + s32 mMagic; // _0 + u32 mPosition; // _4 + s32 mSectionCount; // _8 +}; + +class BinaryFileHeader { +public: + bool IsValid(s64 packedSig, s32 majorVer, s32 minorVer, s32 microVer) const; + bool IsRelocated() const; + bool IsEndianReverse() const; + nn::util::RelocationTable* GetRelocationTable(); + + s32 mMagic; // _0 + u32 mSig; // _4 + u8 mVerMicro; // _8 + u8 mVerMinor; // _9 + u16 mVerMajor; // _A + u16 mBOM; // _C + u8 mAlignment; // _E + u8 mTargetAddrSize; // _F + u32 mFileNameOffset; // _10 + u16 mFlag; // _14 + u16 mFirstBlockOffs; // _16 + u32 mRelocationTableOffs; // _18 + u32 mSize; // _1C +}; + +template +struct BitFlagSet {}; +}; // namespace util + +void ReferSymbol(void const*); +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/util/Float2.h b/lib/NintendoSDK/include/nn/util/Float2.h new file mode 100644 index 00000000..39a231b9 --- /dev/null +++ b/lib/NintendoSDK/include/nn/util/Float2.h @@ -0,0 +1,19 @@ +/** + * @file Float2.h + * @brief Some odd float implementation that I don't understand yet... + */ + +#pragma once + +#include + +namespace nn { +namespace util { +struct Float2 { + u64 _0; + u64 _8; + u64 _10; + u64 _18; +}; +}; // namespace util +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/vfx/Config.h b/lib/NintendoSDK/include/nn/vfx/Config.h new file mode 100644 index 00000000..86c17f21 --- /dev/null +++ b/lib/NintendoSDK/include/nn/vfx/Config.h @@ -0,0 +1,15 @@ +/** + * @file Config.h + * @brief VFX configuration. + */ + +#pragma once + +namespace nn { +namespace vfx { +class Config { +public: + virtual ~Config(); +}; +}; // namespace vfx +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/vfx/Heap.h b/lib/NintendoSDK/include/nn/vfx/Heap.h new file mode 100644 index 00000000..c6aa91c1 --- /dev/null +++ b/lib/NintendoSDK/include/nn/vfx/Heap.h @@ -0,0 +1,17 @@ +/** + * @file Heap.h + * @brief VFX heap implementation. + */ + +#pragma once + +#include + +namespace nn { +namespace vfx { +class Heap { +public: + virtual ~Heap(); +}; +}; // namespace vfx +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/vfx/System.h b/lib/NintendoSDK/include/nn/vfx/System.h new file mode 100644 index 00000000..7e1ade46 --- /dev/null +++ b/lib/NintendoSDK/include/nn/vfx/System.h @@ -0,0 +1,27 @@ +/** + * @file System.h + * @brief VFX system implementation. + */ + +#pragma once + +#include +#include + +// this class is massive +namespace nn { +namespace vfx { + +struct Heap; + +class System { +public: + System(nn::vfx::Config const&); + + virtual ~System(); + virtual void Initialize(nn::vfx::Heap*, nn::vfx::Heap*, nn::vfx::Config const&); + + u8 _0[0x1700]; +}; +}; // namespace vfx +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nn/vi.h b/lib/NintendoSDK/include/nn/vi.h new file mode 100644 index 00000000..e1e31829 --- /dev/null +++ b/lib/NintendoSDK/include/nn/vi.h @@ -0,0 +1,40 @@ +/** + * @file vi.h + * @brief Visual interface implementation. + */ + +#pragma once + +#include + +namespace nn { + +namespace os { +struct SystemEventType; +} + +namespace vi { +class Display; +class Layer; +class NativWindow; +struct DisplayInfo { + static const int maxNameLen = 64; + char name[maxNameLen]; + bool hasLayerLimit; + int64_t maxLayers; + int64_t maxWidth; + int64_t maxHeight; +}; + +enum ScalingMode { None, Exact, FitLayer, ScaleAndCrop, PreserveAspectRatio }; + +void Initialize(); +Result OpenDefaultDisplay(nn::vi::Display** outDisp); +Result CreateLayer(nn::vi::Layer** outLayer, nn::vi::Display* disp); +Result SetLayerScalingMode(nn::vi::Layer* layer, nn::vi::ScalingMode scalingMode); +Result GetDisplayVsyncEvent(nn::os::SystemEventType*, nn::vi::Display*); +Result GetNativeWindow(void** window, nn::vi::Layer*); +Result GetLatestFrameNumber(u64* pOutFrameNumber, const Layer* pLayer); +int ListDisplays(DisplayInfo* outDisplays, int count); +}; // namespace vi +}; // namespace nn \ No newline at end of file diff --git a/lib/NintendoSDK/include/nv.h b/lib/NintendoSDK/include/nv.h new file mode 100644 index 00000000..aaac8ba5 --- /dev/null +++ b/lib/NintendoSDK/include/nv.h @@ -0,0 +1,13 @@ +#pragma once + +#include + +namespace nv { +void SetGraphicsAllocator(void* (*allocator)(size_t, size_t, void*), + void (*deallocator)(void*, void*), + void* (*reallocator)(void*, size_t, void*), void* unk); +void SetGraphicsDevtoolsAllocator(void* (*allocator)(size_t, size_t, void*), + void (*deallocator)(void*, void*), + void* (*reallocator)(void*, size_t, void*), void* unk); +void InitializeGraphics(void* address, size_t size); +} // namespace nv diff --git a/lib/NintendoSDK/include/nvn/nvn.h b/lib/NintendoSDK/include/nvn/nvn.h new file mode 100644 index 00000000..e462944d --- /dev/null +++ b/lib/NintendoSDK/include/nvn/nvn.h @@ -0,0 +1,6 @@ +#pragma once + +#include +#include + +NVNdummyProc nvnBootstrapLoader(const char* name); diff --git a/lib/NintendoSDK/include/nvn/nvn_api.h b/lib/NintendoSDK/include/nvn/nvn_api.h new file mode 100644 index 00000000..6bf5d168 --- /dev/null +++ b/lib/NintendoSDK/include/nvn/nvn_api.h @@ -0,0 +1,1646 @@ +// AUTOGENERATED DO NOT EDIT +#pragma once + +#ifdef __cplusplus +extern "C" { +#endif + +#include +#include +#include + +// Function definitions +typedef void (*nvnDeviceBuilderSetDefaultsFunction)(NVNdeviceBuilder*); +typedef void (*nvnDeviceBuilderSetFlagsFunction)(NVNdeviceBuilder*, NVNdeviceFlagBits); +typedef bool (*nvnDeviceInitializeFunction)(NVNdevice*, const NVNdeviceBuilder*); +typedef void (*nvnDeviceFinalizeFunction)(NVNdevice*); +typedef void (*nvnDeviceSetDebugLabelFunction)(NVNdevice*, const char*); +typedef NVNdummyProc (*nvnDeviceGetProcAddressFunction)(const NVNdevice*, const char*); +typedef void (*nvnDeviceGetIntegerFunction)(const NVNdevice*, NVNdeviceInfo, int*); +typedef uint64_t (*nvnDeviceGetCurrentTimestampInNanosecondsFunction)(const NVNdevice*); +typedef void (*nvnDeviceSetIntermediateShaderCacheFunction)(NVNdevice*, int); +typedef NVNtextureHandle (*nvnDeviceGetTextureHandleFunction)(const NVNdevice*, int, int); +typedef NVNtextureHandle (*nvnDeviceGetTexelFetchHandleFunction)(const NVNdevice*, int); +typedef NVNimageHandle (*nvnDeviceGetImageHandleFunction)(const NVNdevice*, int); +typedef void (*nvnDeviceInstallDebugCallbackFunction)(NVNdevice*, const NVNdebugCallback, void*, + bool); +typedef NVNdebugDomainId (*nvnDeviceGenerateDebugDomainIdFunction)(const NVNdevice*, const char*); +typedef void (*nvnDeviceSetWindowOriginModeFunction)(NVNdevice*, NVNwindowOriginMode); +typedef void (*nvnDeviceSetDepthModeFunction)(NVNdevice*, NVNdepthMode); +typedef bool (*nvnDeviceRegisterFastClearColorFunction)(NVNdevice*, const float*, NVNformat); +typedef bool (*nvnDeviceRegisterFastClearColoriFunction)(NVNdevice*, const int*, NVNformat); +typedef bool (*nvnDeviceRegisterFastClearColoruiFunction)(NVNdevice*, const uint32_t*, NVNformat); +typedef bool (*nvnDeviceRegisterFastClearDepthFunction)(NVNdevice*, float); +typedef NVNwindowOriginMode (*nvnDeviceGetWindowOriginModeFunction)(const NVNdevice*); +typedef NVNdepthMode (*nvnDeviceGetDepthModeFunction)(const NVNdevice*); +typedef uint64_t (*nvnDeviceGetTimestampInNanosecondsFunction)(const NVNdevice*, + const NVNcounterData*); +typedef void (*nvnDeviceApplyDeferredFinalizesFunction)(NVNdevice*, int); +typedef void (*nvnDeviceFinalizeCommandHandleFunction)(NVNdevice*, NVNcommandHandle); +typedef void (*nvnDeviceWalkDebugDatabaseFunction)(const NVNdevice*, NVNdebugObjectType, + NVNwalkDebugDatabaseCallback, void*); +typedef NVNseparateTextureHandle (*nvnDeviceGetSeparateTextureHandleFunction)(const NVNdevice*, + int); +typedef NVNseparateSamplerHandle (*nvnDeviceGetSeparateSamplerHandleFunction)(const NVNdevice*, + int); +typedef bool (*nvnDeviceIsExternalDebuggerAttachedFunction)(const NVNdevice*); +typedef NVNqueueGetErrorResult (*nvnQueueGetErrorFunction)(NVNqueue*, NVNqueueErrorInfo*); +typedef size_t (*nvnQueueGetTotalCommandMemoryUsedFunction)(NVNqueue*); +typedef size_t (*nvnQueueGetTotalControlMemoryUsedFunction)(NVNqueue*); +typedef size_t (*nvnQueueGetTotalComputeMemoryUsedFunction)(NVNqueue*); +typedef void (*nvnQueueResetMemoryUsageCountsFunction)(NVNqueue*); +typedef void (*nvnQueueBuilderSetDeviceFunction)(NVNqueueBuilder*, NVNdevice*); +typedef void (*nvnQueueBuilderSetDefaultsFunction)(NVNqueueBuilder*); +typedef void (*nvnQueueBuilderSetFlagsFunction)(NVNqueueBuilder*, int); +typedef void (*nvnQueueBuilderSetCommandMemorySizeFunction)(NVNqueueBuilder*, size_t); +typedef void (*nvnQueueBuilderSetComputeMemorySizeFunction)(NVNqueueBuilder*, size_t); +typedef void (*nvnQueueBuilderSetControlMemorySizeFunction)(NVNqueueBuilder*, size_t); +typedef size_t (*nvnQueueBuilderGetQueueMemorySizeFunction)(const NVNqueueBuilder*); +typedef void (*nvnQueueBuilderSetQueueMemoryFunction)(NVNqueueBuilder*, void*, size_t); +typedef void (*nvnQueueBuilderSetCommandFlushThresholdFunction)(NVNqueueBuilder*, size_t); +typedef bool (*nvnQueueInitializeFunction)(NVNqueue*, const NVNqueueBuilder*); +typedef void (*nvnQueueFinalizeFunction)(NVNqueue*); +typedef void (*nvnQueueSetDebugLabelFunction)(NVNqueue*, const char*); +typedef void (*nvnQueueSubmitCommandsFunction)(NVNqueue*, int, const NVNcommandHandle*); +typedef void (*nvnQueueFlushFunction)(NVNqueue*); +typedef void (*nvnQueueFinishFunction)(NVNqueue*); +typedef void (*nvnQueuePresentTextureFunction)(NVNqueue*, NVNwindow*, int); +typedef NVNqueueAcquireTextureResult (*nvnQueueAcquireTextureFunction)(NVNqueue*, NVNwindow*, int*); +typedef void (*nvnWindowBuilderSetDeviceFunction)(NVNwindowBuilder*, NVNdevice*); +typedef void (*nvnWindowBuilderSetDefaultsFunction)(NVNwindowBuilder*); +typedef void (*nvnWindowBuilderSetNativeWindowFunction)(NVNwindowBuilder*, NVNnativeWindow); +typedef void (*nvnWindowBuilderSetTexturesFunction)(NVNwindowBuilder*, int, NVNtexture* const*); +typedef void (*nvnWindowBuilderSetPresentIntervalFunction)(NVNwindowBuilder*, int); +typedef NVNnativeWindow (*nvnWindowBuilderGetNativeWindowFunction)(const NVNwindowBuilder*); +typedef int (*nvnWindowBuilderGetPresentIntervalFunction)(const NVNwindowBuilder*); +typedef bool (*nvnWindowInitializeFunction)(NVNwindow*, const NVNwindowBuilder*); +typedef void (*nvnWindowFinalizeFunction)(NVNwindow*); +typedef void (*nvnWindowSetDebugLabelFunction)(NVNwindow*, const char*); +typedef NVNwindowAcquireTextureResult (*nvnWindowAcquireTextureFunction)(NVNwindow*, NVNsync*, + int*); +typedef NVNnativeWindow (*nvnWindowGetNativeWindowFunction)(const NVNwindow*); +typedef int (*nvnWindowGetPresentIntervalFunction)(const NVNwindow*); +typedef void (*nvnWindowSetPresentIntervalFunction)(NVNwindow*, int); +typedef void (*nvnWindowSetCropFunction)(NVNwindow*, int, int, int, int); +typedef void (*nvnWindowGetCropFunction)(const NVNwindow*, NVNrectangle*); +typedef bool (*nvnProgramInitializeFunction)(NVNprogram*, NVNdevice*); +typedef void (*nvnProgramFinalizeFunction)(NVNprogram*); +typedef void (*nvnProgramSetDebugLabelFunction)(NVNprogram*, const char*); +typedef bool (*nvnProgramSetShadersFunction)(NVNprogram*, int, const NVNshaderData*); +typedef void (*nvnMemoryPoolBuilderSetDeviceFunction)(NVNmemoryPoolBuilder*, NVNdevice*); +typedef void (*nvnMemoryPoolBuilderSetDefaultsFunction)(NVNmemoryPoolBuilder*); +typedef void (*nvnMemoryPoolBuilderSetStorageFunction)(NVNmemoryPoolBuilder*, void*, size_t); +typedef void (*nvnMemoryPoolBuilderSetFlagsFunction)(NVNmemoryPoolBuilder*, int); +typedef void (*nvnMemoryPoolBuilderGetMemoryFunction)(const NVNmemoryPoolBuilder*); +typedef size_t (*nvnMemoryPoolBuilderGetSizeFunction)(const NVNmemoryPoolBuilder*); +typedef NVNmemoryPoolFlags (*nvnMemoryPoolBuilderGetFlagsFunction)(const NVNmemoryPoolBuilder*); +typedef bool (*nvnMemoryPoolInitializeFunction)(NVNmemoryPool*, const NVNmemoryPoolBuilder*); +typedef void (*nvnMemoryPoolSetDebugLabelFunction)(NVNmemoryPool*, const char*); +typedef void (*nvnMemoryPoolFinalizeFunction)(NVNmemoryPool*); +typedef void (*nvnMemoryPoolMapFunction)(const NVNmemoryPool*); +typedef void (*nvnMemoryPoolFlushMappedRangeFunction)(const NVNmemoryPool*, ptrdiff_t, size_t); +typedef void (*nvnMemoryPoolInvalidateMappedRangeFunction)(const NVNmemoryPool*, ptrdiff_t, size_t); +typedef NVNbufferAddress (*nvnMemoryPoolGetBufferAddressFunction)(const NVNmemoryPool*); +typedef bool (*nvnMemoryPoolMapVirtualFunction)(NVNmemoryPool*, int, const NVNmappingRequest*); +typedef size_t (*nvnMemoryPoolGetSizeFunction)(const NVNmemoryPool*); +typedef NVNmemoryPoolFlags (*nvnMemoryPoolGetFlagsFunction)(const NVNmemoryPool*); +typedef bool (*nvnTexturePoolInitializeFunction)(NVNtexturePool*, const NVNmemoryPool*, ptrdiff_t, + int); +typedef void (*nvnTexturePoolSetDebugLabelFunction)(NVNtexturePool*, const char*); +typedef void (*nvnTexturePoolFinalizeFunction)(NVNtexturePool*); +typedef void (*nvnTexturePoolRegisterTextureFunction)(const NVNtexturePool*, int, const NVNtexture*, + const NVNtextureView*); +typedef void (*nvnTexturePoolRegisterImageFunction)(const NVNtexturePool*, int, const NVNtexture*, + const NVNtextureView*); +typedef const NVNmemoryPool* (*nvnTexturePoolGetMemoryPoolFunction)(const NVNtexturePool*); +typedef ptrdiff_t (*nvnTexturePoolGetMemoryOffsetFunction)(const NVNtexturePool*); +typedef int (*nvnTexturePoolGetSizeFunction)(const NVNtexturePool*); +typedef bool (*nvnSamplerPoolInitializeFunction)(NVNsamplerPool*, const NVNmemoryPool*, ptrdiff_t, + int); +typedef void (*nvnSamplerPoolSetDebugLabelFunction)(NVNsamplerPool*, const char*); +typedef void (*nvnSamplerPoolFinalizeFunction)(NVNsamplerPool*); +typedef void (*nvnSamplerPoolRegisterSamplerFunction)(const NVNsamplerPool*, int, + const NVNsampler*); +typedef void (*nvnSamplerPoolRegisterSamplerBuilderFunction)(const NVNsamplerPool*, int, + const NVNsamplerBuilder*); +typedef const NVNmemoryPool* (*nvnSamplerPoolGetMemoryPoolFunction)(const NVNsamplerPool*); +typedef ptrdiff_t (*nvnSamplerPoolGetMemoryOffsetFunction)(const NVNsamplerPool*); +typedef int (*nvnSamplerPoolGetSizeFunction)(const NVNsamplerPool*); +typedef void (*nvnBufferBuilderSetDeviceFunction)(NVNbufferBuilder*, NVNdevice*); +typedef void (*nvnBufferBuilderSetDefaultsFunction)(NVNbufferBuilder*); +typedef void (*nvnBufferBuilderSetStorageFunction)(NVNbufferBuilder*, NVNmemoryPool*, ptrdiff_t, + size_t); +typedef NVNmemoryPool (*nvnBufferBuilderGetMemoryPoolFunction)(const NVNbufferBuilder*); +typedef ptrdiff_t (*nvnBufferBuilderGetMemoryOffsetFunction)(const NVNbufferBuilder*); +typedef size_t (*nvnBufferBuilderGetSizeFunction)(const NVNbufferBuilder*); +typedef bool (*nvnBufferInitializeFunction)(NVNbuffer*, const NVNbufferBuilder*); +typedef void (*nvnBufferSetDebugLabelFunction)(NVNbuffer*, const char*); +typedef void (*nvnBufferFinalizeFunction)(NVNbuffer*); +typedef void (*nvnBufferMapFunction)(const NVNbuffer*); +typedef NVNbufferAddress (*nvnBufferGetAddressFunction)(const NVNbuffer*); +typedef void (*nvnBufferFlushMappedRangeFunction)(const NVNbuffer*, ptrdiff_t, size_t); +typedef void (*nvnBufferInvalidateMappedRangeFunction)(const NVNbuffer*, ptrdiff_t, size_t); +typedef NVNmemoryPool (*nvnBufferGetMemoryPoolFunction)(const NVNbuffer*); +typedef ptrdiff_t (*nvnBufferGetMemoryOffsetFunction)(const NVNbuffer*); +typedef size_t (*nvnBufferGetSizeFunction)(const NVNbuffer*); +typedef uint64_t (*nvnBufferGetDebugIDFunction)(const NVNbuffer*); +typedef void (*nvnTextureBuilderSetDeviceFunction)(NVNtextureBuilder*, NVNdevice*); +typedef void (*nvnTextureBuilderSetDefaultsFunction)(NVNtextureBuilder*); +typedef void (*nvnTextureBuilderSetFlagsFunction)(NVNtextureBuilder*, int); +typedef void (*nvnTextureBuilderSetTargetFunction)(NVNtextureBuilder*, NVNtextureTarget); +typedef void (*nvnTextureBuilderSetWidthFunction)(NVNtextureBuilder*, int); +typedef void (*nvnTextureBuilderSetHeightFunction)(NVNtextureBuilder*, int); +typedef void (*nvnTextureBuilderSetDepthFunction)(NVNtextureBuilder*, int); +typedef void (*nvnTextureBuilderSetSize1DFunction)(NVNtextureBuilder*, int); +typedef void (*nvnTextureBuilderSetSize2DFunction)(NVNtextureBuilder*, int, int); +typedef void (*nvnTextureBuilderSetSize3DFunction)(NVNtextureBuilder*, int, int, int); +typedef void (*nvnTextureBuilderSetLevelsFunction)(NVNtextureBuilder*, int); +typedef void (*nvnTextureBuilderSetFormatFunction)(NVNtextureBuilder*, NVNformat); +typedef void (*nvnTextureBuilderSetSamplesFunction)(NVNtextureBuilder*, int); +typedef void (*nvnTextureBuilderSetSwizzleFunction)(NVNtextureBuilder*, NVNtextureSwizzle, + NVNtextureSwizzle, NVNtextureSwizzle, + NVNtextureSwizzle); +typedef void (*nvnTextureBuilderSetDepthStencilModeFunction)(NVNtextureBuilder*, + NVNtextureDepthStencilMode); +typedef size_t (*nvnTextureBuilderGetStorageSizeFunction)(const NVNtextureBuilder*); +typedef size_t (*nvnTextureBuilderGetStorageAlignmentFunction)(const NVNtextureBuilder*); +typedef void (*nvnTextureBuilderSetStorageFunction)(NVNtextureBuilder*, NVNmemoryPool*, ptrdiff_t); +typedef void (*nvnTextureBuilderSetPackagedTextureDataFunction)(NVNtextureBuilder*, const void*); +typedef void (*nvnTextureBuilderSetPackagedTextureLayoutFunction)(NVNtextureBuilder*, + const NVNpackagedTextureLayout*); +typedef void (*nvnTextureBuilderSetStrideFunction)(NVNtextureBuilder*, ptrdiff_t); +typedef void (*nvnTextureBuilderSetGLTextureNameFunction)(NVNtextureBuilder*, uint32_t); +typedef NVNstorageClass (*nvnTextureBuilderGetStorageClassFunction)(const NVNtextureBuilder*); +typedef NVNtextureFlags (*nvnTextureBuilderGetFlagsFunction)(const NVNtextureBuilder*); +typedef NVNtextureTarget (*nvnTextureBuilderGetTargetFunction)(const NVNtextureBuilder*); +typedef int (*nvnTextureBuilderGetWidthFunction)(const NVNtextureBuilder*); +typedef int (*nvnTextureBuilderGetHeightFunction)(const NVNtextureBuilder*); +typedef int (*nvnTextureBuilderGetDepthFunction)(const NVNtextureBuilder*); +typedef int (*nvnTextureBuilderGetLevelsFunction)(const NVNtextureBuilder*); +typedef NVNformat (*nvnTextureBuilderGetFormatFunction)(const NVNtextureBuilder*); +typedef int (*nvnTextureBuilderGetSamplesFunction)(const NVNtextureBuilder*); +typedef void (*nvnTextureBuilderGetSwizzleFunction)(const NVNtextureBuilder*, NVNtextureSwizzle*, + NVNtextureSwizzle*, NVNtextureSwizzle*, + NVNtextureSwizzle*); +typedef NVNtextureDepthStencilMode (*nvnTextureBuilderGetDepthStencilModeFunction)( + const NVNtextureBuilder*); +typedef const void* (*nvnTextureBuilderGetPackagedTextureDataFunction)(const NVNtextureBuilder*); +typedef ptrdiff_t (*nvnTextureBuilderGetStrideFunction)(const NVNtextureBuilder*); +typedef void (*nvnTextureBuilderGetSparseTileLayoutFunction)(const NVNtextureBuilder*, + NVNtextureSparseTileLayout*); +typedef uint32_t (*nvnTextureBuilderGetGLTextureNameFunction)(const NVNtextureBuilder*); +typedef size_t (*nvnTextureBuilderGetZCullStorageSizeFunction)(const NVNtextureBuilder*); +typedef NVNmemoryPool (*nvnTextureBuilderGetMemoryPoolFunction)(const NVNtextureBuilder*); +typedef ptrdiff_t (*nvnTextureBuilderGetMemoryOffsetFunction)(const NVNtextureBuilder*); +typedef void (*nvnTextureViewSetDefaultsFunction)(NVNtextureView*); +typedef void (*nvnTextureViewSetLevelsFunction)(NVNtextureView*, int, int); +typedef void (*nvnTextureViewSetLayersFunction)(NVNtextureView*, int, int); +typedef void (*nvnTextureViewSetFormatFunction)(NVNtextureView*, NVNformat); +typedef void (*nvnTextureViewSetSwizzleFunction)(NVNtextureView*, NVNtextureSwizzle, + NVNtextureSwizzle, NVNtextureSwizzle, + NVNtextureSwizzle); +typedef void (*nvnTextureViewSetDepthStencilModeFunction)(NVNtextureView*, + NVNtextureDepthStencilMode); +typedef void (*nvnTextureViewSetTargetFunction)(NVNtextureView*, NVNtextureTarget); +typedef bool (*nvnTextureViewGetLevelsFunction)(const NVNtextureView*, int*, int*); +typedef bool (*nvnTextureViewGetLayersFunction)(const NVNtextureView*, int*, int*); +typedef bool (*nvnTextureViewGetFormatFunction)(const NVNtextureView*, NVNformat*); +typedef bool (*nvnTextureViewGetSwizzleFunction)(const NVNtextureView*, NVNtextureSwizzle*, + NVNtextureSwizzle*, NVNtextureSwizzle*, + NVNtextureSwizzle*); +typedef bool (*nvnTextureViewGetDepthStencilModeFunction)(const NVNtextureView*, + NVNtextureDepthStencilMode*); +typedef bool (*nvnTextureViewGetTargetFunction)(const NVNtextureView*, NVNtextureTarget*); +typedef bool (*nvnTextureViewCompareFunction)(const NVNtextureView*, const NVNtextureView*); +typedef bool (*nvnTextureInitializeFunction)(NVNtexture*, const NVNtextureBuilder*); +typedef size_t (*nvnTextureGetZCullStorageSizeFunction)(const NVNtexture*); +typedef void (*nvnTextureFinalizeFunction)(NVNtexture*); +typedef void (*nvnTextureSetDebugLabelFunction)(NVNtexture*, const char*); +typedef NVNstorageClass (*nvnTextureGetStorageClassFunction)(const NVNtexture*); +typedef ptrdiff_t (*nvnTextureGetViewOffsetFunction)(const NVNtexture*, const NVNtextureView*); +typedef NVNtextureFlags (*nvnTextureGetFlagsFunction)(const NVNtexture*); +typedef NVNtextureTarget (*nvnTextureGetTargetFunction)(const NVNtexture*); +typedef int (*nvnTextureGetWidthFunction)(const NVNtexture*); +typedef int (*nvnTextureGetHeightFunction)(const NVNtexture*); +typedef int (*nvnTextureGetDepthFunction)(const NVNtexture*); +typedef int (*nvnTextureGetLevelsFunction)(const NVNtexture*); +typedef NVNformat (*nvnTextureGetFormatFunction)(const NVNtexture*); +typedef int (*nvnTextureGetSamplesFunction)(const NVNtexture*); +typedef void (*nvnTextureGetSwizzleFunction)(const NVNtexture*, NVNtextureSwizzle*, + NVNtextureSwizzle*, NVNtextureSwizzle*, + NVNtextureSwizzle*); +typedef NVNtextureDepthStencilMode (*nvnTextureGetDepthStencilModeFunction)(const NVNtexture*); +typedef ptrdiff_t (*nvnTextureGetStrideFunction)(const NVNtexture*); +typedef NVNtextureAddress (*nvnTextureGetTextureAddressFunction)(const NVNtexture*); +typedef void (*nvnTextureGetSparseTileLayoutFunction)(const NVNtexture*, + NVNtextureSparseTileLayout*); +typedef void (*nvnTextureWriteTexelsFunction)(const NVNtexture*, const NVNtextureView*, + const NVNcopyRegion*, const void*); +typedef void (*nvnTextureWriteTexelsStridedFunction)(const NVNtexture*, const NVNtextureView*, + const NVNcopyRegion*, const void*, ptrdiff_t, + ptrdiff_t); +typedef void (*nvnTextureReadTexelsFunction)(const NVNtexture*, const NVNtextureView*, + const NVNcopyRegion*, void*); +typedef void (*nvnTextureReadTexelsStridedFunction)(const NVNtexture*, const NVNtextureView*, + const NVNcopyRegion*, void*, ptrdiff_t, + ptrdiff_t); +typedef void (*nvnTextureFlushTexelsFunction)(const NVNtexture*, const NVNtextureView*, + const NVNcopyRegion*); +typedef void (*nvnTextureInvalidateTexelsFunction)(const NVNtexture*, const NVNtextureView*, + const NVNcopyRegion*); +typedef NVNmemoryPool (*nvnTextureGetMemoryPoolFunction)(const NVNtexture*); +typedef ptrdiff_t (*nvnTextureGetMemoryOffsetFunction)(const NVNtexture*); +typedef int (*nvnTextureGetStorageSizeFunction)(const NVNtexture*); +typedef bool (*nvnTextureCompareFunction)(const NVNtexture*, const NVNtexture*); +typedef uint64_t (*nvnTextureGetDebugIDFunction)(const NVNtexture*); +typedef void (*nvnSamplerBuilderSetDeviceFunction)(NVNsamplerBuilder*, NVNdevice*); +typedef void (*nvnSamplerBuilderSetDefaultsFunction)(NVNsamplerBuilder*); +typedef void (*nvnSamplerBuilderSetMinMagFilterFunction)(NVNsamplerBuilder*, NVNminFilter, + NVNmagFilter); +typedef void (*nvnSamplerBuilderSetWrapModeFunction)(NVNsamplerBuilder*, NVNwrapMode, NVNwrapMode, + NVNwrapMode); +typedef void (*nvnSamplerBuilderSetLodClampFunction)(NVNsamplerBuilder*, float, float); +typedef void (*nvnSamplerBuilderSetLodBiasFunction)(NVNsamplerBuilder*, float); +typedef void (*nvnSamplerBuilderSetCompareFunction)(NVNsamplerBuilder*, NVNcompareMode, + NVNcompareFunc); +typedef void (*nvnSamplerBuilderSetBorderColorFunction)(NVNsamplerBuilder*, const float*); +typedef void (*nvnSamplerBuilderSetBorderColoriFunction)(NVNsamplerBuilder*, const int*); +typedef void (*nvnSamplerBuilderSetBorderColoruiFunction)(NVNsamplerBuilder*, const uint32_t*); +typedef void (*nvnSamplerBuilderSetMaxAnisotropyFunction)(NVNsamplerBuilder*, float); +typedef void (*nvnSamplerBuilderSetReductionFilterFunction)(NVNsamplerBuilder*, + NVNsamplerReduction); +typedef void (*nvnSamplerBuilderSetLodSnapFunction)(NVNsamplerBuilder*, float); +typedef void (*nvnSamplerBuilderGetMinMagFilterFunction)(const NVNsamplerBuilder*, NVNminFilter*, + NVNmagFilter*); +typedef void (*nvnSamplerBuilderGetWrapModeFunction)(const NVNsamplerBuilder*, NVNwrapMode*, + NVNwrapMode*, NVNwrapMode*); +typedef void (*nvnSamplerBuilderGetLodClampFunction)(const NVNsamplerBuilder*, float*, float*); +typedef float (*nvnSamplerBuilderGetLodBiasFunction)(const NVNsamplerBuilder*); +typedef void (*nvnSamplerBuilderGetCompareFunction)(const NVNsamplerBuilder*, NVNcompareMode*, + NVNcompareFunc*); +typedef void (*nvnSamplerBuilderGetBorderColorFunction)(const NVNsamplerBuilder*, float*); +typedef void (*nvnSamplerBuilderGetBorderColoriFunction)(const NVNsamplerBuilder*, int*); +typedef void (*nvnSamplerBuilderGetBorderColoruiFunction)(const NVNsamplerBuilder*, uint32_t*); +typedef float (*nvnSamplerBuilderGetMaxAnisotropyFunction)(const NVNsamplerBuilder*); +typedef NVNsamplerReduction (*nvnSamplerBuilderGetReductionFilterFunction)( + const NVNsamplerBuilder*); +typedef float (*nvnSamplerBuilderGetLodSnapFunction)(const NVNsamplerBuilder*); +typedef bool (*nvnSamplerInitializeFunction)(NVNsampler*, const NVNsamplerBuilder*); +typedef void (*nvnSamplerFinalizeFunction)(NVNsampler*); +typedef void (*nvnSamplerSetDebugLabelFunction)(NVNsampler*, const char*); +typedef void (*nvnSamplerGetMinMagFilterFunction)(const NVNsampler*, NVNminFilter*, NVNmagFilter*); +typedef void (*nvnSamplerGetWrapModeFunction)(const NVNsampler*, NVNwrapMode*, NVNwrapMode*, + NVNwrapMode*); +typedef void (*nvnSamplerGetLodClampFunction)(const NVNsampler*, float*, float*); +typedef float (*nvnSamplerGetLodBiasFunction)(const NVNsampler*); +typedef void (*nvnSamplerGetCompareFunction)(const NVNsampler*, NVNcompareMode*, NVNcompareFunc*); +typedef void (*nvnSamplerGetBorderColorFunction)(const NVNsampler*, float*); +typedef void (*nvnSamplerGetBorderColoriFunction)(const NVNsampler*, int*); +typedef void (*nvnSamplerGetBorderColoruiFunction)(const NVNsampler*, uint32_t*); +typedef float (*nvnSamplerGetMaxAnisotropyFunction)(const NVNsampler*); +typedef NVNsamplerReduction (*nvnSamplerGetReductionFilterFunction)(const NVNsampler*); +typedef bool (*nvnSamplerCompareFunction)(const NVNsampler*, const NVNsampler*); +typedef uint64_t (*nvnSamplerGetDebugIDFunction)(const NVNsampler*); +typedef void (*nvnBlendStateSetDefaultsFunction)(NVNblendState*); +typedef void (*nvnBlendStateSetBlendTargetFunction)(NVNblendState*, int); +typedef void (*nvnBlendStateSetBlendFuncFunction)(NVNblendState*, NVNblendFunc, NVNblendFunc, + NVNblendFunc, NVNblendFunc); +typedef void (*nvnBlendStateSetBlendEquationFunction)(NVNblendState*, NVNblendEquation, + NVNblendEquation); +typedef void (*nvnBlendStateSetAdvancedModeFunction)(NVNblendState*, NVNblendAdvancedMode); +typedef void (*nvnBlendStateSetAdvancedOverlapFunction)(NVNblendState*, NVNblendAdvancedOverlap); +typedef void (*nvnBlendStateSetAdvancedPremultipliedSrcFunction)(NVNblendState*, bool); +typedef void (*nvnBlendStateSetAdvancedNormalizedDstFunction)(NVNblendState*, bool); +typedef int (*nvnBlendStateGetBlendTargetFunction)(const NVNblendState*); +typedef void (*nvnBlendStateGetBlendFuncFunction)(const NVNblendState*, NVNblendFunc*, + NVNblendFunc*, NVNblendFunc*, NVNblendFunc*); +typedef void (*nvnBlendStateGetBlendEquationFunction)(const NVNblendState*, NVNblendEquation*, + NVNblendEquation*); +typedef NVNblendAdvancedMode (*nvnBlendStateGetAdvancedModeFunction)(const NVNblendState*); +typedef NVNblendAdvancedOverlap (*nvnBlendStateGetAdvancedOverlapFunction)(const NVNblendState*); +typedef bool (*nvnBlendStateGetAdvancedPremultipliedSrcFunction)(const NVNblendState*); +typedef bool (*nvnBlendStateGetAdvancedNormalizedDstFunction)(const NVNblendState*); +typedef void (*nvnColorStateSetDefaultsFunction)(NVNcolorState*); +typedef void (*nvnColorStateSetBlendEnableFunction)(NVNcolorState*, int, bool); +typedef void (*nvnColorStateSetLogicOpFunction)(NVNcolorState*, NVNlogicOp); +typedef void (*nvnColorStateSetAlphaTestFunction)(NVNcolorState*, NVNalphaFunc); +typedef bool (*nvnColorStateGetBlendEnableFunction)(const NVNcolorState*, int); +typedef NVNlogicOp (*nvnColorStateGetLogicOpFunction)(const NVNcolorState*); +typedef NVNalphaFunc (*nvnColorStateGetAlphaTestFunction)(const NVNcolorState*); +typedef void (*nvnChannelMaskStateSetDefaultsFunction)(NVNchannelMaskState*); +typedef void (*nvnChannelMaskStateSetChannelMaskFunction)(NVNchannelMaskState*, int, bool, bool, + bool, bool); +typedef void (*nvnChannelMaskStateGetChannelMaskFunction)(const NVNchannelMaskState*, int, bool*, + bool*, bool*, bool*); +typedef void (*nvnMultisampleStateSetDefaultsFunction)(NVNmultisampleState*); +typedef void (*nvnMultisampleStateSetMultisampleEnableFunction)(NVNmultisampleState*, bool); +typedef void (*nvnMultisampleStateSetSamplesFunction)(NVNmultisampleState*, int); +typedef void (*nvnMultisampleStateSetAlphaToCoverageEnableFunction)(NVNmultisampleState*, bool); +typedef void (*nvnMultisampleStateSetAlphaToCoverageDitherFunction)(NVNmultisampleState*, bool); +typedef bool (*nvnMultisampleStateGetMultisampleEnableFunction)(const NVNmultisampleState*); +typedef int (*nvnMultisampleStateGetSamplesFunction)(const NVNmultisampleState*); +typedef bool (*nvnMultisampleStateGetAlphaToCoverageEnableFunction)(const NVNmultisampleState*); +typedef bool (*nvnMultisampleStateGetAlphaToCoverageDitherFunction)(const NVNmultisampleState*); +typedef void (*nvnMultisampleStateSetRasterSamplesFunction)(NVNmultisampleState*, int); +typedef int (*nvnMultisampleStateGetRasterSamplesFunction)(NVNmultisampleState*); +typedef void (*nvnMultisampleStateSetCoverageModulationModeFunction)(NVNmultisampleState*, + NVNcoverageModulationMode); +typedef NVNcoverageModulationMode (*nvnMultisampleStateGetCoverageModulationModeFunction)( + const NVNmultisampleState*); +typedef void (*nvnMultisampleStateSetCoverageToColorEnableFunction)(NVNmultisampleState*, bool); +typedef bool (*nvnMultisampleStateGetCoverageToColorEnableFunction)(const NVNmultisampleState*); +typedef void (*nvnMultisampleStateSetCoverageToColorOutputFunction)(NVNmultisampleState*, int); +typedef int (*nvnMultisampleStateGetCoverageToColorOutputFunction)(const NVNmultisampleState*); +typedef void (*nvnMultisampleStateSetSampleLocationsEnableFunction)(NVNmultisampleState*, bool); +typedef bool (*nvnMultisampleStateGetSampleLocationsEnableFunction)(const NVNmultisampleState*); +typedef void (*nvnMultisampleStateGetSampleLocationsGridFunction)(NVNmultisampleState*, int*, int*); +typedef void (*nvnMultisampleStateSetSampleLocationsGridEnableFunction)(NVNmultisampleState*, bool); +typedef bool (*nvnMultisampleStateGetSampleLocationsGridEnableFunction)(const NVNmultisampleState*); +typedef void (*nvnMultisampleStateSetSampleLocationsFunction)(NVNmultisampleState*, bool); +typedef void (*nvnPolygonStateSetDefaultsFunction)(NVNpolygonState*); +typedef void (*nvnPolygonStateSetCullFaceFunction)(NVNpolygonState*, NVNface); +typedef void (*nvnPolygonStateSetFrontFaceFunction)(NVNpolygonState*, NVNfrontFace); +typedef void (*nvnPolygonStateSetPolygonModeFunction)(NVNpolygonState*, NVNpolygonMode); +typedef void (*nvnPolygonStateSetPolygonOffsetEnablesFunction)(NVNpolygonState*, int); +typedef NVNface (*nvnPolygonStateGetCullFaceFunction)(const NVNpolygonState*); +typedef NVNfrontFace (*nvnPolygonStateGetFrontFaceFunction)(const NVNpolygonState*); +typedef NVNpolygonMode (*nvnPolygonStateGetPolygonModeFunction)(const NVNpolygonState*); +typedef NVNpolygonOffsetEnable (*nvnPolygonStateGetPolygonOffsetEnablesFunction)( + const NVNpolygonState*); +typedef void (*nvnDepthStencilStateSetDefaultsFunction)(NVNdepthStencilState*); +typedef void (*nvnDepthStencilStateSetDepthTestEnableFunction)(NVNdepthStencilState*, bool); +typedef void (*nvnDepthStencilStateSetDepthWriteEnableFunction)(NVNdepthStencilState*, bool); +typedef void (*nvnDepthStencilStateSetDepthFuncFunction)(NVNdepthStencilState*, NVNdepthFunc); +typedef void (*nvnDepthStencilStateSetStencilTestEnableFunction)(NVNdepthStencilState*, bool); +typedef void (*nvnDepthStencilStateSetStencilFuncFunction)(NVNdepthStencilState*, NVNface, + NVNstencilFunc); +typedef void (*nvnDepthStencilStateSetStencilOpFunction)(NVNdepthStencilState*, NVNface, + NVNstencilOp, NVNstencilOp, NVNstencilOp); +typedef bool (*nvnDepthStencilStateGetDepthTestEnableFunction)(const NVNdepthStencilState*); +typedef bool (*nvnDepthStencilStateGetDepthWriteEnableFunction)(const NVNdepthStencilState*); +typedef NVNdepthFunc (*nvnDepthStencilStateGetDepthFuncFunction)(const NVNdepthStencilState*); +typedef bool (*nvnDepthStencilStateGetStencilTestEnableFunction)(const NVNdepthStencilState*); +typedef NVNstencilFunc (*nvnDepthStencilStateGetStencilFuncFunction)(const NVNdepthStencilState*, + NVNface); +typedef void (*nvnDepthStencilStateGetStencilOpFunction)(const NVNdepthStencilState*, NVNface, + NVNstencilOp*, NVNstencilOp*, + NVNstencilOp*); +typedef void (*nvnVertexAttribStateSetDefaultsFunction)(NVNvertexAttribState*); +typedef void (*nvnVertexAttribStateSetFormatFunction)(NVNvertexAttribState*, NVNformat, ptrdiff_t); +typedef void (*nvnVertexAttribStateSetStreamIndexFunction)(NVNvertexAttribState*, int); +typedef void (*nvnVertexAttribStateGetFormatFunction)(const NVNvertexAttribState*, NVNformat*, + ptrdiff_t*); +typedef int (*nvnVertexAttribStateGetStreamIndexFunction)(const NVNvertexAttribState*); +typedef void (*nvnVertexStreamStateSetDefaultsFunction)(NVNvertexStreamState*); +typedef void (*nvnVertexStreamStateSetStrideFunction)(NVNvertexStreamState*, ptrdiff_t); +typedef void (*nvnVertexStreamStateSetDivisorFunction)(NVNvertexStreamState*, int); +typedef ptrdiff_t (*nvnVertexStreamStateGetStrideFunction)(const NVNvertexStreamState*); +typedef int (*nvnVertexStreamStateGetDivisorFunction)(const NVNvertexStreamState*); +typedef bool (*nvnCommandBufferInitializeFunction)(NVNcommandBuffer*, NVNdevice*); +typedef void (*nvnCommandBufferFinalizeFunction)(NVNcommandBuffer*); +typedef void (*nvnCommandBufferSetDebugLabelFunction)(NVNcommandBuffer*, const char*); +typedef void (*nvnCommandBufferSetMemoryCallbackFunction)(NVNcommandBuffer*, + NVNcommandBufferMemoryCallback); +typedef void (*nvnCommandBufferSetMemoryCallbackDataFunction)(NVNcommandBuffer*, void*); +typedef void (*nvnCommandBufferAddCommandMemoryFunction)(NVNcommandBuffer*, const NVNmemoryPool*, + ptrdiff_t, size_t); +typedef void (*nvnCommandBufferAddControlMemoryFunction)(NVNcommandBuffer*, void*, size_t); +typedef size_t (*nvnCommandBufferGetCommandMemorySizeFunction)(const NVNcommandBuffer*); +typedef size_t (*nvnCommandBufferGetCommandMemoryUsedFunction)(const NVNcommandBuffer*); +typedef size_t (*nvnCommandBufferGetCommandMemoryFreeFunction)(const NVNcommandBuffer*); +typedef size_t (*nvnCommandBufferGetControlMemorySizeFunction)(const NVNcommandBuffer*); +typedef size_t (*nvnCommandBufferGetControlMemoryUsedFunction)(const NVNcommandBuffer*); +typedef size_t (*nvnCommandBufferGetControlMemoryFreeFunction)(const NVNcommandBuffer*); +typedef void (*nvnCommandBufferBeginRecordingFunction)(NVNcommandBuffer*); +typedef NVNcommandHandle (*nvnCommandBufferEndRecordingFunction)(NVNcommandBuffer*); +typedef void (*nvnCommandBufferCallCommandsFunction)(NVNcommandBuffer*, int, + const NVNcommandHandle*); +typedef void (*nvnCommandBufferCopyCommandsFunction)(NVNcommandBuffer*, int, + const NVNcommandHandle*); +typedef void (*nvnCommandBufferBindBlendStateFunction)(NVNcommandBuffer*, const NVNblendState*); +typedef void (*nvnCommandBufferBindChannelMaskStateFunction)(NVNcommandBuffer*, + const NVNchannelMaskState*); +typedef void (*nvnCommandBufferBindColorStateFunction)(NVNcommandBuffer*, const NVNcolorState*); +typedef void (*nvnCommandBufferBindMultisampleStateFunction)(NVNcommandBuffer*, + const NVNmultisampleState*); +typedef void (*nvnCommandBufferBindPolygonStateFunction)(NVNcommandBuffer*, const NVNpolygonState*); +typedef void (*nvnCommandBufferBindDepthStencilStateFunction)(NVNcommandBuffer*, + const NVNdepthStencilState*); +typedef void (*nvnCommandBufferBindVertexAttribStateFunction)(NVNcommandBuffer*, int, + const NVNvertexAttribState*); +typedef void (*nvnCommandBufferBindVertexStreamStateFunction)(NVNcommandBuffer*, int, + const NVNvertexStreamState*); +typedef void (*nvnCommandBufferBindProgramFunction)(NVNcommandBuffer*, const NVNprogram*, int); +typedef void (*nvnCommandBufferBindVertexBufferFunction)(NVNcommandBuffer*, int, NVNbufferAddress, + size_t); +typedef void (*nvnCommandBufferBindVertexBuffersFunction)(NVNcommandBuffer*, int, int, + const NVNbufferRange*); +typedef void (*nvnCommandBufferBindUniformBufferFunction)(NVNcommandBuffer*, NVNshaderStage, int, + NVNbufferAddress, size_t); +typedef void (*nvnCommandBufferBindUniformBuffersFunction)(NVNcommandBuffer*, NVNshaderStage, int, + int, const NVNbufferRange*); +typedef void (*nvnCommandBufferBindTransformFeedbackBufferFunction)(NVNcommandBuffer*, int, + NVNbufferAddress, size_t); +typedef void (*nvnCommandBufferBindTransformFeedbackBuffersFunction)(NVNcommandBuffer*, int, int, + const NVNbufferRange*); +typedef void (*nvnCommandBufferBindStorageBufferFunction)(NVNcommandBuffer*, NVNshaderStage, int, + NVNbufferAddress, size_t); +typedef void (*nvnCommandBufferBindStorageBuffersFunction)(NVNcommandBuffer*, NVNshaderStage, int, + int, const NVNbufferRange*); +typedef void (*nvnCommandBufferBindTextureFunction)(NVNcommandBuffer*, NVNshaderStage, int, + NVNtextureHandle); +typedef void (*nvnCommandBufferBindTexturesFunction)(NVNcommandBuffer*, NVNshaderStage, int, int, + const NVNtextureHandle*); +typedef void (*nvnCommandBufferBindImageFunction)(NVNcommandBuffer*, NVNshaderStage, int, + NVNimageHandle); +typedef void (*nvnCommandBufferBindImagesFunction)(NVNcommandBuffer*, NVNshaderStage, int, int, + const NVNimageHandle*); +typedef void (*nvnCommandBufferSetPatchSizeFunction)(NVNcommandBuffer*, int); +typedef void (*nvnCommandBufferSetInnerTessellationLevelsFunction)(NVNcommandBuffer*, const float*); +typedef void (*nvnCommandBufferSetOuterTessellationLevelsFunction)(NVNcommandBuffer*, const float*); +typedef void (*nvnCommandBufferSetPrimitiveRestartFunction)(NVNcommandBuffer*, bool, int); +typedef void (*nvnCommandBufferBeginTransformFeedbackFunction)(NVNcommandBuffer*, NVNbufferAddress); +typedef void (*nvnCommandBufferEndTransformFeedbackFunction)(NVNcommandBuffer*, NVNbufferAddress); +typedef void (*nvnCommandBufferPauseTransformFeedbackFunction)(NVNcommandBuffer*, NVNbufferAddress); +typedef void (*nvnCommandBufferResumeTransformFeedbackFunction)(NVNcommandBuffer*, + NVNbufferAddress); +typedef void (*nvnCommandBufferDrawTransformFeedbackFunction)(NVNcommandBuffer*, NVNdrawPrimitive, + NVNbufferAddress); +typedef void (*nvnCommandBufferDrawArraysFunction)(NVNcommandBuffer*, NVNdrawPrimitive, int, int); +typedef void (*nvnCommandBufferDrawElementsFunction)(NVNcommandBuffer*, NVNdrawPrimitive, + NVNindexType, int, NVNbufferAddress); +typedef void (*nvnCommandBufferDrawElementsBaseVertexFunction)(NVNcommandBuffer*, NVNdrawPrimitive, + NVNindexType, int, NVNbufferAddress, + int); +typedef void (*nvnCommandBufferDrawArraysInstancedFunction)(NVNcommandBuffer*, NVNdrawPrimitive, + int, int, int, int); +typedef void (*nvnCommandBufferDrawElementsInstancedFunction)(NVNcommandBuffer*, NVNdrawPrimitive, + NVNindexType, int, NVNbufferAddress, + int, int, int); +typedef void (*nvnCommandBufferDrawArraysIndirectFunction)(NVNcommandBuffer*, NVNdrawPrimitive, + NVNbufferAddress); +typedef void (*nvnCommandBufferDrawElementsIndirectFunction)(NVNcommandBuffer*, NVNdrawPrimitive, + NVNindexType, NVNbufferAddress, + NVNbufferAddress); +typedef void (*nvnCommandBufferMultiDrawArraysIndirectCountFunction)( + NVNcommandBuffer*, NVNdrawPrimitive, NVNbufferAddress, NVNbufferAddress, int, ptrdiff_t); +typedef void (*nvnCommandBufferMultiDrawElementsIndirectCountFunction)( + NVNcommandBuffer*, NVNdrawPrimitive, NVNindexType, NVNbufferAddress, NVNbufferAddress, + NVNbufferAddress, int, ptrdiff_t); +typedef void (*nvnCommandBufferClearColorFunction)(NVNcommandBuffer*, int, const float*, int); +typedef void (*nvnCommandBufferClearColoriFunction)(NVNcommandBuffer*, int, const int*, int); +typedef void (*nvnCommandBufferClearColoruiFunction)(NVNcommandBuffer*, int, const uint32_t*, int); +typedef void (*nvnCommandBufferClearDepthStencilFunction)(NVNcommandBuffer*, float, bool, int, int); +typedef void (*nvnCommandBufferDispatchComputeFunction)(NVNcommandBuffer*, int, int, int); +typedef void (*nvnCommandBufferDispatchComputeIndirectFunction)(NVNcommandBuffer*, + NVNbufferAddress); +typedef void (*nvnCommandBufferSetViewportFunction)(NVNcommandBuffer*, int, int, int, int); +typedef void (*nvnCommandBufferSetViewportsFunction)(NVNcommandBuffer*, int, int, const float*); +typedef void (*nvnCommandBufferSetViewportSwizzlesFunction)(NVNcommandBuffer*, int, int, + const NVNviewportSwizzle*); +typedef void (*nvnCommandBufferSetScissorFunction)(NVNcommandBuffer*, int, int, int, int); +typedef void (*nvnCommandBufferSetScissorsFunction)(NVNcommandBuffer*, int, int, const int*); +typedef void (*nvnCommandBufferSetDepthRangeFunction)(NVNcommandBuffer*, float, float); +typedef void (*nvnCommandBufferSetDepthBoundsFunction)(NVNcommandBuffer*, bool, float, float); +typedef void (*nvnCommandBufferSetDepthRangesFunction)(NVNcommandBuffer*, int, int, const float*); +typedef void (*nvnCommandBufferSetTiledCacheActionFunction)(NVNcommandBuffer*, NVNtiledCacheAction); +typedef void (*nvnCommandBufferSetTiledCacheTileSizeFunction)(NVNcommandBuffer*, int, int); +typedef void (*nvnCommandBufferBindSeparateTextureFunction)(NVNcommandBuffer*, NVNshaderStage, int, + NVNseparateTextureHandle); +typedef void (*nvnCommandBufferBindSeparateSamplerFunction)(NVNcommandBuffer*, NVNshaderStage, int, + NVNseparateSamplerHandle); +typedef void (*nvnCommandBufferBindSeparateTexturesFunction)(NVNcommandBuffer*, NVNshaderStage, int, + int, const NVNseparateTextureHandle*); +typedef void (*nvnCommandBufferBindSeparateSamplersFunction)(NVNcommandBuffer*, NVNshaderStage, int, + int, const NVNseparateSamplerHandle*); +typedef void (*nvnCommandBufferSetStencilValueMaskFunction)(NVNcommandBuffer*, NVNface, int); +typedef void (*nvnCommandBufferSetStencilMaskFunction)(NVNcommandBuffer*, NVNface, int); +typedef void (*nvnCommandBufferSetStencilRefFunction)(NVNcommandBuffer*, NVNface, int); +typedef void (*nvnCommandBufferSetBlendColorFunction)(NVNcommandBuffer*, const float*); +typedef void (*nvnCommandBufferSetPointSizeFunction)(NVNcommandBuffer*, float); +typedef void (*nvnCommandBufferSetLineWidthFunction)(NVNcommandBuffer*, float); +typedef void (*nvnCommandBufferSetPolygonOffsetClampFunction)(NVNcommandBuffer*, float, float, + float); +typedef void (*nvnCommandBufferSetAlphaRefFunction)(NVNcommandBuffer*, float); +typedef void (*nvnCommandBufferSetSampleMaskFunction)(NVNcommandBuffer*, int); +typedef void (*nvnCommandBufferSetRasterizerDiscardFunction)(NVNcommandBuffer*, bool); +typedef void (*nvnCommandBufferSetDepthClampFunction)(NVNcommandBuffer*, bool); +typedef void (*nvnCommandBufferSetConservativeRasterEnableFunction)(NVNcommandBuffer*, bool); +typedef void (*nvnCommandBufferSetConservativeRasterDilateFunction)(NVNcommandBuffer*, float); +typedef void (*nvnCommandBufferSetSubpixelPrecisionBiasFunction)(NVNcommandBuffer*, int, int); +typedef void (*nvnCommandBufferCopyBufferToTextureFunction)(NVNcommandBuffer*, NVNbufferAddress, + const NVNtexture*, + const NVNtextureView*, + const NVNcopyRegion*, int); +typedef void (*nvnCommandBufferCopyTextureToBufferFunction)(NVNcommandBuffer*, const NVNtexture*, + const NVNtextureView*, + const NVNcopyRegion*, NVNbufferAddress, + int); +typedef void (*nvnCommandBufferCopyTextureToTextureFunction)( + NVNcommandBuffer*, const NVNtexture*, const NVNtextureView*, const NVNcopyRegion*, + const NVNtexture*, const NVNtextureView*, const NVNcopyRegion*, int); +typedef void (*nvnCommandBufferCopyBufferToBufferFunction)(NVNcommandBuffer*, NVNbufferAddress, + NVNbufferAddress, size_t, int); +typedef void (*nvnCommandBufferClearBufferFunction)(NVNcommandBuffer*, NVNbufferAddress, size_t, + uint32_t); +typedef void (*nvnCommandBufferClearTextureFunction)(NVNcommandBuffer*, const NVNtexture*, + const NVNtextureView*, const NVNcopyRegion*, + const float*, int); +typedef void (*nvnCommandBufferClearTextureiFunction)(NVNcommandBuffer*, const NVNtexture*, + const NVNtextureView*, const NVNcopyRegion*, + const int*, int); +typedef void (*nvnCommandBufferClearTextureuiFunction)(NVNcommandBuffer*, const NVNtexture*, + const NVNtextureView*, const NVNcopyRegion*, + const uint32_t*, int); +typedef void (*nvnCommandBufferUpdateUniformBufferFunction)(NVNcommandBuffer*, NVNbufferAddress, + size_t, ptrdiff_t, size_t, const void*); +typedef void (*nvnCommandBufferReportCounterFunction)(NVNcommandBuffer*, NVNcounterType, + NVNbufferAddress); +typedef void (*nvnCommandBufferResetCounterFunction)(NVNcommandBuffer*, NVNcounterType); +typedef void (*nvnCommandBufferReportValueFunction)(NVNcommandBuffer*, uint32_t, NVNbufferAddress); +typedef void (*nvnCommandBufferSetRenderEnableFunction)(NVNcommandBuffer*, bool); +typedef void (*nvnCommandBufferSetRenderEnableConditionalFunction)(NVNcommandBuffer*, + NVNconditionalRenderMode, + NVNbufferAddress); +typedef void (*nvnCommandBufferSetRenderTargetsFunction)(NVNcommandBuffer*, int, + const NVNtexture* const*, + const NVNtextureView* const*, + const NVNtexture*, const NVNtextureView*); +typedef void (*nvnCommandBufferDiscardColorFunction)(NVNcommandBuffer*, int); +typedef void (*nvnCommandBufferDiscardDepthStencilFunction)(NVNcommandBuffer*); +typedef void (*nvnCommandBufferDownsampleFunction)(NVNcommandBuffer*, const NVNtexture*, + const NVNtexture*); +typedef void (*nvnCommandBufferTiledDownsampleFunction)(NVNcommandBuffer*, const NVNtexture*, + const NVNtexture*); +typedef void (*nvnCommandBufferDownsampleTextureViewFunction)(NVNcommandBuffer*, const NVNtexture*, + const NVNtextureView*, + const NVNtexture*, + const NVNtextureView*); +typedef void (*nvnCommandBufferTiledDownsampleTextureViewFunction)(NVNcommandBuffer*, + const NVNtexture*, + const NVNtextureView*, + const NVNtexture*, + const NVNtextureView*); +typedef void (*nvnCommandBufferBarrierFunction)(NVNcommandBuffer*, int); +typedef void (*nvnCommandBufferWaitSyncFunction)(NVNcommandBuffer*, const NVNsync*); +typedef void (*nvnCommandBufferFenceSyncFunction)(NVNcommandBuffer*, NVNsync*, NVNsyncCondition, + int); +typedef void (*nvnCommandBufferSetTexturePoolFunction)(NVNcommandBuffer*, const NVNtexturePool*); +typedef void (*nvnCommandBufferSetSamplerPoolFunction)(NVNcommandBuffer*, const NVNsamplerPool*); +typedef void (*nvnCommandBufferSetShaderScratchMemoryFunction)(NVNcommandBuffer*, + const NVNmemoryPool*, ptrdiff_t, + size_t); +typedef void (*nvnCommandBufferSaveZCullDataFunction)(NVNcommandBuffer*, NVNbufferAddress, size_t); +typedef void (*nvnCommandBufferRestoreZCullDataFunction)(NVNcommandBuffer*, NVNbufferAddress, + size_t); +typedef void (*nvnCommandBufferSetCopyRowStrideFunction)(NVNcommandBuffer*, ptrdiff_t); +typedef void (*nvnCommandBufferSetCopyImageStrideFunction)(NVNcommandBuffer*, ptrdiff_t); +typedef ptrdiff_t (*nvnCommandBufferGetCopyRowStrideFunction)(const NVNcommandBuffer*); +typedef ptrdiff_t (*nvnCommandBufferGetCopyImageStrideFunction)(const NVNcommandBuffer*); +typedef void (*nvnCommandBufferDrawTextureFunction)(NVNcommandBuffer*, NVNtextureHandle, + const NVNdrawTextureRegion*, + const NVNdrawTextureRegion*); +typedef bool (*nvnProgramSetSubroutineLinkageFunction)(NVNprogram*, int, + const NVNsubroutineLinkageMapPtr*); +typedef void (*nvnCommandBufferSetProgramSubroutinesFunction)(NVNcommandBuffer*, NVNprogram*, + NVNshaderStage, const int, const int, + const int*); +typedef void (*nvnCommandBufferBindCoverageModulationTableFunction)(NVNcommandBuffer*, + const float*); +typedef void (*nvnCommandBufferResolveDepthBufferFunction)(NVNcommandBuffer*); +typedef void (*nvnCommandBufferPushDebugGroupStaticFunction)(NVNcommandBuffer*, uint32_t, + const char*); +typedef void (*nvnCommandBufferPushDebugGroupDynamicFunction)(NVNcommandBuffer*, uint32_t, + const char*); +typedef void (*nvnCommandBufferPushDebugGroupFunction)(NVNcommandBuffer*, uint32_t, const char*); +typedef void (*nvnCommandBufferPopDebugGroupFunction)(NVNcommandBuffer*); +typedef void (*nvnCommandBufferPopDebugGroupIdFunction)(NVNcommandBuffer*, uint32_t); +typedef void (*nvnCommandBufferInsertDebugMarkerStaticFunction)(NVNcommandBuffer*, uint32_t, + const char*); +typedef void (*nvnCommandBufferInsertDebugMarkerDynamicFunction)(NVNcommandBuffer*, uint32_t, + const char*); +typedef void (*nvnCommandBufferInsertDebugMarkerFunction)(NVNcommandBuffer*, uint32_t, const char*); +typedef NVNcommandBufferMemoryCallback (*nvnCommandBufferGetMemoryCallbackFunction)( + const NVNcommandBuffer*); +typedef void (*nvnCommandBufferGetMemoryCallbackDataFunction)(const NVNcommandBuffer*); +typedef bool (*nvnCommandBufferIsRecordingFunction)(const NVNcommandBuffer*); +typedef bool (*nvnSyncInitializeFunction)(NVNsync*, NVNdevice*); +typedef void (*nvnSyncFinalizeFunction)(NVNsync*); +typedef void (*nvnSyncSetDebugLabelFunction)(NVNsync*, const char*); +typedef void (*nvnQueueFenceSyncFunction)(NVNqueue*, NVNsync*, NVNsyncCondition, int); +typedef NVNsyncWaitResult (*nvnSyncWaitFunction)(const NVNsync*, uint64_t); +typedef bool (*nvnQueueWaitSyncFunction)(NVNqueue*, const NVNsync*); +typedef void (*nvnEventBuilderSetDefaultsFunction)(NVNeventBuilder*); +typedef void (*nvnEventBuilderSetStorageFunction)(NVNeventBuilder*, const NVNmemoryPool*, int64_t); +typedef bool (*nvnEventInitializeFunction)(NVNevent*, const NVNeventBuilder*); +typedef void (*nvnEventFinalizeFunction)(NVNevent*); +typedef uint32_t (*nvnEventGetValueFunction)(const NVNevent*); +typedef void (*nvnEventSignalFunction)(NVNevent*, NVNeventSignalMode, uint32_t); +typedef void (*nvnCommandBufferWaitEventFunction)(NVNcommandBuffer*, const NVNevent*, + NVNeventWaitMode, uint32_t); +typedef void (*nvnCommandBufferSignalEventFunction)(NVNcommandBuffer*, const NVNevent*, + NVNeventSignalMode, NVNeventSignalLocation, int, + uint32_t); + +// Function pointer definitions +extern nvnDeviceBuilderSetDefaultsFunction pfnc_nvnDeviceBuilderSetDefaults; +extern nvnDeviceBuilderSetFlagsFunction pfnc_nvnDeviceBuilderSetFlags; +extern nvnDeviceInitializeFunction pfnc_nvnDeviceInitialize; +extern nvnDeviceFinalizeFunction pfnc_nvnDeviceFinalize; +extern nvnDeviceSetDebugLabelFunction pfnc_nvnDeviceSetDebugLabel; +extern nvnDeviceGetProcAddressFunction pfnc_nvnDeviceGetProcAddress; +extern nvnDeviceGetIntegerFunction pfnc_nvnDeviceGetInteger; +extern nvnDeviceGetCurrentTimestampInNanosecondsFunction + pfnc_nvnDeviceGetCurrentTimestampInNanoseconds; +extern nvnDeviceSetIntermediateShaderCacheFunction pfnc_nvnDeviceSetIntermediateShaderCache; +extern nvnDeviceGetTextureHandleFunction pfnc_nvnDeviceGetTextureHandle; +extern nvnDeviceGetTexelFetchHandleFunction pfnc_nvnDeviceGetTexelFetchHandle; +extern nvnDeviceGetImageHandleFunction pfnc_nvnDeviceGetImageHandle; +extern nvnDeviceInstallDebugCallbackFunction pfnc_nvnDeviceInstallDebugCallback; +extern nvnDeviceGenerateDebugDomainIdFunction pfnc_nvnDeviceGenerateDebugDomainId; +extern nvnDeviceSetWindowOriginModeFunction pfnc_nvnDeviceSetWindowOriginMode; +extern nvnDeviceSetDepthModeFunction pfnc_nvnDeviceSetDepthMode; +extern nvnDeviceRegisterFastClearColorFunction pfnc_nvnDeviceRegisterFastClearColor; +extern nvnDeviceRegisterFastClearColoriFunction pfnc_nvnDeviceRegisterFastClearColori; +extern nvnDeviceRegisterFastClearColoruiFunction pfnc_nvnDeviceRegisterFastClearColorui; +extern nvnDeviceRegisterFastClearDepthFunction pfnc_nvnDeviceRegisterFastClearDepth; +extern nvnDeviceGetWindowOriginModeFunction pfnc_nvnDeviceGetWindowOriginMode; +extern nvnDeviceGetDepthModeFunction pfnc_nvnDeviceGetDepthMode; +extern nvnDeviceGetTimestampInNanosecondsFunction pfnc_nvnDeviceGetTimestampInNanoseconds; +extern nvnDeviceApplyDeferredFinalizesFunction pfnc_nvnDeviceApplyDeferredFinalizes; +extern nvnDeviceFinalizeCommandHandleFunction pfnc_nvnDeviceFinalizeCommandHandle; +extern nvnDeviceWalkDebugDatabaseFunction pfnc_nvnDeviceWalkDebugDatabase; +extern nvnDeviceGetSeparateTextureHandleFunction pfnc_nvnDeviceGetSeparateTextureHandle; +extern nvnDeviceGetSeparateSamplerHandleFunction pfnc_nvnDeviceGetSeparateSamplerHandle; +extern nvnDeviceIsExternalDebuggerAttachedFunction pfnc_nvnDeviceIsExternalDebuggerAttached; +extern nvnQueueGetErrorFunction pfnc_nvnQueueGetError; +extern nvnQueueGetTotalCommandMemoryUsedFunction pfnc_nvnQueueGetTotalCommandMemoryUsed; +extern nvnQueueGetTotalControlMemoryUsedFunction pfnc_nvnQueueGetTotalControlMemoryUsed; +extern nvnQueueGetTotalComputeMemoryUsedFunction pfnc_nvnQueueGetTotalComputeMemoryUsed; +extern nvnQueueResetMemoryUsageCountsFunction pfnc_nvnQueueResetMemoryUsageCounts; +extern nvnQueueBuilderSetDeviceFunction pfnc_nvnQueueBuilderSetDevice; +extern nvnQueueBuilderSetDefaultsFunction pfnc_nvnQueueBuilderSetDefaults; +extern nvnQueueBuilderSetFlagsFunction pfnc_nvnQueueBuilderSetFlags; +extern nvnQueueBuilderSetCommandMemorySizeFunction pfnc_nvnQueueBuilderSetCommandMemorySize; +extern nvnQueueBuilderSetComputeMemorySizeFunction pfnc_nvnQueueBuilderSetComputeMemorySize; +extern nvnQueueBuilderSetControlMemorySizeFunction pfnc_nvnQueueBuilderSetControlMemorySize; +extern nvnQueueBuilderGetQueueMemorySizeFunction pfnc_nvnQueueBuilderGetQueueMemorySize; +extern nvnQueueBuilderSetQueueMemoryFunction pfnc_nvnQueueBuilderSetQueueMemory; +extern nvnQueueBuilderSetCommandFlushThresholdFunction pfnc_nvnQueueBuilderSetCommandFlushThreshold; +extern nvnQueueInitializeFunction pfnc_nvnQueueInitialize; +extern nvnQueueFinalizeFunction pfnc_nvnQueueFinalize; +extern nvnQueueSetDebugLabelFunction pfnc_nvnQueueSetDebugLabel; +extern nvnQueueSubmitCommandsFunction pfnc_nvnQueueSubmitCommands; +extern nvnQueueFlushFunction pfnc_nvnQueueFlush; +extern nvnQueueFinishFunction pfnc_nvnQueueFinish; +extern nvnQueuePresentTextureFunction pfnc_nvnQueuePresentTexture; +extern nvnQueueAcquireTextureFunction pfnc_nvnQueueAcquireTexture; +extern nvnWindowBuilderSetDeviceFunction pfnc_nvnWindowBuilderSetDevice; +extern nvnWindowBuilderSetDefaultsFunction pfnc_nvnWindowBuilderSetDefaults; +extern nvnWindowBuilderSetNativeWindowFunction pfnc_nvnWindowBuilderSetNativeWindow; +extern nvnWindowBuilderSetTexturesFunction pfnc_nvnWindowBuilderSetTextures; +extern nvnWindowBuilderSetPresentIntervalFunction pfnc_nvnWindowBuilderSetPresentInterval; +extern nvnWindowBuilderGetNativeWindowFunction pfnc_nvnWindowBuilderGetNativeWindow; +extern nvnWindowBuilderGetPresentIntervalFunction pfnc_nvnWindowBuilderGetPresentInterval; +extern nvnWindowInitializeFunction pfnc_nvnWindowInitialize; +extern nvnWindowFinalizeFunction pfnc_nvnWindowFinalize; +extern nvnWindowSetDebugLabelFunction pfnc_nvnWindowSetDebugLabel; +extern nvnWindowAcquireTextureFunction pfnc_nvnWindowAcquireTexture; +extern nvnWindowGetNativeWindowFunction pfnc_nvnWindowGetNativeWindow; +extern nvnWindowGetPresentIntervalFunction pfnc_nvnWindowGetPresentInterval; +extern nvnWindowSetPresentIntervalFunction pfnc_nvnWindowSetPresentInterval; +extern nvnWindowSetCropFunction pfnc_nvnWindowSetCrop; +extern nvnWindowGetCropFunction pfnc_nvnWindowGetCrop; +extern nvnProgramInitializeFunction pfnc_nvnProgramInitialize; +extern nvnProgramFinalizeFunction pfnc_nvnProgramFinalize; +extern nvnProgramSetDebugLabelFunction pfnc_nvnProgramSetDebugLabel; +extern nvnProgramSetShadersFunction pfnc_nvnProgramSetShaders; +extern nvnMemoryPoolBuilderSetDeviceFunction pfnc_nvnMemoryPoolBuilderSetDevice; +extern nvnMemoryPoolBuilderSetDefaultsFunction pfnc_nvnMemoryPoolBuilderSetDefaults; +extern nvnMemoryPoolBuilderSetStorageFunction pfnc_nvnMemoryPoolBuilderSetStorage; +extern nvnMemoryPoolBuilderSetFlagsFunction pfnc_nvnMemoryPoolBuilderSetFlags; +extern nvnMemoryPoolBuilderGetMemoryFunction pfnc_nvnMemoryPoolBuilderGetMemory; +extern nvnMemoryPoolBuilderGetSizeFunction pfnc_nvnMemoryPoolBuilderGetSize; +extern nvnMemoryPoolBuilderGetFlagsFunction pfnc_nvnMemoryPoolBuilderGetFlags; +extern nvnMemoryPoolInitializeFunction pfnc_nvnMemoryPoolInitialize; +extern nvnMemoryPoolSetDebugLabelFunction pfnc_nvnMemoryPoolSetDebugLabel; +extern nvnMemoryPoolFinalizeFunction pfnc_nvnMemoryPoolFinalize; +extern nvnMemoryPoolMapFunction pfnc_nvnMemoryPoolMap; +extern nvnMemoryPoolFlushMappedRangeFunction pfnc_nvnMemoryPoolFlushMappedRange; +extern nvnMemoryPoolInvalidateMappedRangeFunction pfnc_nvnMemoryPoolInvalidateMappedRange; +extern nvnMemoryPoolGetBufferAddressFunction pfnc_nvnMemoryPoolGetBufferAddress; +extern nvnMemoryPoolMapVirtualFunction pfnc_nvnMemoryPoolMapVirtual; +extern nvnMemoryPoolGetSizeFunction pfnc_nvnMemoryPoolGetSize; +extern nvnMemoryPoolGetFlagsFunction pfnc_nvnMemoryPoolGetFlags; +extern nvnTexturePoolInitializeFunction pfnc_nvnTexturePoolInitialize; +extern nvnTexturePoolSetDebugLabelFunction pfnc_nvnTexturePoolSetDebugLabel; +extern nvnTexturePoolFinalizeFunction pfnc_nvnTexturePoolFinalize; +extern nvnTexturePoolRegisterTextureFunction pfnc_nvnTexturePoolRegisterTexture; +extern nvnTexturePoolRegisterImageFunction pfnc_nvnTexturePoolRegisterImage; +extern nvnTexturePoolGetMemoryPoolFunction pfnc_nvnTexturePoolGetMemoryPool; +extern nvnTexturePoolGetMemoryOffsetFunction pfnc_nvnTexturePoolGetMemoryOffset; +extern nvnTexturePoolGetSizeFunction pfnc_nvnTexturePoolGetSize; +extern nvnSamplerPoolInitializeFunction pfnc_nvnSamplerPoolInitialize; +extern nvnSamplerPoolSetDebugLabelFunction pfnc_nvnSamplerPoolSetDebugLabel; +extern nvnSamplerPoolFinalizeFunction pfnc_nvnSamplerPoolFinalize; +extern nvnSamplerPoolRegisterSamplerFunction pfnc_nvnSamplerPoolRegisterSampler; +extern nvnSamplerPoolRegisterSamplerBuilderFunction pfnc_nvnSamplerPoolRegisterSamplerBuilder; +extern nvnSamplerPoolGetMemoryPoolFunction pfnc_nvnSamplerPoolGetMemoryPool; +extern nvnSamplerPoolGetMemoryOffsetFunction pfnc_nvnSamplerPoolGetMemoryOffset; +extern nvnSamplerPoolGetSizeFunction pfnc_nvnSamplerPoolGetSize; +extern nvnBufferBuilderSetDeviceFunction pfnc_nvnBufferBuilderSetDevice; +extern nvnBufferBuilderSetDefaultsFunction pfnc_nvnBufferBuilderSetDefaults; +extern nvnBufferBuilderSetStorageFunction pfnc_nvnBufferBuilderSetStorage; +extern nvnBufferBuilderGetMemoryPoolFunction pfnc_nvnBufferBuilderGetMemoryPool; +extern nvnBufferBuilderGetMemoryOffsetFunction pfnc_nvnBufferBuilderGetMemoryOffset; +extern nvnBufferBuilderGetSizeFunction pfnc_nvnBufferBuilderGetSize; +extern nvnBufferInitializeFunction pfnc_nvnBufferInitialize; +extern nvnBufferSetDebugLabelFunction pfnc_nvnBufferSetDebugLabel; +extern nvnBufferFinalizeFunction pfnc_nvnBufferFinalize; +extern nvnBufferMapFunction pfnc_nvnBufferMap; +extern nvnBufferGetAddressFunction pfnc_nvnBufferGetAddress; +extern nvnBufferFlushMappedRangeFunction pfnc_nvnBufferFlushMappedRange; +extern nvnBufferInvalidateMappedRangeFunction pfnc_nvnBufferInvalidateMappedRange; +extern nvnBufferGetMemoryPoolFunction pfnc_nvnBufferGetMemoryPool; +extern nvnBufferGetMemoryOffsetFunction pfnc_nvnBufferGetMemoryOffset; +extern nvnBufferGetSizeFunction pfnc_nvnBufferGetSize; +extern nvnBufferGetDebugIDFunction pfnc_nvnBufferGetDebugID; +extern nvnTextureBuilderSetDeviceFunction pfnc_nvnTextureBuilderSetDevice; +extern nvnTextureBuilderSetDefaultsFunction pfnc_nvnTextureBuilderSetDefaults; +extern nvnTextureBuilderSetFlagsFunction pfnc_nvnTextureBuilderSetFlags; +extern nvnTextureBuilderSetTargetFunction pfnc_nvnTextureBuilderSetTarget; +extern nvnTextureBuilderSetWidthFunction pfnc_nvnTextureBuilderSetWidth; +extern nvnTextureBuilderSetHeightFunction pfnc_nvnTextureBuilderSetHeight; +extern nvnTextureBuilderSetDepthFunction pfnc_nvnTextureBuilderSetDepth; +extern nvnTextureBuilderSetSize1DFunction pfnc_nvnTextureBuilderSetSize1D; +extern nvnTextureBuilderSetSize2DFunction pfnc_nvnTextureBuilderSetSize2D; +extern nvnTextureBuilderSetSize3DFunction pfnc_nvnTextureBuilderSetSize3D; +extern nvnTextureBuilderSetLevelsFunction pfnc_nvnTextureBuilderSetLevels; +extern nvnTextureBuilderSetFormatFunction pfnc_nvnTextureBuilderSetFormat; +extern nvnTextureBuilderSetSamplesFunction pfnc_nvnTextureBuilderSetSamples; +extern nvnTextureBuilderSetSwizzleFunction pfnc_nvnTextureBuilderSetSwizzle; +extern nvnTextureBuilderSetDepthStencilModeFunction pfnc_nvnTextureBuilderSetDepthStencilMode; +extern nvnTextureBuilderGetStorageSizeFunction pfnc_nvnTextureBuilderGetStorageSize; +extern nvnTextureBuilderGetStorageAlignmentFunction pfnc_nvnTextureBuilderGetStorageAlignment; +extern nvnTextureBuilderSetStorageFunction pfnc_nvnTextureBuilderSetStorage; +extern nvnTextureBuilderSetPackagedTextureDataFunction pfnc_nvnTextureBuilderSetPackagedTextureData; +extern nvnTextureBuilderSetPackagedTextureLayoutFunction + pfnc_nvnTextureBuilderSetPackagedTextureLayout; +extern nvnTextureBuilderSetStrideFunction pfnc_nvnTextureBuilderSetStride; +extern nvnTextureBuilderSetGLTextureNameFunction pfnc_nvnTextureBuilderSetGLTextureName; +extern nvnTextureBuilderGetStorageClassFunction pfnc_nvnTextureBuilderGetStorageClass; +extern nvnTextureBuilderGetFlagsFunction pfnc_nvnTextureBuilderGetFlags; +extern nvnTextureBuilderGetTargetFunction pfnc_nvnTextureBuilderGetTarget; +extern nvnTextureBuilderGetWidthFunction pfnc_nvnTextureBuilderGetWidth; +extern nvnTextureBuilderGetHeightFunction pfnc_nvnTextureBuilderGetHeight; +extern nvnTextureBuilderGetDepthFunction pfnc_nvnTextureBuilderGetDepth; +extern nvnTextureBuilderGetLevelsFunction pfnc_nvnTextureBuilderGetLevels; +extern nvnTextureBuilderGetFormatFunction pfnc_nvnTextureBuilderGetFormat; +extern nvnTextureBuilderGetSamplesFunction pfnc_nvnTextureBuilderGetSamples; +extern nvnTextureBuilderGetSwizzleFunction pfnc_nvnTextureBuilderGetSwizzle; +extern nvnTextureBuilderGetDepthStencilModeFunction pfnc_nvnTextureBuilderGetDepthStencilMode; +extern nvnTextureBuilderGetPackagedTextureDataFunction pfnc_nvnTextureBuilderGetPackagedTextureData; +extern nvnTextureBuilderGetStrideFunction pfnc_nvnTextureBuilderGetStride; +extern nvnTextureBuilderGetSparseTileLayoutFunction pfnc_nvnTextureBuilderGetSparseTileLayout; +extern nvnTextureBuilderGetGLTextureNameFunction pfnc_nvnTextureBuilderGetGLTextureName; +extern nvnTextureBuilderGetZCullStorageSizeFunction pfnc_nvnTextureBuilderGetZCullStorageSize; +extern nvnTextureBuilderGetMemoryPoolFunction pfnc_nvnTextureBuilderGetMemoryPool; +extern nvnTextureBuilderGetMemoryOffsetFunction pfnc_nvnTextureBuilderGetMemoryOffset; +extern nvnTextureViewSetDefaultsFunction pfnc_nvnTextureViewSetDefaults; +extern nvnTextureViewSetLevelsFunction pfnc_nvnTextureViewSetLevels; +extern nvnTextureViewSetLayersFunction pfnc_nvnTextureViewSetLayers; +extern nvnTextureViewSetFormatFunction pfnc_nvnTextureViewSetFormat; +extern nvnTextureViewSetSwizzleFunction pfnc_nvnTextureViewSetSwizzle; +extern nvnTextureViewSetDepthStencilModeFunction pfnc_nvnTextureViewSetDepthStencilMode; +extern nvnTextureViewSetTargetFunction pfnc_nvnTextureViewSetTarget; +extern nvnTextureViewGetLevelsFunction pfnc_nvnTextureViewGetLevels; +extern nvnTextureViewGetLayersFunction pfnc_nvnTextureViewGetLayers; +extern nvnTextureViewGetFormatFunction pfnc_nvnTextureViewGetFormat; +extern nvnTextureViewGetSwizzleFunction pfnc_nvnTextureViewGetSwizzle; +extern nvnTextureViewGetDepthStencilModeFunction pfnc_nvnTextureViewGetDepthStencilMode; +extern nvnTextureViewGetTargetFunction pfnc_nvnTextureViewGetTarget; +extern nvnTextureViewCompareFunction pfnc_nvnTextureViewCompare; +extern nvnTextureInitializeFunction pfnc_nvnTextureInitialize; +extern nvnTextureGetZCullStorageSizeFunction pfnc_nvnTextureGetZCullStorageSize; +extern nvnTextureFinalizeFunction pfnc_nvnTextureFinalize; +extern nvnTextureSetDebugLabelFunction pfnc_nvnTextureSetDebugLabel; +extern nvnTextureGetStorageClassFunction pfnc_nvnTextureGetStorageClass; +extern nvnTextureGetViewOffsetFunction pfnc_nvnTextureGetViewOffset; +extern nvnTextureGetFlagsFunction pfnc_nvnTextureGetFlags; +extern nvnTextureGetTargetFunction pfnc_nvnTextureGetTarget; +extern nvnTextureGetWidthFunction pfnc_nvnTextureGetWidth; +extern nvnTextureGetHeightFunction pfnc_nvnTextureGetHeight; +extern nvnTextureGetDepthFunction pfnc_nvnTextureGetDepth; +extern nvnTextureGetLevelsFunction pfnc_nvnTextureGetLevels; +extern nvnTextureGetFormatFunction pfnc_nvnTextureGetFormat; +extern nvnTextureGetSamplesFunction pfnc_nvnTextureGetSamples; +extern nvnTextureGetSwizzleFunction pfnc_nvnTextureGetSwizzle; +extern nvnTextureGetDepthStencilModeFunction pfnc_nvnTextureGetDepthStencilMode; +extern nvnTextureGetStrideFunction pfnc_nvnTextureGetStride; +extern nvnTextureGetTextureAddressFunction pfnc_nvnTextureGetTextureAddress; +extern nvnTextureGetSparseTileLayoutFunction pfnc_nvnTextureGetSparseTileLayout; +extern nvnTextureWriteTexelsFunction pfnc_nvnTextureWriteTexels; +extern nvnTextureWriteTexelsStridedFunction pfnc_nvnTextureWriteTexelsStrided; +extern nvnTextureReadTexelsFunction pfnc_nvnTextureReadTexels; +extern nvnTextureReadTexelsStridedFunction pfnc_nvnTextureReadTexelsStrided; +extern nvnTextureFlushTexelsFunction pfnc_nvnTextureFlushTexels; +extern nvnTextureInvalidateTexelsFunction pfnc_nvnTextureInvalidateTexels; +extern nvnTextureGetMemoryPoolFunction pfnc_nvnTextureGetMemoryPool; +extern nvnTextureGetMemoryOffsetFunction pfnc_nvnTextureGetMemoryOffset; +extern nvnTextureGetStorageSizeFunction pfnc_nvnTextureGetStorageSize; +extern nvnTextureCompareFunction pfnc_nvnTextureCompare; +extern nvnTextureGetDebugIDFunction pfnc_nvnTextureGetDebugID; +extern nvnSamplerBuilderSetDeviceFunction pfnc_nvnSamplerBuilderSetDevice; +extern nvnSamplerBuilderSetDefaultsFunction pfnc_nvnSamplerBuilderSetDefaults; +extern nvnSamplerBuilderSetMinMagFilterFunction pfnc_nvnSamplerBuilderSetMinMagFilter; +extern nvnSamplerBuilderSetWrapModeFunction pfnc_nvnSamplerBuilderSetWrapMode; +extern nvnSamplerBuilderSetLodClampFunction pfnc_nvnSamplerBuilderSetLodClamp; +extern nvnSamplerBuilderSetLodBiasFunction pfnc_nvnSamplerBuilderSetLodBias; +extern nvnSamplerBuilderSetCompareFunction pfnc_nvnSamplerBuilderSetCompare; +extern nvnSamplerBuilderSetBorderColorFunction pfnc_nvnSamplerBuilderSetBorderColor; +extern nvnSamplerBuilderSetBorderColoriFunction pfnc_nvnSamplerBuilderSetBorderColori; +extern nvnSamplerBuilderSetBorderColoruiFunction pfnc_nvnSamplerBuilderSetBorderColorui; +extern nvnSamplerBuilderSetMaxAnisotropyFunction pfnc_nvnSamplerBuilderSetMaxAnisotropy; +extern nvnSamplerBuilderSetReductionFilterFunction pfnc_nvnSamplerBuilderSetReductionFilter; +extern nvnSamplerBuilderSetLodSnapFunction pfnc_nvnSamplerBuilderSetLodSnap; +extern nvnSamplerBuilderGetMinMagFilterFunction pfnc_nvnSamplerBuilderGetMinMagFilter; +extern nvnSamplerBuilderGetWrapModeFunction pfnc_nvnSamplerBuilderGetWrapMode; +extern nvnSamplerBuilderGetLodClampFunction pfnc_nvnSamplerBuilderGetLodClamp; +extern nvnSamplerBuilderGetLodBiasFunction pfnc_nvnSamplerBuilderGetLodBias; +extern nvnSamplerBuilderGetCompareFunction pfnc_nvnSamplerBuilderGetCompare; +extern nvnSamplerBuilderGetBorderColorFunction pfnc_nvnSamplerBuilderGetBorderColor; +extern nvnSamplerBuilderGetBorderColoriFunction pfnc_nvnSamplerBuilderGetBorderColori; +extern nvnSamplerBuilderGetBorderColoruiFunction pfnc_nvnSamplerBuilderGetBorderColorui; +extern nvnSamplerBuilderGetMaxAnisotropyFunction pfnc_nvnSamplerBuilderGetMaxAnisotropy; +extern nvnSamplerBuilderGetReductionFilterFunction pfnc_nvnSamplerBuilderGetReductionFilter; +extern nvnSamplerBuilderGetLodSnapFunction pfnc_nvnSamplerBuilderGetLodSnap; +extern nvnSamplerInitializeFunction pfnc_nvnSamplerInitialize; +extern nvnSamplerFinalizeFunction pfnc_nvnSamplerFinalize; +extern nvnSamplerSetDebugLabelFunction pfnc_nvnSamplerSetDebugLabel; +extern nvnSamplerGetMinMagFilterFunction pfnc_nvnSamplerGetMinMagFilter; +extern nvnSamplerGetWrapModeFunction pfnc_nvnSamplerGetWrapMode; +extern nvnSamplerGetLodClampFunction pfnc_nvnSamplerGetLodClamp; +extern nvnSamplerGetLodBiasFunction pfnc_nvnSamplerGetLodBias; +extern nvnSamplerGetCompareFunction pfnc_nvnSamplerGetCompare; +extern nvnSamplerGetBorderColorFunction pfnc_nvnSamplerGetBorderColor; +extern nvnSamplerGetBorderColoriFunction pfnc_nvnSamplerGetBorderColori; +extern nvnSamplerGetBorderColoruiFunction pfnc_nvnSamplerGetBorderColorui; +extern nvnSamplerGetMaxAnisotropyFunction pfnc_nvnSamplerGetMaxAnisotropy; +extern nvnSamplerGetReductionFilterFunction pfnc_nvnSamplerGetReductionFilter; +extern nvnSamplerCompareFunction pfnc_nvnSamplerCompare; +extern nvnSamplerGetDebugIDFunction pfnc_nvnSamplerGetDebugID; +extern nvnBlendStateSetDefaultsFunction pfnc_nvnBlendStateSetDefaults; +extern nvnBlendStateSetBlendTargetFunction pfnc_nvnBlendStateSetBlendTarget; +extern nvnBlendStateSetBlendFuncFunction pfnc_nvnBlendStateSetBlendFunc; +extern nvnBlendStateSetBlendEquationFunction pfnc_nvnBlendStateSetBlendEquation; +extern nvnBlendStateSetAdvancedModeFunction pfnc_nvnBlendStateSetAdvancedMode; +extern nvnBlendStateSetAdvancedOverlapFunction pfnc_nvnBlendStateSetAdvancedOverlap; +extern nvnBlendStateSetAdvancedPremultipliedSrcFunction + pfnc_nvnBlendStateSetAdvancedPremultipliedSrc; +extern nvnBlendStateSetAdvancedNormalizedDstFunction pfnc_nvnBlendStateSetAdvancedNormalizedDst; +extern nvnBlendStateGetBlendTargetFunction pfnc_nvnBlendStateGetBlendTarget; +extern nvnBlendStateGetBlendFuncFunction pfnc_nvnBlendStateGetBlendFunc; +extern nvnBlendStateGetBlendEquationFunction pfnc_nvnBlendStateGetBlendEquation; +extern nvnBlendStateGetAdvancedModeFunction pfnc_nvnBlendStateGetAdvancedMode; +extern nvnBlendStateGetAdvancedOverlapFunction pfnc_nvnBlendStateGetAdvancedOverlap; +extern nvnBlendStateGetAdvancedPremultipliedSrcFunction + pfnc_nvnBlendStateGetAdvancedPremultipliedSrc; +extern nvnBlendStateGetAdvancedNormalizedDstFunction pfnc_nvnBlendStateGetAdvancedNormalizedDst; +extern nvnColorStateSetDefaultsFunction pfnc_nvnColorStateSetDefaults; +extern nvnColorStateSetBlendEnableFunction pfnc_nvnColorStateSetBlendEnable; +extern nvnColorStateSetLogicOpFunction pfnc_nvnColorStateSetLogicOp; +extern nvnColorStateSetAlphaTestFunction pfnc_nvnColorStateSetAlphaTest; +extern nvnColorStateGetBlendEnableFunction pfnc_nvnColorStateGetBlendEnable; +extern nvnColorStateGetLogicOpFunction pfnc_nvnColorStateGetLogicOp; +extern nvnColorStateGetAlphaTestFunction pfnc_nvnColorStateGetAlphaTest; +extern nvnChannelMaskStateSetDefaultsFunction pfnc_nvnChannelMaskStateSetDefaults; +extern nvnChannelMaskStateSetChannelMaskFunction pfnc_nvnChannelMaskStateSetChannelMask; +extern nvnChannelMaskStateGetChannelMaskFunction pfnc_nvnChannelMaskStateGetChannelMask; +extern nvnMultisampleStateSetDefaultsFunction pfnc_nvnMultisampleStateSetDefaults; +extern nvnMultisampleStateSetMultisampleEnableFunction pfnc_nvnMultisampleStateSetMultisampleEnable; +extern nvnMultisampleStateSetSamplesFunction pfnc_nvnMultisampleStateSetSamples; +extern nvnMultisampleStateSetAlphaToCoverageEnableFunction + pfnc_nvnMultisampleStateSetAlphaToCoverageEnable; +extern nvnMultisampleStateSetAlphaToCoverageDitherFunction + pfnc_nvnMultisampleStateSetAlphaToCoverageDither; +extern nvnMultisampleStateGetMultisampleEnableFunction pfnc_nvnMultisampleStateGetMultisampleEnable; +extern nvnMultisampleStateGetSamplesFunction pfnc_nvnMultisampleStateGetSamples; +extern nvnMultisampleStateGetAlphaToCoverageEnableFunction + pfnc_nvnMultisampleStateGetAlphaToCoverageEnable; +extern nvnMultisampleStateGetAlphaToCoverageDitherFunction + pfnc_nvnMultisampleStateGetAlphaToCoverageDither; +extern nvnMultisampleStateSetRasterSamplesFunction pfnc_nvnMultisampleStateSetRasterSamples; +extern nvnMultisampleStateGetRasterSamplesFunction pfnc_nvnMultisampleStateGetRasterSamples; +extern nvnMultisampleStateSetCoverageModulationModeFunction + pfnc_nvnMultisampleStateSetCoverageModulationMode; +extern nvnMultisampleStateGetCoverageModulationModeFunction + pfnc_nvnMultisampleStateGetCoverageModulationMode; +extern nvnMultisampleStateSetCoverageToColorEnableFunction + pfnc_nvnMultisampleStateSetCoverageToColorEnable; +extern nvnMultisampleStateGetCoverageToColorEnableFunction + pfnc_nvnMultisampleStateGetCoverageToColorEnable; +extern nvnMultisampleStateSetCoverageToColorOutputFunction + pfnc_nvnMultisampleStateSetCoverageToColorOutput; +extern nvnMultisampleStateGetCoverageToColorOutputFunction + pfnc_nvnMultisampleStateGetCoverageToColorOutput; +extern nvnMultisampleStateSetSampleLocationsEnableFunction + pfnc_nvnMultisampleStateSetSampleLocationsEnable; +extern nvnMultisampleStateGetSampleLocationsEnableFunction + pfnc_nvnMultisampleStateGetSampleLocationsEnable; +extern nvnMultisampleStateGetSampleLocationsGridFunction + pfnc_nvnMultisampleStateGetSampleLocationsGrid; +extern nvnMultisampleStateSetSampleLocationsGridEnableFunction + pfnc_nvnMultisampleStateSetSampleLocationsGridEnable; +extern nvnMultisampleStateGetSampleLocationsGridEnableFunction + pfnc_nvnMultisampleStateGetSampleLocationsGridEnable; +extern nvnMultisampleStateSetSampleLocationsFunction pfnc_nvnMultisampleStateSetSampleLocations; +extern nvnPolygonStateSetDefaultsFunction pfnc_nvnPolygonStateSetDefaults; +extern nvnPolygonStateSetCullFaceFunction pfnc_nvnPolygonStateSetCullFace; +extern nvnPolygonStateSetFrontFaceFunction pfnc_nvnPolygonStateSetFrontFace; +extern nvnPolygonStateSetPolygonModeFunction pfnc_nvnPolygonStateSetPolygonMode; +extern nvnPolygonStateSetPolygonOffsetEnablesFunction pfnc_nvnPolygonStateSetPolygonOffsetEnables; +extern nvnPolygonStateGetCullFaceFunction pfnc_nvnPolygonStateGetCullFace; +extern nvnPolygonStateGetFrontFaceFunction pfnc_nvnPolygonStateGetFrontFace; +extern nvnPolygonStateGetPolygonModeFunction pfnc_nvnPolygonStateGetPolygonMode; +extern nvnPolygonStateGetPolygonOffsetEnablesFunction pfnc_nvnPolygonStateGetPolygonOffsetEnables; +extern nvnDepthStencilStateSetDefaultsFunction pfnc_nvnDepthStencilStateSetDefaults; +extern nvnDepthStencilStateSetDepthTestEnableFunction pfnc_nvnDepthStencilStateSetDepthTestEnable; +extern nvnDepthStencilStateSetDepthWriteEnableFunction pfnc_nvnDepthStencilStateSetDepthWriteEnable; +extern nvnDepthStencilStateSetDepthFuncFunction pfnc_nvnDepthStencilStateSetDepthFunc; +extern nvnDepthStencilStateSetStencilTestEnableFunction + pfnc_nvnDepthStencilStateSetStencilTestEnable; +extern nvnDepthStencilStateSetStencilFuncFunction pfnc_nvnDepthStencilStateSetStencilFunc; +extern nvnDepthStencilStateSetStencilOpFunction pfnc_nvnDepthStencilStateSetStencilOp; +extern nvnDepthStencilStateGetDepthTestEnableFunction pfnc_nvnDepthStencilStateGetDepthTestEnable; +extern nvnDepthStencilStateGetDepthWriteEnableFunction pfnc_nvnDepthStencilStateGetDepthWriteEnable; +extern nvnDepthStencilStateGetDepthFuncFunction pfnc_nvnDepthStencilStateGetDepthFunc; +extern nvnDepthStencilStateGetStencilTestEnableFunction + pfnc_nvnDepthStencilStateGetStencilTestEnable; +extern nvnDepthStencilStateGetStencilFuncFunction pfnc_nvnDepthStencilStateGetStencilFunc; +extern nvnDepthStencilStateGetStencilOpFunction pfnc_nvnDepthStencilStateGetStencilOp; +extern nvnVertexAttribStateSetDefaultsFunction pfnc_nvnVertexAttribStateSetDefaults; +extern nvnVertexAttribStateSetFormatFunction pfnc_nvnVertexAttribStateSetFormat; +extern nvnVertexAttribStateSetStreamIndexFunction pfnc_nvnVertexAttribStateSetStreamIndex; +extern nvnVertexAttribStateGetFormatFunction pfnc_nvnVertexAttribStateGetFormat; +extern nvnVertexAttribStateGetStreamIndexFunction pfnc_nvnVertexAttribStateGetStreamIndex; +extern nvnVertexStreamStateSetDefaultsFunction pfnc_nvnVertexStreamStateSetDefaults; +extern nvnVertexStreamStateSetStrideFunction pfnc_nvnVertexStreamStateSetStride; +extern nvnVertexStreamStateSetDivisorFunction pfnc_nvnVertexStreamStateSetDivisor; +extern nvnVertexStreamStateGetStrideFunction pfnc_nvnVertexStreamStateGetStride; +extern nvnVertexStreamStateGetDivisorFunction pfnc_nvnVertexStreamStateGetDivisor; +extern nvnCommandBufferInitializeFunction pfnc_nvnCommandBufferInitialize; +extern nvnCommandBufferFinalizeFunction pfnc_nvnCommandBufferFinalize; +extern nvnCommandBufferSetDebugLabelFunction pfnc_nvnCommandBufferSetDebugLabel; +extern nvnCommandBufferSetMemoryCallbackFunction pfnc_nvnCommandBufferSetMemoryCallback; +extern nvnCommandBufferSetMemoryCallbackDataFunction pfnc_nvnCommandBufferSetMemoryCallbackData; +extern nvnCommandBufferAddCommandMemoryFunction pfnc_nvnCommandBufferAddCommandMemory; +extern nvnCommandBufferAddControlMemoryFunction pfnc_nvnCommandBufferAddControlMemory; +extern nvnCommandBufferGetCommandMemorySizeFunction pfnc_nvnCommandBufferGetCommandMemorySize; +extern nvnCommandBufferGetCommandMemoryUsedFunction pfnc_nvnCommandBufferGetCommandMemoryUsed; +extern nvnCommandBufferGetCommandMemoryFreeFunction pfnc_nvnCommandBufferGetCommandMemoryFree; +extern nvnCommandBufferGetControlMemorySizeFunction pfnc_nvnCommandBufferGetControlMemorySize; +extern nvnCommandBufferGetControlMemoryUsedFunction pfnc_nvnCommandBufferGetControlMemoryUsed; +extern nvnCommandBufferGetControlMemoryFreeFunction pfnc_nvnCommandBufferGetControlMemoryFree; +extern nvnCommandBufferBeginRecordingFunction pfnc_nvnCommandBufferBeginRecording; +extern nvnCommandBufferEndRecordingFunction pfnc_nvnCommandBufferEndRecording; +extern nvnCommandBufferCallCommandsFunction pfnc_nvnCommandBufferCallCommands; +extern nvnCommandBufferCopyCommandsFunction pfnc_nvnCommandBufferCopyCommands; +extern nvnCommandBufferBindBlendStateFunction pfnc_nvnCommandBufferBindBlendState; +extern nvnCommandBufferBindChannelMaskStateFunction pfnc_nvnCommandBufferBindChannelMaskState; +extern nvnCommandBufferBindColorStateFunction pfnc_nvnCommandBufferBindColorState; +extern nvnCommandBufferBindMultisampleStateFunction pfnc_nvnCommandBufferBindMultisampleState; +extern nvnCommandBufferBindPolygonStateFunction pfnc_nvnCommandBufferBindPolygonState; +extern nvnCommandBufferBindDepthStencilStateFunction pfnc_nvnCommandBufferBindDepthStencilState; +extern nvnCommandBufferBindVertexAttribStateFunction pfnc_nvnCommandBufferBindVertexAttribState; +extern nvnCommandBufferBindVertexStreamStateFunction pfnc_nvnCommandBufferBindVertexStreamState; +extern nvnCommandBufferBindProgramFunction pfnc_nvnCommandBufferBindProgram; +extern nvnCommandBufferBindVertexBufferFunction pfnc_nvnCommandBufferBindVertexBuffer; +extern nvnCommandBufferBindVertexBuffersFunction pfnc_nvnCommandBufferBindVertexBuffers; +extern nvnCommandBufferBindUniformBufferFunction pfnc_nvnCommandBufferBindUniformBuffer; +extern nvnCommandBufferBindUniformBuffersFunction pfnc_nvnCommandBufferBindUniformBuffers; +extern nvnCommandBufferBindTransformFeedbackBufferFunction + pfnc_nvnCommandBufferBindTransformFeedbackBuffer; +extern nvnCommandBufferBindTransformFeedbackBuffersFunction + pfnc_nvnCommandBufferBindTransformFeedbackBuffers; +extern nvnCommandBufferBindStorageBufferFunction pfnc_nvnCommandBufferBindStorageBuffer; +extern nvnCommandBufferBindStorageBuffersFunction pfnc_nvnCommandBufferBindStorageBuffers; +extern nvnCommandBufferBindTextureFunction pfnc_nvnCommandBufferBindTexture; +extern nvnCommandBufferBindTexturesFunction pfnc_nvnCommandBufferBindTextures; +extern nvnCommandBufferBindImageFunction pfnc_nvnCommandBufferBindImage; +extern nvnCommandBufferBindImagesFunction pfnc_nvnCommandBufferBindImages; +extern nvnCommandBufferSetPatchSizeFunction pfnc_nvnCommandBufferSetPatchSize; +extern nvnCommandBufferSetInnerTessellationLevelsFunction + pfnc_nvnCommandBufferSetInnerTessellationLevels; +extern nvnCommandBufferSetOuterTessellationLevelsFunction + pfnc_nvnCommandBufferSetOuterTessellationLevels; +extern nvnCommandBufferSetPrimitiveRestartFunction pfnc_nvnCommandBufferSetPrimitiveRestart; +extern nvnCommandBufferBeginTransformFeedbackFunction pfnc_nvnCommandBufferBeginTransformFeedback; +extern nvnCommandBufferEndTransformFeedbackFunction pfnc_nvnCommandBufferEndTransformFeedback; +extern nvnCommandBufferPauseTransformFeedbackFunction pfnc_nvnCommandBufferPauseTransformFeedback; +extern nvnCommandBufferResumeTransformFeedbackFunction pfnc_nvnCommandBufferResumeTransformFeedback; +extern nvnCommandBufferDrawTransformFeedbackFunction pfnc_nvnCommandBufferDrawTransformFeedback; +extern nvnCommandBufferDrawArraysFunction pfnc_nvnCommandBufferDrawArrays; +extern nvnCommandBufferDrawElementsFunction pfnc_nvnCommandBufferDrawElements; +extern nvnCommandBufferDrawElementsBaseVertexFunction pfnc_nvnCommandBufferDrawElementsBaseVertex; +extern nvnCommandBufferDrawArraysInstancedFunction pfnc_nvnCommandBufferDrawArraysInstanced; +extern nvnCommandBufferDrawElementsInstancedFunction pfnc_nvnCommandBufferDrawElementsInstanced; +extern nvnCommandBufferDrawArraysIndirectFunction pfnc_nvnCommandBufferDrawArraysIndirect; +extern nvnCommandBufferDrawElementsIndirectFunction pfnc_nvnCommandBufferDrawElementsIndirect; +extern nvnCommandBufferMultiDrawArraysIndirectCountFunction + pfnc_nvnCommandBufferMultiDrawArraysIndirectCount; +extern nvnCommandBufferMultiDrawElementsIndirectCountFunction + pfnc_nvnCommandBufferMultiDrawElementsIndirectCount; +extern nvnCommandBufferClearColorFunction pfnc_nvnCommandBufferClearColor; +extern nvnCommandBufferClearColoriFunction pfnc_nvnCommandBufferClearColori; +extern nvnCommandBufferClearColoruiFunction pfnc_nvnCommandBufferClearColorui; +extern nvnCommandBufferClearDepthStencilFunction pfnc_nvnCommandBufferClearDepthStencil; +extern nvnCommandBufferDispatchComputeFunction pfnc_nvnCommandBufferDispatchCompute; +extern nvnCommandBufferDispatchComputeIndirectFunction pfnc_nvnCommandBufferDispatchComputeIndirect; +extern nvnCommandBufferSetViewportFunction pfnc_nvnCommandBufferSetViewport; +extern nvnCommandBufferSetViewportsFunction pfnc_nvnCommandBufferSetViewports; +extern nvnCommandBufferSetViewportSwizzlesFunction pfnc_nvnCommandBufferSetViewportSwizzles; +extern nvnCommandBufferSetScissorFunction pfnc_nvnCommandBufferSetScissor; +extern nvnCommandBufferSetScissorsFunction pfnc_nvnCommandBufferSetScissors; +extern nvnCommandBufferSetDepthRangeFunction pfnc_nvnCommandBufferSetDepthRange; +extern nvnCommandBufferSetDepthBoundsFunction pfnc_nvnCommandBufferSetDepthBounds; +extern nvnCommandBufferSetDepthRangesFunction pfnc_nvnCommandBufferSetDepthRanges; +extern nvnCommandBufferSetTiledCacheActionFunction pfnc_nvnCommandBufferSetTiledCacheAction; +extern nvnCommandBufferSetTiledCacheTileSizeFunction pfnc_nvnCommandBufferSetTiledCacheTileSize; +extern nvnCommandBufferBindSeparateTextureFunction pfnc_nvnCommandBufferBindSeparateTexture; +extern nvnCommandBufferBindSeparateSamplerFunction pfnc_nvnCommandBufferBindSeparateSampler; +extern nvnCommandBufferBindSeparateTexturesFunction pfnc_nvnCommandBufferBindSeparateTextures; +extern nvnCommandBufferBindSeparateSamplersFunction pfnc_nvnCommandBufferBindSeparateSamplers; +extern nvnCommandBufferSetStencilValueMaskFunction pfnc_nvnCommandBufferSetStencilValueMask; +extern nvnCommandBufferSetStencilMaskFunction pfnc_nvnCommandBufferSetStencilMask; +extern nvnCommandBufferSetStencilRefFunction pfnc_nvnCommandBufferSetStencilRef; +extern nvnCommandBufferSetBlendColorFunction pfnc_nvnCommandBufferSetBlendColor; +extern nvnCommandBufferSetPointSizeFunction pfnc_nvnCommandBufferSetPointSize; +extern nvnCommandBufferSetLineWidthFunction pfnc_nvnCommandBufferSetLineWidth; +extern nvnCommandBufferSetPolygonOffsetClampFunction pfnc_nvnCommandBufferSetPolygonOffsetClamp; +extern nvnCommandBufferSetAlphaRefFunction pfnc_nvnCommandBufferSetAlphaRef; +extern nvnCommandBufferSetSampleMaskFunction pfnc_nvnCommandBufferSetSampleMask; +extern nvnCommandBufferSetRasterizerDiscardFunction pfnc_nvnCommandBufferSetRasterizerDiscard; +extern nvnCommandBufferSetDepthClampFunction pfnc_nvnCommandBufferSetDepthClamp; +extern nvnCommandBufferSetConservativeRasterEnableFunction + pfnc_nvnCommandBufferSetConservativeRasterEnable; +extern nvnCommandBufferSetConservativeRasterDilateFunction + pfnc_nvnCommandBufferSetConservativeRasterDilate; +extern nvnCommandBufferSetSubpixelPrecisionBiasFunction + pfnc_nvnCommandBufferSetSubpixelPrecisionBias; +extern nvnCommandBufferCopyBufferToTextureFunction pfnc_nvnCommandBufferCopyBufferToTexture; +extern nvnCommandBufferCopyTextureToBufferFunction pfnc_nvnCommandBufferCopyTextureToBuffer; +extern nvnCommandBufferCopyTextureToTextureFunction pfnc_nvnCommandBufferCopyTextureToTexture; +extern nvnCommandBufferCopyBufferToBufferFunction pfnc_nvnCommandBufferCopyBufferToBuffer; +extern nvnCommandBufferClearBufferFunction pfnc_nvnCommandBufferClearBuffer; +extern nvnCommandBufferClearTextureFunction pfnc_nvnCommandBufferClearTexture; +extern nvnCommandBufferClearTextureiFunction pfnc_nvnCommandBufferClearTexturei; +extern nvnCommandBufferClearTextureuiFunction pfnc_nvnCommandBufferClearTextureui; +extern nvnCommandBufferUpdateUniformBufferFunction pfnc_nvnCommandBufferUpdateUniformBuffer; +extern nvnCommandBufferReportCounterFunction pfnc_nvnCommandBufferReportCounter; +extern nvnCommandBufferResetCounterFunction pfnc_nvnCommandBufferResetCounter; +extern nvnCommandBufferReportValueFunction pfnc_nvnCommandBufferReportValue; +extern nvnCommandBufferSetRenderEnableFunction pfnc_nvnCommandBufferSetRenderEnable; +extern nvnCommandBufferSetRenderEnableConditionalFunction + pfnc_nvnCommandBufferSetRenderEnableConditional; +extern nvnCommandBufferSetRenderTargetsFunction pfnc_nvnCommandBufferSetRenderTargets; +extern nvnCommandBufferDiscardColorFunction pfnc_nvnCommandBufferDiscardColor; +extern nvnCommandBufferDiscardDepthStencilFunction pfnc_nvnCommandBufferDiscardDepthStencil; +extern nvnCommandBufferDownsampleFunction pfnc_nvnCommandBufferDownsample; +extern nvnCommandBufferTiledDownsampleFunction pfnc_nvnCommandBufferTiledDownsample; +extern nvnCommandBufferDownsampleTextureViewFunction pfnc_nvnCommandBufferDownsampleTextureView; +extern nvnCommandBufferTiledDownsampleTextureViewFunction + pfnc_nvnCommandBufferTiledDownsampleTextureView; +extern nvnCommandBufferBarrierFunction pfnc_nvnCommandBufferBarrier; +extern nvnCommandBufferWaitSyncFunction pfnc_nvnCommandBufferWaitSync; +extern nvnCommandBufferFenceSyncFunction pfnc_nvnCommandBufferFenceSync; +extern nvnCommandBufferSetTexturePoolFunction pfnc_nvnCommandBufferSetTexturePool; +extern nvnCommandBufferSetSamplerPoolFunction pfnc_nvnCommandBufferSetSamplerPool; +extern nvnCommandBufferSetShaderScratchMemoryFunction pfnc_nvnCommandBufferSetShaderScratchMemory; +extern nvnCommandBufferSaveZCullDataFunction pfnc_nvnCommandBufferSaveZCullData; +extern nvnCommandBufferRestoreZCullDataFunction pfnc_nvnCommandBufferRestoreZCullData; +extern nvnCommandBufferSetCopyRowStrideFunction pfnc_nvnCommandBufferSetCopyRowStride; +extern nvnCommandBufferSetCopyImageStrideFunction pfnc_nvnCommandBufferSetCopyImageStride; +extern nvnCommandBufferGetCopyRowStrideFunction pfnc_nvnCommandBufferGetCopyRowStride; +extern nvnCommandBufferGetCopyImageStrideFunction pfnc_nvnCommandBufferGetCopyImageStride; +extern nvnCommandBufferDrawTextureFunction pfnc_nvnCommandBufferDrawTexture; +extern nvnProgramSetSubroutineLinkageFunction pfnc_nvnProgramSetSubroutineLinkage; +extern nvnCommandBufferSetProgramSubroutinesFunction pfnc_nvnCommandBufferSetProgramSubroutines; +extern nvnCommandBufferBindCoverageModulationTableFunction + pfnc_nvnCommandBufferBindCoverageModulationTable; +extern nvnCommandBufferResolveDepthBufferFunction pfnc_nvnCommandBufferResolveDepthBuffer; +extern nvnCommandBufferPushDebugGroupStaticFunction pfnc_nvnCommandBufferPushDebugGroupStatic; +extern nvnCommandBufferPushDebugGroupDynamicFunction pfnc_nvnCommandBufferPushDebugGroupDynamic; +extern nvnCommandBufferPushDebugGroupFunction pfnc_nvnCommandBufferPushDebugGroup; +extern nvnCommandBufferPopDebugGroupFunction pfnc_nvnCommandBufferPopDebugGroup; +extern nvnCommandBufferPopDebugGroupIdFunction pfnc_nvnCommandBufferPopDebugGroupId; +extern nvnCommandBufferInsertDebugMarkerStaticFunction pfnc_nvnCommandBufferInsertDebugMarkerStatic; +extern nvnCommandBufferInsertDebugMarkerDynamicFunction + pfnc_nvnCommandBufferInsertDebugMarkerDynamic; +extern nvnCommandBufferInsertDebugMarkerFunction pfnc_nvnCommandBufferInsertDebugMarker; +extern nvnCommandBufferGetMemoryCallbackFunction pfnc_nvnCommandBufferGetMemoryCallback; +extern nvnCommandBufferGetMemoryCallbackDataFunction pfnc_nvnCommandBufferGetMemoryCallbackData; +extern nvnCommandBufferIsRecordingFunction pfnc_nvnCommandBufferIsRecording; +extern nvnSyncInitializeFunction pfnc_nvnSyncInitialize; +extern nvnSyncFinalizeFunction pfnc_nvnSyncFinalize; +extern nvnSyncSetDebugLabelFunction pfnc_nvnSyncSetDebugLabel; +extern nvnQueueFenceSyncFunction pfnc_nvnQueueFenceSync; +extern nvnSyncWaitFunction pfnc_nvnSyncWait; +extern nvnQueueWaitSyncFunction pfnc_nvnQueueWaitSync; +extern nvnEventBuilderSetDefaultsFunction pfnc_nvnEventBuilderSetDefaults; +extern nvnEventBuilderSetStorageFunction pfnc_nvnEventBuilderSetStorage; +extern nvnEventInitializeFunction pfnc_nvnEventInitialize; +extern nvnEventFinalizeFunction pfnc_nvnEventFinalize; +extern nvnEventGetValueFunction pfnc_nvnEventGetValue; +extern nvnEventSignalFunction pfnc_nvnEventSignal; +extern nvnCommandBufferWaitEventFunction pfnc_nvnCommandBufferWaitEvent; +extern nvnCommandBufferSignalEventFunction pfnc_nvnCommandBufferSignalEvent; + +// Function mappings +#define nvnDeviceBuilderSetDefaults pfnc_nvnDeviceBuilderSetDefaults +#define nvnDeviceBuilderSetFlags pfnc_nvnDeviceBuilderSetFlags +#define nvnDeviceInitialize pfnc_nvnDeviceInitialize +#define nvnDeviceFinalize pfnc_nvnDeviceFinalize +#define nvnDeviceSetDebugLabel pfnc_nvnDeviceSetDebugLabel +#define nvnDeviceGetProcAddress pfnc_nvnDeviceGetProcAddress +#define nvnDeviceGetInteger pfnc_nvnDeviceGetInteger +#define nvnDeviceGetCurrentTimestampInNanoseconds pfnc_nvnDeviceGetCurrentTimestampInNanoseconds +#define nvnDeviceSetIntermediateShaderCache pfnc_nvnDeviceSetIntermediateShaderCache +#define nvnDeviceGetTextureHandle pfnc_nvnDeviceGetTextureHandle +#define nvnDeviceGetTexelFetchHandle pfnc_nvnDeviceGetTexelFetchHandle +#define nvnDeviceGetImageHandle pfnc_nvnDeviceGetImageHandle +#define nvnDeviceInstallDebugCallback pfnc_nvnDeviceInstallDebugCallback +#define nvnDeviceGenerateDebugDomainId pfnc_nvnDeviceGenerateDebugDomainId +#define nvnDeviceSetWindowOriginMode pfnc_nvnDeviceSetWindowOriginMode +#define nvnDeviceSetDepthMode pfnc_nvnDeviceSetDepthMode +#define nvnDeviceRegisterFastClearColor pfnc_nvnDeviceRegisterFastClearColor +#define nvnDeviceRegisterFastClearColori pfnc_nvnDeviceRegisterFastClearColori +#define nvnDeviceRegisterFastClearColorui pfnc_nvnDeviceRegisterFastClearColorui +#define nvnDeviceRegisterFastClearDepth pfnc_nvnDeviceRegisterFastClearDepth +#define nvnDeviceGetWindowOriginMode pfnc_nvnDeviceGetWindowOriginMode +#define nvnDeviceGetDepthMode pfnc_nvnDeviceGetDepthMode +#define nvnDeviceGetTimestampInNanoseconds pfnc_nvnDeviceGetTimestampInNanoseconds +#define nvnDeviceApplyDeferredFinalizes pfnc_nvnDeviceApplyDeferredFinalizes +#define nvnDeviceFinalizeCommandHandle pfnc_nvnDeviceFinalizeCommandHandle +#define nvnDeviceWalkDebugDatabase pfnc_nvnDeviceWalkDebugDatabase +#define nvnDeviceGetSeparateTextureHandle pfnc_nvnDeviceGetSeparateTextureHandle +#define nvnDeviceGetSeparateSamplerHandle pfnc_nvnDeviceGetSeparateSamplerHandle +#define nvnDeviceIsExternalDebuggerAttached pfnc_nvnDeviceIsExternalDebuggerAttached +#define nvnQueueGetError pfnc_nvnQueueGetError +#define nvnQueueGetTotalCommandMemoryUsed pfnc_nvnQueueGetTotalCommandMemoryUsed +#define nvnQueueGetTotalControlMemoryUsed pfnc_nvnQueueGetTotalControlMemoryUsed +#define nvnQueueGetTotalComputeMemoryUsed pfnc_nvnQueueGetTotalComputeMemoryUsed +#define nvnQueueResetMemoryUsageCounts pfnc_nvnQueueResetMemoryUsageCounts +#define nvnQueueBuilderSetDevice pfnc_nvnQueueBuilderSetDevice +#define nvnQueueBuilderSetDefaults pfnc_nvnQueueBuilderSetDefaults +#define nvnQueueBuilderSetFlags pfnc_nvnQueueBuilderSetFlags +#define nvnQueueBuilderSetCommandMemorySize pfnc_nvnQueueBuilderSetCommandMemorySize +#define nvnQueueBuilderSetComputeMemorySize pfnc_nvnQueueBuilderSetComputeMemorySize +#define nvnQueueBuilderSetControlMemorySize pfnc_nvnQueueBuilderSetControlMemorySize +#define nvnQueueBuilderGetQueueMemorySize pfnc_nvnQueueBuilderGetQueueMemorySize +#define nvnQueueBuilderSetQueueMemory pfnc_nvnQueueBuilderSetQueueMemory +#define nvnQueueBuilderSetCommandFlushThreshold pfnc_nvnQueueBuilderSetCommandFlushThreshold +#define nvnQueueInitialize pfnc_nvnQueueInitialize +#define nvnQueueFinalize pfnc_nvnQueueFinalize +#define nvnQueueSetDebugLabel pfnc_nvnQueueSetDebugLabel +#define nvnQueueSubmitCommands pfnc_nvnQueueSubmitCommands +#define nvnQueueFlush pfnc_nvnQueueFlush +#define nvnQueueFinish pfnc_nvnQueueFinish +#define nvnQueuePresentTexture pfnc_nvnQueuePresentTexture +#define nvnQueueAcquireTexture pfnc_nvnQueueAcquireTexture +#define nvnWindowBuilderSetDevice pfnc_nvnWindowBuilderSetDevice +#define nvnWindowBuilderSetDefaults pfnc_nvnWindowBuilderSetDefaults +#define nvnWindowBuilderSetNativeWindow pfnc_nvnWindowBuilderSetNativeWindow +#define nvnWindowBuilderSetTextures pfnc_nvnWindowBuilderSetTextures +#define nvnWindowBuilderSetPresentInterval pfnc_nvnWindowBuilderSetPresentInterval +#define nvnWindowBuilderGetNativeWindow pfnc_nvnWindowBuilderGetNativeWindow +#define nvnWindowBuilderGetPresentInterval pfnc_nvnWindowBuilderGetPresentInterval +#define nvnWindowInitialize pfnc_nvnWindowInitialize +#define nvnWindowFinalize pfnc_nvnWindowFinalize +#define nvnWindowSetDebugLabel pfnc_nvnWindowSetDebugLabel +#define nvnWindowAcquireTexture pfnc_nvnWindowAcquireTexture +#define nvnWindowGetNativeWindow pfnc_nvnWindowGetNativeWindow +#define nvnWindowGetPresentInterval pfnc_nvnWindowGetPresentInterval +#define nvnWindowSetPresentInterval pfnc_nvnWindowSetPresentInterval +#define nvnWindowSetCrop pfnc_nvnWindowSetCrop +#define nvnWindowGetCrop pfnc_nvnWindowGetCrop +#define nvnProgramInitialize pfnc_nvnProgramInitialize +#define nvnProgramFinalize pfnc_nvnProgramFinalize +#define nvnProgramSetDebugLabel pfnc_nvnProgramSetDebugLabel +#define nvnProgramSetShaders pfnc_nvnProgramSetShaders +#define nvnMemoryPoolBuilderSetDevice pfnc_nvnMemoryPoolBuilderSetDevice +#define nvnMemoryPoolBuilderSetDefaults pfnc_nvnMemoryPoolBuilderSetDefaults +#define nvnMemoryPoolBuilderSetStorage pfnc_nvnMemoryPoolBuilderSetStorage +#define nvnMemoryPoolBuilderSetFlags pfnc_nvnMemoryPoolBuilderSetFlags +#define nvnMemoryPoolBuilderGetMemory pfnc_nvnMemoryPoolBuilderGetMemory +#define nvnMemoryPoolBuilderGetSize pfnc_nvnMemoryPoolBuilderGetSize +#define nvnMemoryPoolBuilderGetFlags pfnc_nvnMemoryPoolBuilderGetFlags +#define nvnMemoryPoolInitialize pfnc_nvnMemoryPoolInitialize +#define nvnMemoryPoolSetDebugLabel pfnc_nvnMemoryPoolSetDebugLabel +#define nvnMemoryPoolFinalize pfnc_nvnMemoryPoolFinalize +#define nvnMemoryPoolMap pfnc_nvnMemoryPoolMap +#define nvnMemoryPoolFlushMappedRange pfnc_nvnMemoryPoolFlushMappedRange +#define nvnMemoryPoolInvalidateMappedRange pfnc_nvnMemoryPoolInvalidateMappedRange +#define nvnMemoryPoolGetBufferAddress pfnc_nvnMemoryPoolGetBufferAddress +#define nvnMemoryPoolMapVirtual pfnc_nvnMemoryPoolMapVirtual +#define nvnMemoryPoolGetSize pfnc_nvnMemoryPoolGetSize +#define nvnMemoryPoolGetFlags pfnc_nvnMemoryPoolGetFlags +#define nvnTexturePoolInitialize pfnc_nvnTexturePoolInitialize +#define nvnTexturePoolSetDebugLabel pfnc_nvnTexturePoolSetDebugLabel +#define nvnTexturePoolFinalize pfnc_nvnTexturePoolFinalize +#define nvnTexturePoolRegisterTexture pfnc_nvnTexturePoolRegisterTexture +#define nvnTexturePoolRegisterImage pfnc_nvnTexturePoolRegisterImage +#define nvnTexturePoolGetMemoryPool pfnc_nvnTexturePoolGetMemoryPool +#define nvnTexturePoolGetMemoryOffset pfnc_nvnTexturePoolGetMemoryOffset +#define nvnTexturePoolGetSize pfnc_nvnTexturePoolGetSize +#define nvnSamplerPoolInitialize pfnc_nvnSamplerPoolInitialize +#define nvnSamplerPoolSetDebugLabel pfnc_nvnSamplerPoolSetDebugLabel +#define nvnSamplerPoolFinalize pfnc_nvnSamplerPoolFinalize +#define nvnSamplerPoolRegisterSampler pfnc_nvnSamplerPoolRegisterSampler +#define nvnSamplerPoolRegisterSamplerBuilder pfnc_nvnSamplerPoolRegisterSamplerBuilder +#define nvnSamplerPoolGetMemoryPool pfnc_nvnSamplerPoolGetMemoryPool +#define nvnSamplerPoolGetMemoryOffset pfnc_nvnSamplerPoolGetMemoryOffset +#define nvnSamplerPoolGetSize pfnc_nvnSamplerPoolGetSize +#define nvnBufferBuilderSetDevice pfnc_nvnBufferBuilderSetDevice +#define nvnBufferBuilderSetDefaults pfnc_nvnBufferBuilderSetDefaults +#define nvnBufferBuilderSetStorage pfnc_nvnBufferBuilderSetStorage +#define nvnBufferBuilderGetMemoryPool pfnc_nvnBufferBuilderGetMemoryPool +#define nvnBufferBuilderGetMemoryOffset pfnc_nvnBufferBuilderGetMemoryOffset +#define nvnBufferBuilderGetSize pfnc_nvnBufferBuilderGetSize +#define nvnBufferInitialize pfnc_nvnBufferInitialize +#define nvnBufferSetDebugLabel pfnc_nvnBufferSetDebugLabel +#define nvnBufferFinalize pfnc_nvnBufferFinalize +#define nvnBufferMap pfnc_nvnBufferMap +#define nvnBufferGetAddress pfnc_nvnBufferGetAddress +#define nvnBufferFlushMappedRange pfnc_nvnBufferFlushMappedRange +#define nvnBufferInvalidateMappedRange pfnc_nvnBufferInvalidateMappedRange +#define nvnBufferGetMemoryPool pfnc_nvnBufferGetMemoryPool +#define nvnBufferGetMemoryOffset pfnc_nvnBufferGetMemoryOffset +#define nvnBufferGetSize pfnc_nvnBufferGetSize +#define nvnBufferGetDebugID pfnc_nvnBufferGetDebugID +#define nvnTextureBuilderSetDevice pfnc_nvnTextureBuilderSetDevice +#define nvnTextureBuilderSetDefaults pfnc_nvnTextureBuilderSetDefaults +#define nvnTextureBuilderSetFlags pfnc_nvnTextureBuilderSetFlags +#define nvnTextureBuilderSetTarget pfnc_nvnTextureBuilderSetTarget +#define nvnTextureBuilderSetWidth pfnc_nvnTextureBuilderSetWidth +#define nvnTextureBuilderSetHeight pfnc_nvnTextureBuilderSetHeight +#define nvnTextureBuilderSetDepth pfnc_nvnTextureBuilderSetDepth +#define nvnTextureBuilderSetSize1D pfnc_nvnTextureBuilderSetSize1D +#define nvnTextureBuilderSetSize2D pfnc_nvnTextureBuilderSetSize2D +#define nvnTextureBuilderSetSize3D pfnc_nvnTextureBuilderSetSize3D +#define nvnTextureBuilderSetLevels pfnc_nvnTextureBuilderSetLevels +#define nvnTextureBuilderSetFormat pfnc_nvnTextureBuilderSetFormat +#define nvnTextureBuilderSetSamples pfnc_nvnTextureBuilderSetSamples +#define nvnTextureBuilderSetSwizzle pfnc_nvnTextureBuilderSetSwizzle +#define nvnTextureBuilderSetDepthStencilMode pfnc_nvnTextureBuilderSetDepthStencilMode +#define nvnTextureBuilderGetStorageSize pfnc_nvnTextureBuilderGetStorageSize +#define nvnTextureBuilderGetStorageAlignment pfnc_nvnTextureBuilderGetStorageAlignment +#define nvnTextureBuilderSetStorage pfnc_nvnTextureBuilderSetStorage +#define nvnTextureBuilderSetPackagedTextureData pfnc_nvnTextureBuilderSetPackagedTextureData +#define nvnTextureBuilderSetPackagedTextureLayout pfnc_nvnTextureBuilderSetPackagedTextureLayout +#define nvnTextureBuilderSetStride pfnc_nvnTextureBuilderSetStride +#define nvnTextureBuilderSetGLTextureName pfnc_nvnTextureBuilderSetGLTextureName +#define nvnTextureBuilderGetStorageClass pfnc_nvnTextureBuilderGetStorageClass +#define nvnTextureBuilderGetFlags pfnc_nvnTextureBuilderGetFlags +#define nvnTextureBuilderGetTarget pfnc_nvnTextureBuilderGetTarget +#define nvnTextureBuilderGetWidth pfnc_nvnTextureBuilderGetWidth +#define nvnTextureBuilderGetHeight pfnc_nvnTextureBuilderGetHeight +#define nvnTextureBuilderGetDepth pfnc_nvnTextureBuilderGetDepth +#define nvnTextureBuilderGetLevels pfnc_nvnTextureBuilderGetLevels +#define nvnTextureBuilderGetFormat pfnc_nvnTextureBuilderGetFormat +#define nvnTextureBuilderGetSamples pfnc_nvnTextureBuilderGetSamples +#define nvnTextureBuilderGetSwizzle pfnc_nvnTextureBuilderGetSwizzle +#define nvnTextureBuilderGetDepthStencilMode pfnc_nvnTextureBuilderGetDepthStencilMode +#define nvnTextureBuilderGetPackagedTextureData pfnc_nvnTextureBuilderGetPackagedTextureData +#define nvnTextureBuilderGetStride pfnc_nvnTextureBuilderGetStride +#define nvnTextureBuilderGetSparseTileLayout pfnc_nvnTextureBuilderGetSparseTileLayout +#define nvnTextureBuilderGetGLTextureName pfnc_nvnTextureBuilderGetGLTextureName +#define nvnTextureBuilderGetZCullStorageSize pfnc_nvnTextureBuilderGetZCullStorageSize +#define nvnTextureBuilderGetMemoryPool pfnc_nvnTextureBuilderGetMemoryPool +#define nvnTextureBuilderGetMemoryOffset pfnc_nvnTextureBuilderGetMemoryOffset +#define nvnTextureViewSetDefaults pfnc_nvnTextureViewSetDefaults +#define nvnTextureViewSetLevels pfnc_nvnTextureViewSetLevels +#define nvnTextureViewSetLayers pfnc_nvnTextureViewSetLayers +#define nvnTextureViewSetFormat pfnc_nvnTextureViewSetFormat +#define nvnTextureViewSetSwizzle pfnc_nvnTextureViewSetSwizzle +#define nvnTextureViewSetDepthStencilMode pfnc_nvnTextureViewSetDepthStencilMode +#define nvnTextureViewSetTarget pfnc_nvnTextureViewSetTarget +#define nvnTextureViewGetLevels pfnc_nvnTextureViewGetLevels +#define nvnTextureViewGetLayers pfnc_nvnTextureViewGetLayers +#define nvnTextureViewGetFormat pfnc_nvnTextureViewGetFormat +#define nvnTextureViewGetSwizzle pfnc_nvnTextureViewGetSwizzle +#define nvnTextureViewGetDepthStencilMode pfnc_nvnTextureViewGetDepthStencilMode +#define nvnTextureViewGetTarget pfnc_nvnTextureViewGetTarget +#define nvnTextureViewCompare pfnc_nvnTextureViewCompare +#define nvnTextureInitialize pfnc_nvnTextureInitialize +#define nvnTextureGetZCullStorageSize pfnc_nvnTextureGetZCullStorageSize +#define nvnTextureFinalize pfnc_nvnTextureFinalize +#define nvnTextureSetDebugLabel pfnc_nvnTextureSetDebugLabel +#define nvnTextureGetStorageClass pfnc_nvnTextureGetStorageClass +#define nvnTextureGetViewOffset pfnc_nvnTextureGetViewOffset +#define nvnTextureGetFlags pfnc_nvnTextureGetFlags +#define nvnTextureGetTarget pfnc_nvnTextureGetTarget +#define nvnTextureGetWidth pfnc_nvnTextureGetWidth +#define nvnTextureGetHeight pfnc_nvnTextureGetHeight +#define nvnTextureGetDepth pfnc_nvnTextureGetDepth +#define nvnTextureGetLevels pfnc_nvnTextureGetLevels +#define nvnTextureGetFormat pfnc_nvnTextureGetFormat +#define nvnTextureGetSamples pfnc_nvnTextureGetSamples +#define nvnTextureGetSwizzle pfnc_nvnTextureGetSwizzle +#define nvnTextureGetDepthStencilMode pfnc_nvnTextureGetDepthStencilMode +#define nvnTextureGetStride pfnc_nvnTextureGetStride +#define nvnTextureGetTextureAddress pfnc_nvnTextureGetTextureAddress +#define nvnTextureGetSparseTileLayout pfnc_nvnTextureGetSparseTileLayout +#define nvnTextureWriteTexels pfnc_nvnTextureWriteTexels +#define nvnTextureWriteTexelsStrided pfnc_nvnTextureWriteTexelsStrided +#define nvnTextureReadTexels pfnc_nvnTextureReadTexels +#define nvnTextureReadTexelsStrided pfnc_nvnTextureReadTexelsStrided +#define nvnTextureFlushTexels pfnc_nvnTextureFlushTexels +#define nvnTextureInvalidateTexels pfnc_nvnTextureInvalidateTexels +#define nvnTextureGetMemoryPool pfnc_nvnTextureGetMemoryPool +#define nvnTextureGetMemoryOffset pfnc_nvnTextureGetMemoryOffset +#define nvnTextureGetStorageSize pfnc_nvnTextureGetStorageSize +#define nvnTextureCompare pfnc_nvnTextureCompare +#define nvnTextureGetDebugID pfnc_nvnTextureGetDebugID +#define nvnSamplerBuilderSetDevice pfnc_nvnSamplerBuilderSetDevice +#define nvnSamplerBuilderSetDefaults pfnc_nvnSamplerBuilderSetDefaults +#define nvnSamplerBuilderSetMinMagFilter pfnc_nvnSamplerBuilderSetMinMagFilter +#define nvnSamplerBuilderSetWrapMode pfnc_nvnSamplerBuilderSetWrapMode +#define nvnSamplerBuilderSetLodClamp pfnc_nvnSamplerBuilderSetLodClamp +#define nvnSamplerBuilderSetLodBias pfnc_nvnSamplerBuilderSetLodBias +#define nvnSamplerBuilderSetCompare pfnc_nvnSamplerBuilderSetCompare +#define nvnSamplerBuilderSetBorderColor pfnc_nvnSamplerBuilderSetBorderColor +#define nvnSamplerBuilderSetBorderColori pfnc_nvnSamplerBuilderSetBorderColori +#define nvnSamplerBuilderSetBorderColorui pfnc_nvnSamplerBuilderSetBorderColorui +#define nvnSamplerBuilderSetMaxAnisotropy pfnc_nvnSamplerBuilderSetMaxAnisotropy +#define nvnSamplerBuilderSetReductionFilter pfnc_nvnSamplerBuilderSetReductionFilter +#define nvnSamplerBuilderSetLodSnap pfnc_nvnSamplerBuilderSetLodSnap +#define nvnSamplerBuilderGetMinMagFilter pfnc_nvnSamplerBuilderGetMinMagFilter +#define nvnSamplerBuilderGetWrapMode pfnc_nvnSamplerBuilderGetWrapMode +#define nvnSamplerBuilderGetLodClamp pfnc_nvnSamplerBuilderGetLodClamp +#define nvnSamplerBuilderGetLodBias pfnc_nvnSamplerBuilderGetLodBias +#define nvnSamplerBuilderGetCompare pfnc_nvnSamplerBuilderGetCompare +#define nvnSamplerBuilderGetBorderColor pfnc_nvnSamplerBuilderGetBorderColor +#define nvnSamplerBuilderGetBorderColori pfnc_nvnSamplerBuilderGetBorderColori +#define nvnSamplerBuilderGetBorderColorui pfnc_nvnSamplerBuilderGetBorderColorui +#define nvnSamplerBuilderGetMaxAnisotropy pfnc_nvnSamplerBuilderGetMaxAnisotropy +#define nvnSamplerBuilderGetReductionFilter pfnc_nvnSamplerBuilderGetReductionFilter +#define nvnSamplerBuilderGetLodSnap pfnc_nvnSamplerBuilderGetLodSnap +#define nvnSamplerInitialize pfnc_nvnSamplerInitialize +#define nvnSamplerFinalize pfnc_nvnSamplerFinalize +#define nvnSamplerSetDebugLabel pfnc_nvnSamplerSetDebugLabel +#define nvnSamplerGetMinMagFilter pfnc_nvnSamplerGetMinMagFilter +#define nvnSamplerGetWrapMode pfnc_nvnSamplerGetWrapMode +#define nvnSamplerGetLodClamp pfnc_nvnSamplerGetLodClamp +#define nvnSamplerGetLodBias pfnc_nvnSamplerGetLodBias +#define nvnSamplerGetCompare pfnc_nvnSamplerGetCompare +#define nvnSamplerGetBorderColor pfnc_nvnSamplerGetBorderColor +#define nvnSamplerGetBorderColori pfnc_nvnSamplerGetBorderColori +#define nvnSamplerGetBorderColorui pfnc_nvnSamplerGetBorderColorui +#define nvnSamplerGetMaxAnisotropy pfnc_nvnSamplerGetMaxAnisotropy +#define nvnSamplerGetReductionFilter pfnc_nvnSamplerGetReductionFilter +#define nvnSamplerCompare pfnc_nvnSamplerCompare +#define nvnSamplerGetDebugID pfnc_nvnSamplerGetDebugID +#define nvnBlendStateSetDefaults pfnc_nvnBlendStateSetDefaults +#define nvnBlendStateSetBlendTarget pfnc_nvnBlendStateSetBlendTarget +#define nvnBlendStateSetBlendFunc pfnc_nvnBlendStateSetBlendFunc +#define nvnBlendStateSetBlendEquation pfnc_nvnBlendStateSetBlendEquation +#define nvnBlendStateSetAdvancedMode pfnc_nvnBlendStateSetAdvancedMode +#define nvnBlendStateSetAdvancedOverlap pfnc_nvnBlendStateSetAdvancedOverlap +#define nvnBlendStateSetAdvancedPremultipliedSrc pfnc_nvnBlendStateSetAdvancedPremultipliedSrc +#define nvnBlendStateSetAdvancedNormalizedDst pfnc_nvnBlendStateSetAdvancedNormalizedDst +#define nvnBlendStateGetBlendTarget pfnc_nvnBlendStateGetBlendTarget +#define nvnBlendStateGetBlendFunc pfnc_nvnBlendStateGetBlendFunc +#define nvnBlendStateGetBlendEquation pfnc_nvnBlendStateGetBlendEquation +#define nvnBlendStateGetAdvancedMode pfnc_nvnBlendStateGetAdvancedMode +#define nvnBlendStateGetAdvancedOverlap pfnc_nvnBlendStateGetAdvancedOverlap +#define nvnBlendStateGetAdvancedPremultipliedSrc pfnc_nvnBlendStateGetAdvancedPremultipliedSrc +#define nvnBlendStateGetAdvancedNormalizedDst pfnc_nvnBlendStateGetAdvancedNormalizedDst +#define nvnColorStateSetDefaults pfnc_nvnColorStateSetDefaults +#define nvnColorStateSetBlendEnable pfnc_nvnColorStateSetBlendEnable +#define nvnColorStateSetLogicOp pfnc_nvnColorStateSetLogicOp +#define nvnColorStateSetAlphaTest pfnc_nvnColorStateSetAlphaTest +#define nvnColorStateGetBlendEnable pfnc_nvnColorStateGetBlendEnable +#define nvnColorStateGetLogicOp pfnc_nvnColorStateGetLogicOp +#define nvnColorStateGetAlphaTest pfnc_nvnColorStateGetAlphaTest +#define nvnChannelMaskStateSetDefaults pfnc_nvnChannelMaskStateSetDefaults +#define nvnChannelMaskStateSetChannelMask pfnc_nvnChannelMaskStateSetChannelMask +#define nvnChannelMaskStateGetChannelMask pfnc_nvnChannelMaskStateGetChannelMask +#define nvnMultisampleStateSetDefaults pfnc_nvnMultisampleStateSetDefaults +#define nvnMultisampleStateSetMultisampleEnable pfnc_nvnMultisampleStateSetMultisampleEnable +#define nvnMultisampleStateSetSamples pfnc_nvnMultisampleStateSetSamples +#define nvnMultisampleStateSetAlphaToCoverageEnable pfnc_nvnMultisampleStateSetAlphaToCoverageEnable +#define nvnMultisampleStateSetAlphaToCoverageDither pfnc_nvnMultisampleStateSetAlphaToCoverageDither +#define nvnMultisampleStateGetMultisampleEnable pfnc_nvnMultisampleStateGetMultisampleEnable +#define nvnMultisampleStateGetSamples pfnc_nvnMultisampleStateGetSamples +#define nvnMultisampleStateGetAlphaToCoverageEnable pfnc_nvnMultisampleStateGetAlphaToCoverageEnable +#define nvnMultisampleStateGetAlphaToCoverageDither pfnc_nvnMultisampleStateGetAlphaToCoverageDither +#define nvnMultisampleStateSetRasterSamples pfnc_nvnMultisampleStateSetRasterSamples +#define nvnMultisampleStateGetRasterSamples pfnc_nvnMultisampleStateGetRasterSamples +#define nvnMultisampleStateSetCoverageModulationMode \ + pfnc_nvnMultisampleStateSetCoverageModulationMode +#define nvnMultisampleStateGetCoverageModulationMode \ + pfnc_nvnMultisampleStateGetCoverageModulationMode +#define nvnMultisampleStateSetCoverageToColorEnable pfnc_nvnMultisampleStateSetCoverageToColorEnable +#define nvnMultisampleStateGetCoverageToColorEnable pfnc_nvnMultisampleStateGetCoverageToColorEnable +#define nvnMultisampleStateSetCoverageToColorOutput pfnc_nvnMultisampleStateSetCoverageToColorOutput +#define nvnMultisampleStateGetCoverageToColorOutput pfnc_nvnMultisampleStateGetCoverageToColorOutput +#define nvnMultisampleStateSetSampleLocationsEnable pfnc_nvnMultisampleStateSetSampleLocationsEnable +#define nvnMultisampleStateGetSampleLocationsEnable pfnc_nvnMultisampleStateGetSampleLocationsEnable +#define nvnMultisampleStateGetSampleLocationsGrid pfnc_nvnMultisampleStateGetSampleLocationsGrid +#define nvnMultisampleStateSetSampleLocationsGridEnable \ + pfnc_nvnMultisampleStateSetSampleLocationsGridEnable +#define nvnMultisampleStateGetSampleLocationsGridEnable \ + pfnc_nvnMultisampleStateGetSampleLocationsGridEnable +#define nvnMultisampleStateSetSampleLocations pfnc_nvnMultisampleStateSetSampleLocations +#define nvnPolygonStateSetDefaults pfnc_nvnPolygonStateSetDefaults +#define nvnPolygonStateSetCullFace pfnc_nvnPolygonStateSetCullFace +#define nvnPolygonStateSetFrontFace pfnc_nvnPolygonStateSetFrontFace +#define nvnPolygonStateSetPolygonMode pfnc_nvnPolygonStateSetPolygonMode +#define nvnPolygonStateSetPolygonOffsetEnables pfnc_nvnPolygonStateSetPolygonOffsetEnables +#define nvnPolygonStateGetCullFace pfnc_nvnPolygonStateGetCullFace +#define nvnPolygonStateGetFrontFace pfnc_nvnPolygonStateGetFrontFace +#define nvnPolygonStateGetPolygonMode pfnc_nvnPolygonStateGetPolygonMode +#define nvnPolygonStateGetPolygonOffsetEnables pfnc_nvnPolygonStateGetPolygonOffsetEnables +#define nvnDepthStencilStateSetDefaults pfnc_nvnDepthStencilStateSetDefaults +#define nvnDepthStencilStateSetDepthTestEnable pfnc_nvnDepthStencilStateSetDepthTestEnable +#define nvnDepthStencilStateSetDepthWriteEnable pfnc_nvnDepthStencilStateSetDepthWriteEnable +#define nvnDepthStencilStateSetDepthFunc pfnc_nvnDepthStencilStateSetDepthFunc +#define nvnDepthStencilStateSetStencilTestEnable pfnc_nvnDepthStencilStateSetStencilTestEnable +#define nvnDepthStencilStateSetStencilFunc pfnc_nvnDepthStencilStateSetStencilFunc +#define nvnDepthStencilStateSetStencilOp pfnc_nvnDepthStencilStateSetStencilOp +#define nvnDepthStencilStateGetDepthTestEnable pfnc_nvnDepthStencilStateGetDepthTestEnable +#define nvnDepthStencilStateGetDepthWriteEnable pfnc_nvnDepthStencilStateGetDepthWriteEnable +#define nvnDepthStencilStateGetDepthFunc pfnc_nvnDepthStencilStateGetDepthFunc +#define nvnDepthStencilStateGetStencilTestEnable pfnc_nvnDepthStencilStateGetStencilTestEnable +#define nvnDepthStencilStateGetStencilFunc pfnc_nvnDepthStencilStateGetStencilFunc +#define nvnDepthStencilStateGetStencilOp pfnc_nvnDepthStencilStateGetStencilOp +#define nvnVertexAttribStateSetDefaults pfnc_nvnVertexAttribStateSetDefaults +#define nvnVertexAttribStateSetFormat pfnc_nvnVertexAttribStateSetFormat +#define nvnVertexAttribStateSetStreamIndex pfnc_nvnVertexAttribStateSetStreamIndex +#define nvnVertexAttribStateGetFormat pfnc_nvnVertexAttribStateGetFormat +#define nvnVertexAttribStateGetStreamIndex pfnc_nvnVertexAttribStateGetStreamIndex +#define nvnVertexStreamStateSetDefaults pfnc_nvnVertexStreamStateSetDefaults +#define nvnVertexStreamStateSetStride pfnc_nvnVertexStreamStateSetStride +#define nvnVertexStreamStateSetDivisor pfnc_nvnVertexStreamStateSetDivisor +#define nvnVertexStreamStateGetStride pfnc_nvnVertexStreamStateGetStride +#define nvnVertexStreamStateGetDivisor pfnc_nvnVertexStreamStateGetDivisor +#define nvnCommandBufferInitialize pfnc_nvnCommandBufferInitialize +#define nvnCommandBufferFinalize pfnc_nvnCommandBufferFinalize +#define nvnCommandBufferSetDebugLabel pfnc_nvnCommandBufferSetDebugLabel +#define nvnCommandBufferSetMemoryCallback pfnc_nvnCommandBufferSetMemoryCallback +#define nvnCommandBufferSetMemoryCallbackData pfnc_nvnCommandBufferSetMemoryCallbackData +#define nvnCommandBufferAddCommandMemory pfnc_nvnCommandBufferAddCommandMemory +#define nvnCommandBufferAddControlMemory pfnc_nvnCommandBufferAddControlMemory +#define nvnCommandBufferGetCommandMemorySize pfnc_nvnCommandBufferGetCommandMemorySize +#define nvnCommandBufferGetCommandMemoryUsed pfnc_nvnCommandBufferGetCommandMemoryUsed +#define nvnCommandBufferGetCommandMemoryFree pfnc_nvnCommandBufferGetCommandMemoryFree +#define nvnCommandBufferGetControlMemorySize pfnc_nvnCommandBufferGetControlMemorySize +#define nvnCommandBufferGetControlMemoryUsed pfnc_nvnCommandBufferGetControlMemoryUsed +#define nvnCommandBufferGetControlMemoryFree pfnc_nvnCommandBufferGetControlMemoryFree +#define nvnCommandBufferBeginRecording pfnc_nvnCommandBufferBeginRecording +#define nvnCommandBufferEndRecording pfnc_nvnCommandBufferEndRecording +#define nvnCommandBufferCallCommands pfnc_nvnCommandBufferCallCommands +#define nvnCommandBufferCopyCommands pfnc_nvnCommandBufferCopyCommands +#define nvnCommandBufferBindBlendState pfnc_nvnCommandBufferBindBlendState +#define nvnCommandBufferBindChannelMaskState pfnc_nvnCommandBufferBindChannelMaskState +#define nvnCommandBufferBindColorState pfnc_nvnCommandBufferBindColorState +#define nvnCommandBufferBindMultisampleState pfnc_nvnCommandBufferBindMultisampleState +#define nvnCommandBufferBindPolygonState pfnc_nvnCommandBufferBindPolygonState +#define nvnCommandBufferBindDepthStencilState pfnc_nvnCommandBufferBindDepthStencilState +#define nvnCommandBufferBindVertexAttribState pfnc_nvnCommandBufferBindVertexAttribState +#define nvnCommandBufferBindVertexStreamState pfnc_nvnCommandBufferBindVertexStreamState +#define nvnCommandBufferBindProgram pfnc_nvnCommandBufferBindProgram +#define nvnCommandBufferBindVertexBuffer pfnc_nvnCommandBufferBindVertexBuffer +#define nvnCommandBufferBindVertexBuffers pfnc_nvnCommandBufferBindVertexBuffers +#define nvnCommandBufferBindUniformBuffer pfnc_nvnCommandBufferBindUniformBuffer +#define nvnCommandBufferBindUniformBuffers pfnc_nvnCommandBufferBindUniformBuffers +#define nvnCommandBufferBindTransformFeedbackBuffer pfnc_nvnCommandBufferBindTransformFeedbackBuffer +#define nvnCommandBufferBindTransformFeedbackBuffers \ + pfnc_nvnCommandBufferBindTransformFeedbackBuffers +#define nvnCommandBufferBindStorageBuffer pfnc_nvnCommandBufferBindStorageBuffer +#define nvnCommandBufferBindStorageBuffers pfnc_nvnCommandBufferBindStorageBuffers +#define nvnCommandBufferBindTexture pfnc_nvnCommandBufferBindTexture +#define nvnCommandBufferBindTextures pfnc_nvnCommandBufferBindTextures +#define nvnCommandBufferBindImage pfnc_nvnCommandBufferBindImage +#define nvnCommandBufferBindImages pfnc_nvnCommandBufferBindImages +#define nvnCommandBufferSetPatchSize pfnc_nvnCommandBufferSetPatchSize +#define nvnCommandBufferSetInnerTessellationLevels pfnc_nvnCommandBufferSetInnerTessellationLevels +#define nvnCommandBufferSetOuterTessellationLevels pfnc_nvnCommandBufferSetOuterTessellationLevels +#define nvnCommandBufferSetPrimitiveRestart pfnc_nvnCommandBufferSetPrimitiveRestart +#define nvnCommandBufferBeginTransformFeedback pfnc_nvnCommandBufferBeginTransformFeedback +#define nvnCommandBufferEndTransformFeedback pfnc_nvnCommandBufferEndTransformFeedback +#define nvnCommandBufferPauseTransformFeedback pfnc_nvnCommandBufferPauseTransformFeedback +#define nvnCommandBufferResumeTransformFeedback pfnc_nvnCommandBufferResumeTransformFeedback +#define nvnCommandBufferDrawTransformFeedback pfnc_nvnCommandBufferDrawTransformFeedback +#define nvnCommandBufferDrawArrays pfnc_nvnCommandBufferDrawArrays +#define nvnCommandBufferDrawElements pfnc_nvnCommandBufferDrawElements +#define nvnCommandBufferDrawElementsBaseVertex pfnc_nvnCommandBufferDrawElementsBaseVertex +#define nvnCommandBufferDrawArraysInstanced pfnc_nvnCommandBufferDrawArraysInstanced +#define nvnCommandBufferDrawElementsInstanced pfnc_nvnCommandBufferDrawElementsInstanced +#define nvnCommandBufferDrawArraysIndirect pfnc_nvnCommandBufferDrawArraysIndirect +#define nvnCommandBufferDrawElementsIndirect pfnc_nvnCommandBufferDrawElementsIndirect +#define nvnCommandBufferMultiDrawArraysIndirectCount \ + pfnc_nvnCommandBufferMultiDrawArraysIndirectCount +#define nvnCommandBufferMultiDrawElementsIndirectCount \ + pfnc_nvnCommandBufferMultiDrawElementsIndirectCount +#define nvnCommandBufferClearColor pfnc_nvnCommandBufferClearColor +#define nvnCommandBufferClearColori pfnc_nvnCommandBufferClearColori +#define nvnCommandBufferClearColorui pfnc_nvnCommandBufferClearColorui +#define nvnCommandBufferClearDepthStencil pfnc_nvnCommandBufferClearDepthStencil +#define nvnCommandBufferDispatchCompute pfnc_nvnCommandBufferDispatchCompute +#define nvnCommandBufferDispatchComputeIndirect pfnc_nvnCommandBufferDispatchComputeIndirect +#define nvnCommandBufferSetViewport pfnc_nvnCommandBufferSetViewport +#define nvnCommandBufferSetViewports pfnc_nvnCommandBufferSetViewports +#define nvnCommandBufferSetViewportSwizzles pfnc_nvnCommandBufferSetViewportSwizzles +#define nvnCommandBufferSetScissor pfnc_nvnCommandBufferSetScissor +#define nvnCommandBufferSetScissors pfnc_nvnCommandBufferSetScissors +#define nvnCommandBufferSetDepthRange pfnc_nvnCommandBufferSetDepthRange +#define nvnCommandBufferSetDepthBounds pfnc_nvnCommandBufferSetDepthBounds +#define nvnCommandBufferSetDepthRanges pfnc_nvnCommandBufferSetDepthRanges +#define nvnCommandBufferSetTiledCacheAction pfnc_nvnCommandBufferSetTiledCacheAction +#define nvnCommandBufferSetTiledCacheTileSize pfnc_nvnCommandBufferSetTiledCacheTileSize +#define nvnCommandBufferBindSeparateTexture pfnc_nvnCommandBufferBindSeparateTexture +#define nvnCommandBufferBindSeparateSampler pfnc_nvnCommandBufferBindSeparateSampler +#define nvnCommandBufferBindSeparateTextures pfnc_nvnCommandBufferBindSeparateTextures +#define nvnCommandBufferBindSeparateSamplers pfnc_nvnCommandBufferBindSeparateSamplers +#define nvnCommandBufferSetStencilValueMask pfnc_nvnCommandBufferSetStencilValueMask +#define nvnCommandBufferSetStencilMask pfnc_nvnCommandBufferSetStencilMask +#define nvnCommandBufferSetStencilRef pfnc_nvnCommandBufferSetStencilRef +#define nvnCommandBufferSetBlendColor pfnc_nvnCommandBufferSetBlendColor +#define nvnCommandBufferSetPointSize pfnc_nvnCommandBufferSetPointSize +#define nvnCommandBufferSetLineWidth pfnc_nvnCommandBufferSetLineWidth +#define nvnCommandBufferSetPolygonOffsetClamp pfnc_nvnCommandBufferSetPolygonOffsetClamp +#define nvnCommandBufferSetAlphaRef pfnc_nvnCommandBufferSetAlphaRef +#define nvnCommandBufferSetSampleMask pfnc_nvnCommandBufferSetSampleMask +#define nvnCommandBufferSetRasterizerDiscard pfnc_nvnCommandBufferSetRasterizerDiscard +#define nvnCommandBufferSetDepthClamp pfnc_nvnCommandBufferSetDepthClamp +#define nvnCommandBufferSetConservativeRasterEnable pfnc_nvnCommandBufferSetConservativeRasterEnable +#define nvnCommandBufferSetConservativeRasterDilate pfnc_nvnCommandBufferSetConservativeRasterDilate +#define nvnCommandBufferSetSubpixelPrecisionBias pfnc_nvnCommandBufferSetSubpixelPrecisionBias +#define nvnCommandBufferCopyBufferToTexture pfnc_nvnCommandBufferCopyBufferToTexture +#define nvnCommandBufferCopyTextureToBuffer pfnc_nvnCommandBufferCopyTextureToBuffer +#define nvnCommandBufferCopyTextureToTexture pfnc_nvnCommandBufferCopyTextureToTexture +#define nvnCommandBufferCopyBufferToBuffer pfnc_nvnCommandBufferCopyBufferToBuffer +#define nvnCommandBufferClearBuffer pfnc_nvnCommandBufferClearBuffer +#define nvnCommandBufferClearTexture pfnc_nvnCommandBufferClearTexture +#define nvnCommandBufferClearTexturei pfnc_nvnCommandBufferClearTexturei +#define nvnCommandBufferClearTextureui pfnc_nvnCommandBufferClearTextureui +#define nvnCommandBufferUpdateUniformBuffer pfnc_nvnCommandBufferUpdateUniformBuffer +#define nvnCommandBufferReportCounter pfnc_nvnCommandBufferReportCounter +#define nvnCommandBufferResetCounter pfnc_nvnCommandBufferResetCounter +#define nvnCommandBufferReportValue pfnc_nvnCommandBufferReportValue +#define nvnCommandBufferSetRenderEnable pfnc_nvnCommandBufferSetRenderEnable +#define nvnCommandBufferSetRenderEnableConditional pfnc_nvnCommandBufferSetRenderEnableConditional +#define nvnCommandBufferSetRenderTargets pfnc_nvnCommandBufferSetRenderTargets +#define nvnCommandBufferDiscardColor pfnc_nvnCommandBufferDiscardColor +#define nvnCommandBufferDiscardDepthStencil pfnc_nvnCommandBufferDiscardDepthStencil +#define nvnCommandBufferDownsample pfnc_nvnCommandBufferDownsample +#define nvnCommandBufferTiledDownsample pfnc_nvnCommandBufferTiledDownsample +#define nvnCommandBufferDownsampleTextureView pfnc_nvnCommandBufferDownsampleTextureView +#define nvnCommandBufferTiledDownsampleTextureView pfnc_nvnCommandBufferTiledDownsampleTextureView +#define nvnCommandBufferBarrier pfnc_nvnCommandBufferBarrier +#define nvnCommandBufferWaitSync pfnc_nvnCommandBufferWaitSync +#define nvnCommandBufferFenceSync pfnc_nvnCommandBufferFenceSync +#define nvnCommandBufferSetTexturePool pfnc_nvnCommandBufferSetTexturePool +#define nvnCommandBufferSetSamplerPool pfnc_nvnCommandBufferSetSamplerPool +#define nvnCommandBufferSetShaderScratchMemory pfnc_nvnCommandBufferSetShaderScratchMemory +#define nvnCommandBufferSaveZCullData pfnc_nvnCommandBufferSaveZCullData +#define nvnCommandBufferRestoreZCullData pfnc_nvnCommandBufferRestoreZCullData +#define nvnCommandBufferSetCopyRowStride pfnc_nvnCommandBufferSetCopyRowStride +#define nvnCommandBufferSetCopyImageStride pfnc_nvnCommandBufferSetCopyImageStride +#define nvnCommandBufferGetCopyRowStride pfnc_nvnCommandBufferGetCopyRowStride +#define nvnCommandBufferGetCopyImageStride pfnc_nvnCommandBufferGetCopyImageStride +#define nvnCommandBufferDrawTexture pfnc_nvnCommandBufferDrawTexture +#define nvnProgramSetSubroutineLinkage pfnc_nvnProgramSetSubroutineLinkage +#define nvnCommandBufferSetProgramSubroutines pfnc_nvnCommandBufferSetProgramSubroutines +#define nvnCommandBufferBindCoverageModulationTable pfnc_nvnCommandBufferBindCoverageModulationTable +#define nvnCommandBufferResolveDepthBuffer pfnc_nvnCommandBufferResolveDepthBuffer +#define nvnCommandBufferPushDebugGroupStatic pfnc_nvnCommandBufferPushDebugGroupStatic +#define nvnCommandBufferPushDebugGroupDynamic pfnc_nvnCommandBufferPushDebugGroupDynamic +#define nvnCommandBufferPushDebugGroup pfnc_nvnCommandBufferPushDebugGroup +#define nvnCommandBufferPopDebugGroup pfnc_nvnCommandBufferPopDebugGroup +#define nvnCommandBufferPopDebugGroupId pfnc_nvnCommandBufferPopDebugGroupId +#define nvnCommandBufferInsertDebugMarkerStatic pfnc_nvnCommandBufferInsertDebugMarkerStatic +#define nvnCommandBufferInsertDebugMarkerDynamic pfnc_nvnCommandBufferInsertDebugMarkerDynamic +#define nvnCommandBufferInsertDebugMarker pfnc_nvnCommandBufferInsertDebugMarker +#define nvnCommandBufferGetMemoryCallback pfnc_nvnCommandBufferGetMemoryCallback +#define nvnCommandBufferGetMemoryCallbackData pfnc_nvnCommandBufferGetMemoryCallbackData +#define nvnCommandBufferIsRecording pfnc_nvnCommandBufferIsRecording +#define nvnSyncInitialize pfnc_nvnSyncInitialize +#define nvnSyncFinalize pfnc_nvnSyncFinalize +#define nvnSyncSetDebugLabel pfnc_nvnSyncSetDebugLabel +#define nvnQueueFenceSync pfnc_nvnQueueFenceSync +#define nvnSyncWait pfnc_nvnSyncWait +#define nvnQueueWaitSync pfnc_nvnQueueWaitSync +#define nvnEventBuilderSetDefaults pfnc_nvnEventBuilderSetDefaults +#define nvnEventBuilderSetStorage pfnc_nvnEventBuilderSetStorage +#define nvnEventInitialize pfnc_nvnEventInitialize +#define nvnEventFinalize pfnc_nvnEventFinalize +#define nvnEventGetValue pfnc_nvnEventGetValue +#define nvnEventSignal pfnc_nvnEventSignal +#define nvnCommandBufferWaitEvent pfnc_nvnCommandBufferWaitEvent +#define nvnCommandBufferSignalEvent pfnc_nvnCommandBufferSignalEvent + +#ifdef __cplusplus +} +#endif diff --git a/lib/NintendoSDK/include/nvn/nvn_types.h b/lib/NintendoSDK/include/nvn/nvn_types.h new file mode 100644 index 00000000..c8cc8f65 --- /dev/null +++ b/lib/NintendoSDK/include/nvn/nvn_types.h @@ -0,0 +1,1074 @@ +/* + * Copyright (c) 2020 h1k421 + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +// NVN types reconstructed from Darksiders II DWARF information. +// NOTE: This only includes enums and structs used for NVN 53.105 but might contain more elements +// than expected (as Darksiders II uses a newer version of NVN). +// TODO: Include the extra information from the version used on Darksiders II for completeness. + +#pragma once + +#ifdef __cplusplus +extern "C" { +#endif + +#include +#include + +typedef uint64_t NVNtextureHandle; +typedef uint64_t NVNimageHandle; +typedef uint64_t NVNcommandHandle; +typedef uint64_t NVNbufferAddress; +typedef uint64_t NVNtextureAddress; +typedef int NVNdebugDomainId; +typedef int NVNstorageClass; +typedef void* NVNsubroutineLinkageMapPtr; +typedef void* NVNnativeWindow; + +typedef struct { + char details[0x3000]; +} NVNdevice; + +typedef struct { + char details[0x40]; +} NVNdeviceBuilder; + +typedef struct { + // TODO: reverse and define this as it looks like it's not an opaque type. + char dummy[1]; +} NVNtextureSparseTileLayout; + +typedef struct { + // TODO: reverse and define this as it looks like it's not an opaque type. + char dummy[1]; +} NVNdrawTextureRegion; + +typedef struct { + char details[0x18]; +} NVNmultisampleState; + +typedef struct { + char details[0x8]; +} NVNdepthStencilState; + +typedef struct { + char details[0x4]; +} NVNchannelMaskState; + +typedef struct { + char details[0x4]; +} NVNpolygonState; + +typedef struct { + NVNbufferAddress address; + uint64_t size; +} NVNbufferRange; + +typedef struct { + unsigned char details[4]; +} NVNcolorState; + +typedef struct { + uint64_t counter; + uint64_t timestamp; +} NVNcounterData; + +typedef struct { + uint64_t value; +} NVNseparateTextureHandle; + +typedef struct { + uint64_t value; +} NVNseparateSamplerHandle; + +typedef struct { + char details[0x2000]; +} NVNqueue; + +typedef struct { + // TODO: reverse and define this as it looks like it's not an opaque type. + char dummy[1]; +} NVNqueueErrorInfo; + +typedef struct { + char details[0x40]; +} NVNqueueBuilder; + +typedef struct { + char details[384]; +} NVNwindow; + +typedef struct { + char details[0xC0]; +} NVNtexture; + +typedef struct { + char details[0x28]; +} NVNtextureView; + +typedef struct { + char details[0xA0]; +} NVNcommandBuffer; + +typedef struct { + char details[0x40]; +} NVNsync; + +typedef struct { + int x; + int y; + int width; + int height; +} NVNrectangle; + +typedef struct { + char details[0xC0]; +} NVNprogram; + +typedef struct { + NVNbufferAddress data; + const void* control; +} NVNshaderData; + +typedef struct { + char details[0x100]; +} NVNmemoryPool; + +typedef struct { + char details[0x20]; +} NVNtexturePool; + +typedef struct { + char details[0x20]; +} NVNsamplerPool; + +typedef struct { + char details[0x8]; +} NVNblendState; + +typedef struct { + char details[0x4]; +} NVNvertexAttribState; + +typedef struct { + char details[0x4]; +} NVNvertexStreamState; + +typedef struct { + char details[0x40]; +} NVNmemoryPoolBuilder; + +typedef struct { + // TODO: reverse and define this as it looks like it's not an opaque type. + char dummy[1]; +} NVNmappingRequest; + +typedef struct { + char details[0x60]; +} NVNsamplerBuilder; + +typedef struct { + char details[0x30]; +} NVNsampler; + +typedef struct { + char details[0x40]; +} NVNbufferBuilder; + +typedef struct { + char details[0x30]; +} NVNbuffer; + +typedef struct { + char details[0x40]; +} NVNevent; + +typedef struct { + char details[0x20]; +} NVNeventBuilder; + +typedef struct { + int xoffset; + int yoffset; + int zoffset; + int width; + int height; + int depth; +} NVNcopyRegion; + +typedef struct { + char details[0x40]; +} NVNwindowBuilder; + +typedef struct { + char details[0x80]; +} NVNtextureBuilder; + +typedef struct { + unsigned char layout[8]; +} NVNpackagedTextureLayout; + +typedef enum { + NVN_DEVICE_INFO_API_MAJOR_VERSION = 0x0, + NVN_DEVICE_INFO_API_MINOR_VERSION = 0x1, + NVN_DEVICE_INFO_UNIFORM_BUFFER_BINDINGS_PER_STAGE = 0x2, + NVN_DEVICE_INFO_MAX_UNIFORM_BUFFER_SIZE = 0x3, + NVN_DEVICE_INFO_UNIFORM_BUFFER_ALIGNMENT = 0x4, + NVN_DEVICE_INFO_COLOR_BUFFER_BINDINGS = 0x5, + NVN_DEVICE_INFO_VERTEX_BUFFER_BINDINGS = 0x6, + NVN_DEVICE_INFO_TRANSFORM_FEEDBACK_BUFFER_BINDINGS = 0x7, + NVN_DEVICE_INFO_SHADER_STORAGE_BUFFER_BINDINGS_PER_STAGE = 0x8, + NVN_DEVICE_INFO_TEXTURE_BINDINGS_PER_STAGE = 0x9, + NVN_DEVICE_INFO_COUNTER_ALIGNMENT = 0xA, + NVN_DEVICE_INFO_TRANSFORM_FEEDBACK_BUFFER_ALIGNMENT = 0xB, + NVN_DEVICE_INFO_TRANSFORM_FEEDBACK_CONTROL_ALIGNMENT = 0xC, + NVN_DEVICE_INFO_INDIRECT_DRAW_ALIGNMENT = 0xD, + NVN_DEVICE_INFO_VERTEX_ATTRIBUTES = 0xE, + NVN_DEVICE_INFO_TEXTURE_DESCRIPTOR_SIZE = 0xF, + NVN_DEVICE_INFO_SAMPLER_DESCRIPTOR_SIZE = 0x10, + NVN_DEVICE_INFO_RESERVED_TEXTURE_DESCRIPTORS = 0x11, + NVN_DEVICE_INFO_RESERVED_SAMPLER_DESCRIPTORS = 0x12, + NVN_DEVICE_INFO_COMMAND_BUFFER_COMMAND_ALIGNMENT = 0x13, + NVN_DEVICE_INFO_COMMAND_BUFFER_CONTROL_ALIGNMENT = 0x14, + NVN_DEVICE_INFO_COMMAND_BUFFER_MIN_COMMAND_SIZE = 0x15, + NVN_DEVICE_INFO_COMMAND_BUFFER_MIN_CONTROL_SIZE = 0x16, + NVN_DEVICE_INFO_SHADER_SCRATCH_MEMORY_SCALE_FACTOR_MINIMUM = 0x17, + NVN_DEVICE_INFO_SHADER_SCRATCH_MEMORY_SCALE_FACTOR_RECOMMENDED = 0x18, + NVN_DEVICE_INFO_SHADER_SCRATCH_MEMORY_ALIGNMENT = 0x19, + NVN_DEVICE_INFO_SHADER_SCRATCH_MEMORY_GRANULARITY = 0x1A, + NVN_DEVICE_INFO_MAX_TEXTURE_ANISOTROPY = 0x1B, + NVN_DEVICE_INFO_MAX_COMPUTE_WORK_GROUP_SIZE_X = 0x1C, + NVN_DEVICE_INFO_MAX_COMPUTE_WORK_GROUP_SIZE_Y = 0x1D, + NVN_DEVICE_INFO_MAX_COMPUTE_WORK_GROUP_SIZE_Z = 0x1E, + NVN_DEVICE_INFO_MAX_COMPUTE_WORK_GROUP_SIZE_THREADS = 0x1F, + NVN_DEVICE_INFO_MAX_COMPUTE_DISPATCH_WORK_GROUPS_X = 0x20, + NVN_DEVICE_INFO_MAX_COMPUTE_DISPATCH_WORK_GROUPS_Y = 0x21, + NVN_DEVICE_INFO_MAX_COMPUTE_DISPATCH_WORK_GROUPS_Z = 0x22, + NVN_DEVICE_INFO_IMAGE_BINDINGS_PER_STAGE = 0x23, + NVN_DEVICE_INFO_MAX_TEXTURE_POOL_SIZE = 0x24, + NVN_DEVICE_INFO_MAX_SAMPLER_POOL_SIZE = 0x25, + NVN_DEVICE_INFO_MAX_VIEWPORTS = 0x26, + NVN_DEVICE_INFO_MEMPOOL_TEXTURE_OBJECT_PAGE_ALIGNMENT = 0x27, + NVN_DEVICE_INFO_SUPPORTS_MIN_MAX_FILTERING = 0x28, + NVN_DEVICE_INFO_SUPPORTS_STENCIL8_FORMAT = 0x29, + NVN_DEVICE_INFO_SUPPORTS_ASTC_FORMATS = 0x2A, + NVN_DEVICE_INFO_L2_SIZE = 0x2B, + NVN_DEVICE_INFO_MAX_TEXTURE_LEVELS = 0x2C, + NVN_DEVICE_INFO_MAX_TEXTURE_LAYERS = 0x2D, + NVN_DEVICE_INFO_GLSLC_MAX_SUPPORTED_GPU_CODE_MAJOR_VERSION = 0x2E, + NVN_DEVICE_INFO_GLSLC_MIN_SUPPORTED_GPU_CODE_MAJOR_VERSION = 0x2F, + NVN_DEVICE_INFO_GLSLC_MAX_SUPPORTED_GPU_CODE_MINOR_VERSION = 0x30, + NVN_DEVICE_INFO_GLSLC_MIN_SUPPORTED_GPU_CODE_MINOR_VERSION = 0x31, + NVN_DEVICE_INFO_SUPPORTS_CONSERVATIVE_RASTER = 0x32, + NVN_DEVICE_INFO_SUBPIXEL_BITS = 0x33, + NVN_DEVICE_INFO_MAX_SUBPIXEL_BIAS_BITS = 0x34, + NVN_DEVICE_INFO_INDIRECT_DISPATCH_ALIGNMENT = 0x35, + NVN_DEVICE_INFO_ZCULL_SAVE_RESTORE_ALIGNMENT = 0x36, + NVN_DEVICE_INFO_SHADER_SCRATCH_MEMORY_COMPUTE_SCALE_FACTOR_MINIMUM = 0x37, + NVN_DEVICE_INFO_LINEAR_TEXTURE_STRIDE_ALIGNMENT = 0x38, + NVN_DEVICE_INFO_LINEAR_RENDER_TARGET_STRIDE_ALIGNMENT = 0x39, + NVN_DEVICE_INFO_MEMORY_POOL_PAGE_SIZE = 0x3A, + NVN_DEVICE_INFO_SUPPORTS_ZERO_FROM_UNMAPPED_VIRTUAL_POOL_PAGES = 0x3B, + NVN_DEVICE_INFO_UNIFORM_BUFFER_UPDATE_ALIGNMENT = 0x3C, + NVN_DEVICE_INFO_MAX_TEXTURE_SIZE = 0x3D, + NVN_DEVICE_INFO_MAX_BUFFER_TEXTURE_SIZE = 0x3E, + NVN_DEVICE_INFO_MAX_3D_TEXTURE_SIZE = 0x3F, + NVN_DEVICE_INFO_MAX_CUBE_MAP_TEXTURE_SIZE = 0x40, + NVN_DEVICE_INFO_MAX_RECTANGLE_TEXTURE_SIZE = 0x41, + NVN_DEVICE_INFO_SUPPORTS_PASSTHROUGH_GEOMETRY_SHADERS = 0x42, + NVN_DEVICE_INFO_SUPPORTS_VIEWPORT_SWIZZLE = 0x43, + NVN_DEVICE_INFO_SUPPORTS_SPARSE_TILED_PACKAGED_TEXTURES = 0x44, + NVN_DEVICE_INFO_SUPPORTS_ADVANCED_BLEND_MODES = 0x45, + NVN_DEVICE_INFO_MAX_PRESENT_INTERVAL = 0x46, + NVN_DEVICE_INFO_SUPPORTS_DRAW_TEXTURE = 0x47, + NVN_DEVICE_INFO_SUPPORTS_TARGET_INDEPENDENT_RASTERIZATION = 0x48, + NVN_DEVICE_INFO_SUPPORTS_FRAGMENT_COVERAGE_TO_COLOR = 0x49, + NVN_DEVICE_INFO_SUPPORTS_POST_DEPTH_COVERAGE = 0x4A, + NVN_DEVICE_INFO_SUPPORTS_IMAGES_USING_TEXTURE_HANDLES = 0x4B, + NVN_DEVICE_INFO_SUPPORTS_SAMPLE_LOCATIONS = 0x4C, + NVN_DEVICE_INFO_MAX_SAMPLE_LOCATION_TABLE_ENTRIES = 0x4D, + NVN_DEVICE_INFO_SHADER_CODE_MEMORY_POOL_PADDING_SIZE = 0x4E, + NVN_DEVICE_INFO_MAX_PATCH_SIZE = 0x4F, + NVN_DEVICE_INFO_QUEUE_COMMAND_MEMORY_GRANULARITY = 0x50, + NVN_DEVICE_INFO_QUEUE_COMMAND_MEMORY_MIN_SIZE = 0x51, + NVN_DEVICE_INFO_QUEUE_COMMAND_MEMORY_DEFAULT_SIZE = 0x52, + NVN_DEVICE_INFO_QUEUE_COMPUTE_MEMORY_GRANULARITY = 0x53, + NVN_DEVICE_INFO_QUEUE_COMPUTE_MEMORY_MIN_SIZE = 0x54, + NVN_DEVICE_INFO_QUEUE_COMPUTE_MEMORY_DEFAULT_SIZE = 0x55, + NVN_DEVICE_INFO_QUEUE_COMMAND_MEMORY_MIN_FLUSH_THRESHOLD = 0x56, + NVN_DEVICE_INFO_SUPPORTS_FRAGMENT_SHADER_INTERLOCK = 0x57, + NVN_DEVICE_INFO_MAX_TEXTURES_PER_WINDOW = 0x58, + NVN_DEVICE_INFO_MIN_TEXTURES_PER_WINDOW = 0x59, + NVN_DEVICE_INFO_SUPPORTS_DEBUG_LAYER = 0x5A, + NVN_DEVICE_INFO_QUEUE_CONTROL_MEMORY_MIN_SIZE = 0x5B, + NVN_DEVICE_INFO_QUEUE_CONTROL_MEMORY_DEFAULT_SIZE = 0x5C, + NVN_DEVICE_INFO_QUEUE_CONTROL_MEMORY_GRANULARITY = 0x5D, + NVN_DEVICE_INFO_SEPARATE_TEXTURE_BINDINGS_PER_STAGE = 0x5E, + NVN_DEVICE_INFO_SEPARATE_SAMPLER_BINDINGS_PER_STAGE = 0x5F, + NVN_DEVICE_INFO_DEBUG_GROUPS_MAX_DOMAIN_ID = 0x60, + NVN_DEVICE_INFO_EVENTS_SUPPORT_REDUCTION_OPERATIONS = 0x61, + + NVN_DEVICE_INFO_LARGE = 0x7FFFFFFF +} NVNdeviceInfo; + +typedef enum { + NVN_DEVICE_FLAG_DEBUG_ENABLE = 0x1, + NVN_DEVICE_FLAG_DEBUG_SKIP_CALLS_ON_ERROR = 0x2, + NVN_DEVICE_FLAG_DEBUG_DRAW_VALIDATION = 0x4, + NVN_DEVICE_FLAG_DEFERRED_FINALIZE = 0x8, + NVN_DEVICE_FLAG_DEBUG_DRAW_VALIDATION_HEAVY = 0x10, + NVN_DEVICE_FLAG_DEBUG_ENABLE_LEVEL_0 = 0x20, + NVN_DEVICE_FLAG_DEBUG_ENABLE_LEVEL_1 = 0x40, + NVN_DEVICE_FLAG_DEBUG_ENABLE_LEVEL_2 = 0x1, + NVN_DEVICE_FLAG_DEBUG_ENABLE_LEVEL_3 = 0x4, + NVN_DEVICE_FLAG_DEBUG_ENABLE_LEVEL_4 = 0x10, + NVN_DEVICE_FLAG_DEFERRED_FIRMWARE_MEMORY_RECLAIM = 0x80, + NVN_DEVICE_FLAG_ENABLE_SEPARATE_SAMPLER_TEXTURE_SUPPORT = 0x100, + + NVN_DEVICE_FLAG_LARGE = 0x7FFFFFFF +} NVNdeviceFlagBits; + +typedef enum { + NVN_DEBUG_CALLBACK_SOURCE_API = 0x0, + + NVN_DEBUG_CALLBACK_SOURCE_LARGE = 0x7FFFFFFF +} NVNdebugCallbackSource; + +typedef enum { + NVN_DEBUG_CALLBACK_TYPE_API_ERROR = 0x0, + NVN_DEBUG_CALLBACK_TYPE_API_WARNING = 0x1, + + NVN_DEBUG_CALLBACK_TYPE_LARGE = 0x7FFFFFFF +} NVNdebugCallbackType; + +typedef enum { + NVN_DEBUG_CALLBACK_SEVERITY_HIGH = 0x0, + NVN_DEBUG_CALLBACK_SEVERITY_MEDIUM = 0x1, + NVN_DEBUG_CALLBACK_SEVERITY_LOW = 0x2, + NVN_DEBUG_CALLBACK_SEVERITY_NOTIFICATION = 0x3, + + NVN_DEBUG_CALLBACK_SEVERITY_LARGE = 0x7FFFFFFF +} NVNdebugCallbackSeverity; + +typedef enum { + NVN_WINDOW_ORIGIN_MODE_LOWER_LEFT = 0x0, + NVN_WINDOW_ORIGIN_MODE_UPPER_LEFT = 0x1, + + NVN_WINDOW_ORIGIN_MODE_LARGE = 0x7FFFFFFF +} NVNwindowOriginMode; + +typedef enum { + NVN_DEPTH_MODE_NEAR_IS_MINUS_W = 0x0, + NVN_DEPTH_MODE_NEAR_IS_ZERO = 0x1, + + NVN_DEPTH_MODE_LARGE = 0x7FFFFFFF +} NVNdepthMode; + +typedef enum { + NVN_FORMAT_NONE = 0x0, + NVN_FORMAT_R8 = 0x1, + NVN_FORMAT_R8SN = 0x2, + NVN_FORMAT_R8UI = 0x3, + NVN_FORMAT_R8I = 0x4, + NVN_FORMAT_R16F = 0x5, + NVN_FORMAT_R16 = 0x6, + NVN_FORMAT_R16SN = 0x7, + NVN_FORMAT_R16UI = 0x8, + NVN_FORMAT_R16I = 0x9, + NVN_FORMAT_R32F = 0xA, + NVN_FORMAT_R32UI = 0xB, + NVN_FORMAT_R32I = 0xC, + NVN_FORMAT_RG8 = 0xD, + NVN_FORMAT_RG8SN = 0xE, + NVN_FORMAT_RG8UI = 0xF, + NVN_FORMAT_RG8I = 0x10, + NVN_FORMAT_RG16F = 0x11, + NVN_FORMAT_RG16 = 0x12, + NVN_FORMAT_RG16SN = 0x13, + NVN_FORMAT_RG16UI = 0x14, + NVN_FORMAT_RG16I = 0x15, + NVN_FORMAT_RG32F = 0x16, + NVN_FORMAT_RG32UI = 0x17, + NVN_FORMAT_RG32I = 0x18, + NVN_FORMAT_RGB8 = 0x19, + NVN_FORMAT_RGB8SN = 0x1A, + NVN_FORMAT_RGB8UI = 0x1B, + NVN_FORMAT_RGB8I = 0x1C, + NVN_FORMAT_RGB16F = 0x1D, + NVN_FORMAT_RGB16 = 0x1E, + NVN_FORMAT_RGB16SN = 0x1F, + NVN_FORMAT_RGB16UI = 0x20, + NVN_FORMAT_RGB16I = 0x21, + NVN_FORMAT_RGB32F = 0x22, + NVN_FORMAT_RGB32UI = 0x23, + NVN_FORMAT_RGB32I = 0x24, + NVN_FORMAT_RGBA8 = 0x25, + NVN_FORMAT_RGBA8SN = 0x26, + NVN_FORMAT_RGBA8UI = 0x27, + NVN_FORMAT_RGBA8I = 0x28, + NVN_FORMAT_RGBA16F = 0x29, + NVN_FORMAT_RGBA16 = 0x2A, + NVN_FORMAT_RGBA16SN = 0x2B, + NVN_FORMAT_RGBA16UI = 0x2C, + NVN_FORMAT_RGBA16I = 0x2D, + NVN_FORMAT_RGBA32F = 0x2E, + NVN_FORMAT_RGBA32UI = 0x2F, + NVN_FORMAT_RGBA32I = 0x30, + NVN_FORMAT_STENCIL8 = 0x31, + NVN_FORMAT_DEPTH16 = 0x32, + NVN_FORMAT_DEPTH24 = 0x33, + NVN_FORMAT_DEPTH32F = 0x34, + NVN_FORMAT_DEPTH24_STENCIL8 = 0x35, + NVN_FORMAT_DEPTH32F_STENCIL8 = 0x36, + NVN_FORMAT_RGBX8_SRGB = 0x37, + NVN_FORMAT_RGBA8_SRGB = 0x38, + NVN_FORMAT_RGBA4 = 0x39, + NVN_FORMAT_RGB5 = 0x3A, + NVN_FORMAT_RGB5A1 = 0x3B, + NVN_FORMAT_RGB565 = 0x3C, + NVN_FORMAT_RGB10A2 = 0x3D, + NVN_FORMAT_RGB10A2UI = 0x3E, + NVN_FORMAT_R11G11B10F = 0x3F, + NVN_FORMAT_RGB9E5F = 0x40, + NVN_FORMAT_RGB_DXT1 = 0x41, + NVN_FORMAT_RGBA_DXT1 = 0x42, + NVN_FORMAT_RGBA_DXT3 = 0x43, + NVN_FORMAT_RGBA_DXT5 = 0x44, + NVN_FORMAT_RGB_DXT1_SRGB = 0x45, + NVN_FORMAT_RGBA_DXT1_SRGB = 0x46, + NVN_FORMAT_RGBA_DXT3_SRGB = 0x47, + NVN_FORMAT_RGBA_DXT5_SRGB = 0x48, + NVN_FORMAT_RGTC1_UNORM = 0x49, + NVN_FORMAT_RGTC1_SNORM = 0x4A, + NVN_FORMAT_RGTC2_UNORM = 0x4B, + NVN_FORMAT_RGTC2_SNORM = 0x4C, + NVN_FORMAT_BPTC_UNORM = 0x4D, + NVN_FORMAT_BPTC_UNORM_SRGB = 0x4E, + NVN_FORMAT_BPTC_SFLOAT = 0x4F, + NVN_FORMAT_BPTC_UFLOAT = 0x50, + NVN_FORMAT_R8_UI2F = 0x51, + NVN_FORMAT_R8_I2F = 0x52, + NVN_FORMAT_R16_UI2F = 0x53, + NVN_FORMAT_R16_I2F = 0x54, + NVN_FORMAT_R32_UI2F = 0x55, + NVN_FORMAT_R32_I2F = 0x56, + NVN_FORMAT_RG8_UI2F = 0x57, + NVN_FORMAT_RG8_I2F = 0x58, + NVN_FORMAT_RG16_UI2F = 0x59, + NVN_FORMAT_RG16_I2F = 0x5A, + NVN_FORMAT_RG32_UI2F = 0x5B, + NVN_FORMAT_RG32_I2F = 0x5C, + NVN_FORMAT_RGB8_UI2F = 0x5D, + NVN_FORMAT_RGB8_I2F = 0x5E, + NVN_FORMAT_RGB16_UI2F = 0x5F, + NVN_FORMAT_RGB16_I2F = 0x60, + NVN_FORMAT_RGB32_UI2F = 0x61, + NVN_FORMAT_RGB32_I2F = 0x62, + NVN_FORMAT_RGBA8_UI2F = 0x63, + NVN_FORMAT_RGBA8_I2F = 0x64, + NVN_FORMAT_RGBA16_UI2F = 0x65, + NVN_FORMAT_RGBA16_I2F = 0x66, + NVN_FORMAT_RGBA32_UI2F = 0x67, + NVN_FORMAT_RGBA32_I2F = 0x68, + NVN_FORMAT_RGB10A2SN = 0x69, + NVN_FORMAT_RGB10A2I = 0x6A, + NVN_FORMAT_RGB10A2_UI2F = 0x6B, + NVN_FORMAT_RGB10A2_I2F = 0x6C, + NVN_FORMAT_RGBX8 = 0x6D, + NVN_FORMAT_RGBX8SN = 0x6E, + NVN_FORMAT_RGBX8UI = 0x6F, + NVN_FORMAT_RGBX8I = 0x70, + NVN_FORMAT_RGBX16F = 0x71, + NVN_FORMAT_RGBX16 = 0x72, + NVN_FORMAT_RGBX16SN = 0x73, + NVN_FORMAT_RGBX16UI = 0x74, + NVN_FORMAT_RGBX16I = 0x75, + NVN_FORMAT_RGBX32F = 0x76, + NVN_FORMAT_RGBX32UI = 0x77, + NVN_FORMAT_RGBX32I = 0x78, + NVN_FORMAT_RGBA_ASTC_4x4 = 0x79, + NVN_FORMAT_RGBA_ASTC_5x4 = 0x7A, + NVN_FORMAT_RGBA_ASTC_5x5 = 0x7B, + NVN_FORMAT_RGBA_ASTC_6x5 = 0x7C, + NVN_FORMAT_RGBA_ASTC_6x6 = 0x7D, + NVN_FORMAT_RGBA_ASTC_8x5 = 0x7E, + NVN_FORMAT_RGBA_ASTC_8x6 = 0x7F, + NVN_FORMAT_RGBA_ASTC_8x8 = 0x80, + NVN_FORMAT_RGBA_ASTC_10x5 = 0x81, + NVN_FORMAT_RGBA_ASTC_10x6 = 0x82, + NVN_FORMAT_RGBA_ASTC_10x8 = 0x83, + NVN_FORMAT_RGBA_ASTC_10x10 = 0x84, + NVN_FORMAT_RGBA_ASTC_12x10 = 0x85, + NVN_FORMAT_RGBA_ASTC_12x12 = 0x86, + NVN_FORMAT_RGBA_ASTC_4x4_SRGB = 0x87, + NVN_FORMAT_RGBA_ASTC_5x4_SRGB = 0x88, + NVN_FORMAT_RGBA_ASTC_5x5_SRGB = 0x89, + NVN_FORMAT_RGBA_ASTC_6x5_SRGB = 0x8A, + NVN_FORMAT_RGBA_ASTC_6x6_SRGB = 0x8B, + NVN_FORMAT_RGBA_ASTC_8x5_SRGB = 0x8C, + NVN_FORMAT_RGBA_ASTC_8x6_SRGB = 0x8D, + NVN_FORMAT_RGBA_ASTC_8x8_SRGB = 0x8E, + NVN_FORMAT_RGBA_ASTC_10x5_SRGB = 0x8F, + NVN_FORMAT_RGBA_ASTC_10x6_SRGB = 0x90, + NVN_FORMAT_RGBA_ASTC_10x8_SRGB = 0x91, + NVN_FORMAT_RGBA_ASTC_10x10_SRGB = 0x92, + NVN_FORMAT_RGBA_ASTC_12x10_SRGB = 0x93, + NVN_FORMAT_RGBA_ASTC_12x12_SRGB = 0x94, + NVN_FORMAT_BGR565 = 0x95, + NVN_FORMAT_BGR5 = 0x96, + NVN_FORMAT_BGR5A1 = 0x97, + NVN_FORMAT_A1BGR5 = 0x98, + NVN_FORMAT_BGRX8 = 0x99, + NVN_FORMAT_BGRA8 = 0x9A, + NVN_FORMAT_BGRX8_SRGB = 0x9B, + NVN_FORMAT_BGRA8_SRGB = 0x9C, + + NVN_FORMAT_LARGE = 0x7FFFFFFF +} NVNformat; + +typedef enum { + NVN_DEBUG_OBJECT_TYPE_WINDOW = 0x0, + NVN_DEBUG_OBJECT_TYPE_QUEUE = 0x1, + NVN_DEBUG_OBJECT_TYPE_COMMAND_BUFFER = 0x2, + NVN_DEBUG_OBJECT_TYPE_MEMORY_POOL = 0x3, + NVN_DEBUG_OBJECT_TYPE_SYNC = 0x7, + NVN_DEBUG_OBJECT_TYPE_PROGRAM = 0x9, + NVN_DEBUG_OBJECT_TYPE_TEXTURE_POOL = 0xA, + NVN_DEBUG_OBJECT_TYPE_SAMPLER_POOL = 0xB, + + NVN_DEBUG_OBJECT_TYPE_LARGE = 0x7FFFFFFF +} NVNdebugObjectType; + +typedef enum { + NVN_QUEUE_GET_ERROR_RESULT_GPU_NO_ERROR = 0x0, + NVN_QUEUE_GET_ERROR_RESULT_GPU_ERROR_UNKNOWN = 0x1, + NVN_QUEUE_GET_ERROR_RESULT_GPU_ERROR_MMU_FAULT = 0x2, + NVN_QUEUE_GET_ERROR_RESULT_GPU_ERROR_PBDMA_EXCEPTION = 0x3, + NVN_QUEUE_GET_ERROR_RESULT_GPU_ERROR_ENGINE_EXCEPTION = 0x4, + NVN_QUEUE_GET_ERROR_RESULT_GPU_ERROR_TIMEOUT = 0x5, + + NVN_QUEUE_GET_ERROR_RESULT_LARGE = 0x7FFFFFFF +} NVNqueueGetErrorResult; + +typedef enum { + NVN_QUEUE_BUILDER_FLAGS_NONE = 0x0, + NVN_QUEUE_BUILDER_FLAGS_NO_FRAGMENT_INTERLOCK = 0x1, + NVN_QUEUE_BUILDER_FLAGS_NO_ZCULL = 0x2, + + NVN_QUEUE_BUILDER_FLAGS_LARGE = 0x7FFFFFFF +} NVNqueueBuilderFlags; + +typedef enum { + NVN_QUEUE_ACQUIRE_TEXTURE_RESULT_SUCCESS = 0x0, + NVN_QUEUE_ACQUIRE_TEXTURE_RESULT_NATIVE_ERROR = 0x1, + + NVN_QUEUE_ACQUIRE_TEXTURE_RESULT_LARGE = 0x7FFFFFFF +} NVNqueueAcquireTextureResult; + +typedef enum { + NVN_WINDOW_ACQUIRE_TEXTURE_RESULT_SUCCESS = 0x0, + NVN_WINDOW_ACQUIRE_TEXTURE_RESULT_NATIVE_ERROR = 0x1, + + NVN_WINDOW_ACQUIRE_TEXTURE_RESULT_LARGE = 0x7FFFFFFF +} NVNwindowAcquireTextureResult; + +typedef enum { + NVN_MEMORY_POOL_FLAGS_CPU_NO_ACCESS = 0x1, + NVN_MEMORY_POOL_FLAGS_CPU_UNCACHED = 0x2, + NVN_MEMORY_POOL_FLAGS_CPU_CACHED = 0x4, + NVN_MEMORY_POOL_FLAGS_GPU_NO_ACCESS = 0x8, + NVN_MEMORY_POOL_FLAGS_GPU_UNCACHED = 0x10, + NVN_MEMORY_POOL_FLAGS_GPU_CACHED = 0x20, + NVN_MEMORY_POOL_FLAGS_SHADER_CODE = 0x40, + NVN_MEMORY_POOL_FLAGS_COMPRESSIBLE = 0x80, + NVN_MEMORY_POOL_FLAGS_PHYSICAL = 0x100, + NVN_MEMORY_POOL_FLAGS_VIRTUAL = 0x200, + + NVN_MEMORY_POOL_FLAGS_LARGE = 0x7FFFFFFF +} NVNmemoryPoolFlags; + +typedef enum { + NVN_TEXTURE_SWIZZLE_ZERO = 0x0, + NVN_TEXTURE_SWIZZLE_ONE = 0x1, + NVN_TEXTURE_SWIZZLE_R = 0x2, + NVN_TEXTURE_SWIZZLE_G = 0x3, + NVN_TEXTURE_SWIZZLE_B = 0x4, + NVN_TEXTURE_SWIZZLE_A = 0x5, + + NVN_TEXTURE_SWIZZLE_LARGE = 0x7FFFFFFF +} NVNtextureSwizzle; + +typedef enum { + NVN_SHADER_STAGE_VERTEX = 0x0, + NVN_SHADER_STAGE_FRAGMENT = 0x1, + NVN_SHADER_STAGE_GEOMETRY = 0x2, + NVN_SHADER_STAGE_TESS_CONTROL = 0x3, + NVN_SHADER_STAGE_TESS_EVALUATION = 0x4, + NVN_SHADER_STAGE_COMPUTE = 0x5, + + NVN_SHADER_STAGE_LARGE = 0x7FFFFFFF +} NVNshaderStage; + +typedef enum { + NVN_EVENT_WAIT_MODE_EQUAL = 0x0, + NVN_EVENT_WAIT_MODE_GEQUAL_WRAP = 0x1, + + NVN_EVENT_WAIT_MODE_LARGE = 0x7FFFFFFF +} NVNeventWaitMode; + +typedef enum { + NVN_EVENT_SIGNAL_MODE_WRITE = 0x0, + NVN_EVENT_SIGNAL_MODE_ADD = 0x1, + + NVN_EVENT_SIGNAL_MODE_LARGE = 0x7FFFFFFF +} NVNeventSignalMode; + +typedef enum { + NVN_EVENT_SIGNAL_LOCATION_TOP = 0x0, + NVN_EVENT_SIGNAL_LOCATION_VERTEX_PIPE = 0x1, + NVN_EVENT_SIGNAL_LOCATION_BOTTOM = 0x2, + + NVN_EVENT_SIGNAL_LOCATION_LARGE = 0x7FFFFFFF +} NVNeventSignalLocation; + +typedef enum { + NVN_SYNC_CONDITION_ALL_GPU_COMMANDS_COMPLETE = 0x0, + NVN_SYNC_CONDITION_GRAPHICS_WORLD_SPACE_COMPLETE = 0x1, + + NVN_SYNC_CONDITION_LARGE = 0x7FFFFFFF +} NVNsyncCondition; + +typedef enum { + NVN_COUNTER_TYPE_TIMESTAMP = 0x0, + NVN_COUNTER_TYPE_SAMPLES_PASSED = 0x1, + NVN_COUNTER_TYPE_INPUT_VERTICES = 0x2, + NVN_COUNTER_TYPE_INPUT_PRIMITIVES = 0x3, + NVN_COUNTER_TYPE_VERTEX_SHADER_INVOCATIONS = 0x4, + NVN_COUNTER_TYPE_TESS_CONTROL_SHADER_INVOCATIONS = 0x5, + NVN_COUNTER_TYPE_TESS_EVALUATION_SHADER_INVOCATIONS = 0x6, + NVN_COUNTER_TYPE_GEOMETRY_SHADER_INVOCATIONS = 0x7, + NVN_COUNTER_TYPE_FRAGMENT_SHADER_INVOCATIONS = 0x8, + NVN_COUNTER_TYPE_TESS_EVALUATION_SHADER_PRIMITIVES = 0x9, + NVN_COUNTER_TYPE_GEOMETRY_SHADER_PRIMITIVES = 0xA, + NVN_COUNTER_TYPE_CLIPPER_INPUT_PRIMITIVES = 0xB, + NVN_COUNTER_TYPE_CLIPPER_OUTPUT_PRIMITIVES = 0xC, + NVN_COUNTER_TYPE_PRIMITIVES_GENERATED = 0xD, + NVN_COUNTER_TYPE_TRANSFORM_FEEDBACK_PRIMITIVES_WRITTEN = 0xE, + NVN_COUNTER_TYPE_ZCULL_STATS = 0xF, + NVN_COUNTER_TYPE_TIMESTAMP_TOP = 0x10, + + NVN_COUNTER_TYPE_LARGE = 0x7FFFFFFF +} NVNcounterType; + +typedef enum { + NVN_FACE_NONE = 0x0, + NVN_FACE_FRONT = 0x1, + NVN_FACE_BACK = 0x2, + NVN_FACE_FRONT_AND_BACK = 0x3, + + NVN_FACE_LARGE = 0x7FFFFFFF +} NVNface; + +typedef enum { + NVN_COMMAND_BUFFER_MEMORY_EVENT_OUT_OF_COMMAND_MEMORY = 0x0, + NVN_COMMAND_BUFFER_MEMORY_EVENT_OUT_OF_CONTROL_MEMORY = 0x1, + + NVN_COMMAND_BUFFER_MEMORY_EVENT_LARGE = 0x7FFFFFFF +} NVNcommandBufferMemoryEvent; + +typedef enum { + NVN_DRAW_PRIMITIVE_POINTS = 0x0, + NVN_DRAW_PRIMITIVE_LINES = 0x1, + NVN_DRAW_PRIMITIVE_LINE_LOOP = 0x2, + NVN_DRAW_PRIMITIVE_LINE_STRIP = 0x3, + NVN_DRAW_PRIMITIVE_TRIANGLES = 0x4, + NVN_DRAW_PRIMITIVE_TRIANGLE_STRIP = 0x5, + NVN_DRAW_PRIMITIVE_TRIANGLE_FAN = 0x6, + NVN_DRAW_PRIMITIVE_QUADS = 0x7, + NVN_DRAW_PRIMITIVE_QUAD_STRIP = 0x8, + NVN_DRAW_PRIMITIVE_POLYGON = 0x9, + NVN_DRAW_PRIMITIVE_LINES_ADJACENCY = 0xA, + NVN_DRAW_PRIMITIVE_LINE_STRIP_ADJACENCY = 0xB, + NVN_DRAW_PRIMITIVE_TRIANGLES_ADJACENCY = 0xC, + NVN_DRAW_PRIMITIVE_TRIANGLE_STRIP_ADJACENCY = 0xD, + NVN_DRAW_PRIMITIVE_PATCHES = 0xE, + + NVN_DRAW_PRIMITIVE_LARGE = 0x7FFFFFFF +} NVNdrawPrimitive; + +typedef enum { + NVN_INDEX_TYPE_UNSIGNED_BYTE = 0x0, + NVN_INDEX_TYPE_UNSIGNED_SHORT = 0x1, + NVN_INDEX_TYPE_UNSIGNED_INT = 0x2, + + NVN_INDEX_TYPE_LARGE = 0x7FFFFFFF +} NVNindexType; + +typedef enum { + NVN_TEXTURE_FLAGS_DISPLAY = 0x1, + NVN_TEXTURE_FLAGS_VIDEO_DECODE = 0x2, + NVN_TEXTURE_FLAGS_IMAGE = 0x4, + NVN_TEXTURE_FLAGS_COMPRESSIBLE = 0x8, + NVN_TEXTURE_FLAGS_LINEAR = 0x10, + NVN_TEXTURE_FLAGS_SPARSE = 0x20, + NVN_TEXTURE_FLAGS_LINEAR_RENDER_TARGET = 0x40, + NVN_TEXTURE_FLAGS_ADAPTIVE_ZCULL = 0x80, + NVN_TEXTURE_FLAGS_DEPTH16_PREFER_FAST_CLEAR = 0x100, + NVN_TEXTURE_FLAGS_MINIMAL_LAYOUT = 0x200, + NVN_TEXTURE_FLAGS_ZCULL_SUPPORT_STENCIL = 0x400, + + NVN_TEXTURE_FLAGS_LARGE = 0x7FFFFFFF +} NVNtextureFlags; + +typedef enum { + NVN_TEXTURE_TARGET_1D = 0x0, + NVN_TEXTURE_TARGET_2D = 0x1, + NVN_TEXTURE_TARGET_3D = 0x2, + NVN_TEXTURE_TARGET_1D_ARRAY = 0x3, + NVN_TEXTURE_TARGET_2D_ARRAY = 0x4, + NVN_TEXTURE_TARGET_2D_MULTISAMPLE = 0x5, + NVN_TEXTURE_TARGET_2D_MULTISAMPLE_ARRAY = 0x6, + NVN_TEXTURE_TARGET_RECTANGLE = 0x7, + NVN_TEXTURE_TARGET_CUBEMAP = 0x8, + NVN_TEXTURE_TARGET_CUBEMAP_ARRAY = 0x9, + NVN_TEXTURE_TARGET_BUFFER = 0xA, + + NVN_TEXTURE_TARGET_LARGE = 0x7FFFFFFF +} NVNtextureTarget; + +typedef enum { + NVN_TEXTURE_DEPTH_STENCIL_MODE_DEPTH = 0x0, + NVN_TEXTURE_DEPTH_STENCIL_MODE_STENCIL = 0x1, + + NVN_TEXTURE_DEPTH_STENCIL_MODE_LARGE = 0x7FFFFFFF +} NVNtextureDepthStencilMode; + +typedef enum { + NVN_LOGIC_OP_CLEAR = 0x0, + NVN_LOGIC_OP_AND = 0x1, + NVN_LOGIC_OP_AND_REVERSE = 0x2, + NVN_LOGIC_OP_COPY = 0x3, + NVN_LOGIC_OP_AND_INVERTED = 0x4, + NVN_LOGIC_OP_NOOP = 0x5, + NVN_LOGIC_OP_XOR = 0x6, + NVN_LOGIC_OP_OR = 0x7, + NVN_LOGIC_OP_NOR = 0x8, + NVN_LOGIC_OP_EQUIV = 0x9, + NVN_LOGIC_OP_INVERT = 0xA, + NVN_LOGIC_OP_OR_REVERSE = 0xB, + NVN_LOGIC_OP_COPY_INVERTED = 0xC, + NVN_LOGIC_OP_OR_INVERTED = 0xD, + NVN_LOGIC_OP_NAND = 0xE, + NVN_LOGIC_OP_SET = 0xF, + + NVN_LOGIC_OP_LARGE = 0x7FFFFFFF +} NVNlogicOp; + +typedef enum { + NVN_ALPHA_FUNC_NEVER = 0x1, + NVN_ALPHA_FUNC_LESS = 0x2, + NVN_ALPHA_FUNC_EQUAL = 0x3, + NVN_ALPHA_FUNC_LEQUAL = 0x4, + NVN_ALPHA_FUNC_GREATER = 0x5, + NVN_ALPHA_FUNC_NOTEQUAL = 0x6, + NVN_ALPHA_FUNC_GEQUAL = 0x7, + NVN_ALPHA_FUNC_ALWAYS = 0x8, + + NVN_ALPHA_FUNC_LARGE = 0x7FFFFFFF +} NVNalphaFunc; + +typedef enum { + NVN_BLEND_ADVANCED_MODE_NONE = 0x0, + NVN_BLEND_ADVANCED_MODE_ZERO = 0x5, + NVN_BLEND_ADVANCED_MODE_SRC = 0x6, + NVN_BLEND_ADVANCED_MODE_DST = 0x7, + NVN_BLEND_ADVANCED_MODE_SRC_OVER = 0x8, + NVN_BLEND_ADVANCED_MODE_DST_OVER = 0x9, + NVN_BLEND_ADVANCED_MODE_SRC_IN = 0xA, + NVN_BLEND_ADVANCED_MODE_DST_IN = 0xB, + NVN_BLEND_ADVANCED_MODE_SRC_OUT = 0xC, + NVN_BLEND_ADVANCED_MODE_DST_OUT = 0xD, + NVN_BLEND_ADVANCED_MODE_SRC_ATOP = 0xE, + NVN_BLEND_ADVANCED_MODE_DST_ATOP = 0xF, + NVN_BLEND_ADVANCED_MODE_XOR = 0x10, + NVN_BLEND_ADVANCED_MODE_PLUS = 0x11, + NVN_BLEND_ADVANCED_MODE_PLUS_CLAMPED = 0x12, + NVN_BLEND_ADVANCED_MODE_PLUS_CLAMPED_ALPHA = 0x13, + NVN_BLEND_ADVANCED_MODE_PLUS_DARKER = 0x14, + NVN_BLEND_ADVANCED_MODE_MULTIPLY = 0x15, + NVN_BLEND_ADVANCED_MODE_SCREEN = 0x16, + NVN_BLEND_ADVANCED_MODE_OVERLAY = 0x17, + NVN_BLEND_ADVANCED_MODE_DARKEN = 0x18, + NVN_BLEND_ADVANCED_MODE_LIGHTEN = 0x19, + NVN_BLEND_ADVANCED_MODE_COLORDODGE = 0x1A, + NVN_BLEND_ADVANCED_MODE_COLORBURN = 0x1B, + NVN_BLEND_ADVANCED_MODE_HARDLIGHT = 0x1C, + NVN_BLEND_ADVANCED_MODE_SOFTLIGHT = 0x1D, + NVN_BLEND_ADVANCED_MODE_DIFFERENCE = 0x1E, + NVN_BLEND_ADVANCED_MODE_MINUS = 0x1F, + NVN_BLEND_ADVANCED_MODE_MINUS_CLAMPED = 0x20, + NVN_BLEND_ADVANCED_MODE_EXCLUSION = 0x21, + NVN_BLEND_ADVANCED_MODE_CONTRAST = 0x22, + NVN_BLEND_ADVANCED_MODE_INVERT = 0x23, + NVN_BLEND_ADVANCED_MODE_INVERT_RGB = 0x24, + NVN_BLEND_ADVANCED_MODE_INVERT_OVG = 0x25, + NVN_BLEND_ADVANCED_MODE_LINEARDODGE = 0x26, + NVN_BLEND_ADVANCED_MODE_LINEARBURN = 0x27, + NVN_BLEND_ADVANCED_MODE_VIVIDLIGHT = 0x28, + NVN_BLEND_ADVANCED_MODE_LINEARLIGHT = 0x29, + NVN_BLEND_ADVANCED_MODE_PINLIGHT = 0x2A, + NVN_BLEND_ADVANCED_MODE_HARDMIX = 0x2B, + NVN_BLEND_ADVANCED_MODE_RED = 0x2C, + NVN_BLEND_ADVANCED_MODE_GREEN = 0x2D, + NVN_BLEND_ADVANCED_MODE_BLUE = 0x2E, + NVN_BLEND_ADVANCED_MODE_HSL_HUE = 0x2F, + NVN_BLEND_ADVANCED_MODE_HSL_SATURATION = 0x30, + NVN_BLEND_ADVANCED_MODE_HSL_COLOR = 0x31, + NVN_BLEND_ADVANCED_MODE_HSL_LUMINOSITY = 0x32, + + NVN_BLEND_ADVANCED_MODE_LARGE = 0x7FFFFFFF +} NVNblendAdvancedMode; + +typedef enum { + NVN_MIN_FILTER_NEAREST = 0x0, + NVN_MIN_FILTER_LINEAR = 0x1, + NVN_MIN_FILTER_NEAREST_MIPMAP_NEAREST = 0x2, + NVN_MIN_FILTER_LINEAR_MIPMAP_NEAREST = 0x3, + NVN_MIN_FILTER_NEAREST_MIPMAP_LINEAR = 0x4, + NVN_MIN_FILTER_LINEAR_MIPMAP_LINEAR = 0x5, + + NVN_MIN_FILTER_LARGE = 0x7FFFFFFF +} NVNminFilter; + +typedef enum { + NVN_MAG_FILTER_NEAREST = 0x0, + NVN_MAG_FILTER_LINEAR = 0x1, + + NVN_MAG_FILTER_LARGE = 0x7FFFFFFF +} NVNmagFilter; + +typedef enum { + NVN_WRAP_MODE_CLAMP = 0x0, + NVN_WRAP_MODE_REPEAT = 0x1, + NVN_WRAP_MODE_MIRROR_CLAMP = 0x2, + NVN_WRAP_MODE_MIRROR_CLAMP_TO_EDGE = 0x3, + NVN_WRAP_MODE_MIRROR_CLAMP_TO_BORDER = 0x4, + NVN_WRAP_MODE_CLAMP_TO_BORDER = 0x5, + NVN_WRAP_MODE_MIRRORED_REPEAT = 0x6, + NVN_WRAP_MODE_CLAMP_TO_EDGE = 0x7, + + NVN_WRAP_MODE_LARGE = 0x7FFFFFFF +} NVNwrapMode; + +typedef enum { + NVN_COMPARE_MODE_NONE = 0x0, + NVN_COMPARE_MODE_COMPARE_R_TO_TEXTURE = 0x1, + + NVN_COMPARE_MODE_LARGE = 0x7FFFFFFF +} NVNcompareMode; + +typedef enum { + NVN_COMPARE_FUNC_NEVER = 0x1, + NVN_COMPARE_FUNC_LESS = 0x2, + NVN_COMPARE_FUNC_EQUAL = 0x3, + NVN_COMPARE_FUNC_LEQUAL = 0x4, + NVN_COMPARE_FUNC_GREATER = 0x5, + NVN_COMPARE_FUNC_NOTEQUAL = 0x6, + NVN_COMPARE_FUNC_GEQUAL = 0x7, + NVN_COMPARE_FUNC_ALWAYS = 0x8, + + NVN_COMPARE_FUNC_LARGE = 0x7FFFFFFF +} NVNcompareFunc; + +typedef enum { + NVN_SAMPLER_REDUCTION_AVERAGE = 0x0, + NVN_SAMPLER_REDUCTION_MIN = 0x1, + NVN_SAMPLER_REDUCTION_MAX = 0x2, + + NVN_SAMPLER_REDUCTION_LARGE = 0x7FFFFFFF +} NVNsamplerReduction; + +typedef enum { + NVN_BLEND_FUNC_ZERO = 0x1, + NVN_BLEND_FUNC_ONE = 0x2, + NVN_BLEND_FUNC_SRC_COLOR = 0x3, + NVN_BLEND_FUNC_ONE_MINUS_SRC_COLOR = 0x4, + NVN_BLEND_FUNC_SRC_ALPHA = 0x5, + NVN_BLEND_FUNC_ONE_MINUS_SRC_ALPHA = 0x6, + NVN_BLEND_FUNC_DST_ALPHA = 0x7, + NVN_BLEND_FUNC_ONE_MINUS_DST_ALPHA = 0x8, + NVN_BLEND_FUNC_DST_COLOR = 0x9, + NVN_BLEND_FUNC_ONE_MINUS_DST_COLOR = 0xA, + NVN_BLEND_FUNC_SRC_ALPHA_SATURATE = 0xB, + NVN_BLEND_FUNC_SRC1_COLOR = 0x10, + NVN_BLEND_FUNC_ONE_MINUS_SRC1_COLOR = 0x11, + NVN_BLEND_FUNC_SRC1_ALPHA = 0x12, + NVN_BLEND_FUNC_ONE_MINUS_SRC1_ALPHA = 0x13, + NVN_BLEND_FUNC_CONSTANT_COLOR = 0x61, + NVN_BLEND_FUNC_ONE_MINUS_CONSTANT_COLOR = 0x62, + NVN_BLEND_FUNC_CONSTANT_ALPHA = 0x63, + NVN_BLEND_FUNC_ONE_MINUS_CONSTANT_ALPHA = 0x64, + + NVN_BLEND_FUNC_LARGE = 0x7FFFFFFF +} NVNblendFunc; + +typedef enum { + NVN_BLEND_EQUATION_ADD = 0x1, + NVN_BLEND_EQUATION_SUB = 0x2, + NVN_BLEND_EQUATION_REVERSE_SUB = 0x3, + NVN_BLEND_EQUATION_MIN = 0x4, + NVN_BLEND_EQUATION_MAX = 0x5, + + NVN_BLEND_EQUATION_LARGE = 0x7FFFFFFF +} NVNblendEquation; + +typedef enum { + NVN_BLEND_ADVANCED_OVERLAP_UNCORRELATED = 0x0, + NVN_BLEND_ADVANCED_OVERLAP_DISJOINT = 0x1, + NVN_BLEND_ADVANCED_OVERLAP_CONJOINT = 0x2, + + NVN_BLEND_ADVANCED_OVERLAP_LARGE = 0x7FFFFFFF +} NVNblendAdvancedOverlap; + +typedef enum { + NVN_COVERAGE_MODULATION_MODE_NONE = 0x0, + NVN_COVERAGE_MODULATION_MODE_RGB = 0x1, + NVN_COVERAGE_MODULATION_MODE_ALPHA = 0x2, + NVN_COVERAGE_MODULATION_MODE_RGBA = 0x3, + + NVN_COVERAGE_MODULATION_MODE_LARGE = 0x7FFFFFFF +} NVNcoverageModulationMode; + +typedef enum { + NVN_DEPTH_FUNC_NEVER = 0x1, + NVN_DEPTH_FUNC_LESS = 0x2, + NVN_DEPTH_FUNC_EQUAL = 0x3, + NVN_DEPTH_FUNC_LEQUAL = 0x4, + NVN_DEPTH_FUNC_GREATER = 0x5, + NVN_DEPTH_FUNC_NOTEQUAL = 0x6, + NVN_DEPTH_FUNC_GEQUAL = 0x7, + NVN_DEPTH_FUNC_ALWAYS = 0x8, + + NVN_DEPTH_FUNC_LARGE = 0x7FFFFFFF +} NVNdepthFunc; + +typedef enum { + NVN_STENCIL_FUNC_NEVER = 0x1, + NVN_STENCIL_FUNC_LESS = 0x2, + NVN_STENCIL_FUNC_EQUAL = 0x3, + NVN_STENCIL_FUNC_LEQUAL = 0x4, + NVN_STENCIL_FUNC_GREATER = 0x5, + NVN_STENCIL_FUNC_NOTEQUAL = 0x6, + NVN_STENCIL_FUNC_GEQUAL = 0x7, + NVN_STENCIL_FUNC_ALWAYS = 0x8, + + NVN_STENCIL_FUNC_LARGE = 0x7FFFFFFF +} NVNstencilFunc; + +typedef enum { + NVN_STENCIL_OP_KEEP = 0x1, + NVN_STENCIL_OP_ZERO = 0x2, + NVN_STENCIL_OP_REPLACE = 0x3, + NVN_STENCIL_OP_INCR = 0x4, + NVN_STENCIL_OP_DECR = 0x5, + NVN_STENCIL_OP_INVERT = 0x6, + NVN_STENCIL_OP_INCR_WRAP = 0x7, + NVN_STENCIL_OP_DECR_WRAP = 0x8, + + NVN_STENCIL_OP_LARGE = 0x7FFFFFFF +} NVNstencilOp; + +typedef enum { + NVN_FRONT_FACE_CW = 0x0, + NVN_FRONT_FACE_CCW = 0x1, + + NVN_FRONT_FACE_LARGE = 0x7FFFFFFF +} NVNfrontFace; + +typedef enum { + NVN_SYNC_WAIT_RESULT_ALREADY_SIGNALED = 0x0, + NVN_SYNC_WAIT_RESULT_CONDITION_SATISFIED = 0x1, + NVN_SYNC_WAIT_RESULT_TIMEOUT_EXPIRED = 0x2, + NVN_SYNC_WAIT_RESULT_FAILED = 0x3, + + NVN_SYNC_WAIT_RESULT_LARGE = 0x7FFFFFFF +} NVNsyncWaitResult; + +typedef enum { + NVN_POLYGON_OFFSET_ENABLE_NONE = 0x0, + NVN_POLYGON_OFFSET_ENABLE_POINT = 0x1, + NVN_POLYGON_OFFSET_ENABLE_LINE = 0x2, + NVN_POLYGON_OFFSET_ENABLE_FILL = 0x4, + + NVN_POLYGON_OFFSET_ENABLE_LARGE = 0x7FFFFFFF +} NVNpolygonOffsetEnable; + +typedef enum { + NVN_POLYGON_MODE_POINT = 0x0, + NVN_POLYGON_MODE_LINE = 0x1, + NVN_POLYGON_MODE_FILL = 0x2, + + NVN_POLYGON_MODE_LARGE = 0x7FFFFFFF +} NVNpolygonMode; + +typedef enum { + NVN_VIEWPORT_SWIZZLE_POSITIVE_X = 0x0, + NVN_VIEWPORT_SWIZZLE_NEGATIVE_X = 0x1, + NVN_VIEWPORT_SWIZZLE_POSITIVE_Y = 0x2, + NVN_VIEWPORT_SWIZZLE_NEGATIVE_Y = 0x3, + NVN_VIEWPORT_SWIZZLE_POSITIVE_Z = 0x4, + NVN_VIEWPORT_SWIZZLE_NEGATIVE_Z = 0x5, + NVN_VIEWPORT_SWIZZLE_POSITIVE_W = 0x6, + NVN_VIEWPORT_SWIZZLE_NEGATIVE_W = 0x7, + + NVN_VIEWPORT_SWIZZLE_LARGE = 0x7FFFFFFF +} NVNviewportSwizzle; + +typedef enum { + NVN_TILED_CACHE_ACTION_ENABLE = 0x1, + NVN_TILED_CACHE_ACTION_DISABLE = 0x2, + NVN_TILED_CACHE_ACTION_FLUSH = 0x3, + NVN_TILED_CACHE_ACTION_FLUSH_NO_TILING = 0x4, + NVN_TILED_CACHE_ACTION_ENABLE_RENDER_TARGET_BINNING = 0x5, + NVN_TILED_CACHE_ACTION_DISABLE_RENDER_TARGET_BINNING = 0x6, + + NVN_TILED_CACHE_ACTION_LARGE = 0x7FFFFFFF +} NVNtiledCacheAction; + +typedef enum { + NVN_CONDITIONAL_RENDER_MODE_RENDER_IF_EQUAL = 0x0, + NVN_CONDITIONAL_RENDER_MODE_RENDER_IF_NOT_EQUAL = 0x1, + + NVN_CONDITIONAL_RENDER_MODE_LARGE = 0x7FFFFFFF +} NVNconditionalRenderMode; + +typedef void (*NVNdummyProc)(void); +typedef void (*NVNcommandBufferMemoryCallback)(NVNcommandBuffer*, NVNcommandBufferMemoryEvent, + size_t, void*); +typedef void (*NVNdebugCallback)(NVNdebugCallbackSource source, NVNdebugCallbackType type, int id, + NVNdebugCallbackSeverity severity, const unsigned char* message, + void* user); +typedef void (*NVNwalkDebugDatabaseCallback)(void*, void*); + +#ifdef __cplusplus +} +#endif diff --git a/lib/NintendoSDK/include/vapours/results.hpp b/lib/NintendoSDK/include/vapours/results.hpp new file mode 100644 index 00000000..f4533dd2 --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results.hpp @@ -0,0 +1,55 @@ +/* + * 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 . + */ + +#pragma once + +/* Utilities. */ +#include + +/* Official. */ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +/* Unofficial. */ +#include diff --git a/lib/NintendoSDK/include/vapours/results/cal_results.hpp b/lib/NintendoSDK/include/vapours/results/cal_results.hpp new file mode 100644 index 00000000..e465e8f7 --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/cal_results.hpp @@ -0,0 +1,26 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::cal { + + R_DEFINE_NAMESPACE_RESULT_MODULE(198); + + R_DEFINE_ERROR_RESULT(CalibrationDataCrcError, 101); + +} diff --git a/lib/NintendoSDK/include/vapours/results/capsrv_results.hpp b/lib/NintendoSDK/include/vapours/results/capsrv_results.hpp new file mode 100644 index 00000000..102dad3e --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/capsrv_results.hpp @@ -0,0 +1,92 @@ +/* + * Copyright (c) 2018-2019 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 . + */ +#pragma once +#include + +namespace ams::capsrv { + + R_DEFINE_NAMESPACE_RESULT_MODULE(206); + + R_DEFINE_ERROR_RANGE(AlbumError, 2, 99); + R_DEFINE_ERROR_RESULT(AlbumWorkMemoryError, 3); + + R_DEFINE_ERROR_RESULT(AlbumAlreadyOpened, 7); + R_DEFINE_ERROR_RESULT(AlbumOutOfRange, 8); + + R_DEFINE_ERROR_RANGE(AlbumInvalidFileId, 10, 19); + R_DEFINE_ERROR_RESULT(AlbumInvalidApplicationId, 11); + R_DEFINE_ERROR_RESULT(AlbumInvalidTimestamp, 12); + R_DEFINE_ERROR_RESULT(AlbumInvalidStorage, 13); + R_DEFINE_ERROR_RESULT(AlbumInvalidFileContents, 14); + + R_DEFINE_ERROR_RESULT(AlbumIsNotMounted, 21); + R_DEFINE_ERROR_RESULT(AlbumIsFull, 22); + R_DEFINE_ERROR_RESULT(AlbumFileNotFound, 23); + R_DEFINE_ERROR_RESULT(AlbumInvalidFileData, 24); + R_DEFINE_ERROR_RESULT(AlbumFileCountLimit, 25); + R_DEFINE_ERROR_RESULT(AlbumFileNoThumbnail, 26); + + R_DEFINE_ERROR_RESULT(AlbumReadBufferShortage, 30); + + R_DEFINE_ERROR_RANGE(AlbumFileSystemError, 90, 99); + R_DEFINE_ERROR_RANGE(AlbumAccessCorrupted, 94, 96); + R_DEFINE_ERROR_RESULT(AlbumDestinationAccessCorrupted, 96); + + R_DEFINE_ERROR_RANGE(ControlError, 800, 899); + R_DEFINE_ERROR_RESULT(ControlResourceLimit, 820); + R_DEFINE_ERROR_RESULT(ControlNotOpened, 822); + + R_DEFINE_ERROR_RESULT(NotSupported, 1023); + + R_DEFINE_ERROR_RANGE(InternalError, 1024, 2047); + R_DEFINE_ERROR_RESULT(InternalJpegEncoderError, 1210); + R_DEFINE_ERROR_RESULT(InternalJpegWorkMemoryShortage, 1212); + + R_DEFINE_ERROR_RANGE(InternalFileDataVerificationError, 1300, 1399); + R_DEFINE_ERROR_RESULT(InternalFileDataVerificationEmptyFileData, 1301); + R_DEFINE_ERROR_RESULT(InternalFileDataVerificationExifExtractionFailed, 1302); + R_DEFINE_ERROR_RESULT(InternalFileDataVerificationExifAnalyzationFailed, 1303); + R_DEFINE_ERROR_RESULT(InternalFileDataVerificationDateTimeExtractionFailed, 1304); + R_DEFINE_ERROR_RESULT(InternalFileDataVerificationInvalidDateTimeLength, 1305); + R_DEFINE_ERROR_RESULT(InternalFileDataVerificationInconsistentDateTime, 1306); + R_DEFINE_ERROR_RESULT(InternalFileDataVerificationMakerNoteExtractionFailed, 1307); + R_DEFINE_ERROR_RESULT(InternalFileDataVerificationInconsistentApplicationId, 1308); + R_DEFINE_ERROR_RESULT(InternalFileDataVerificationInconsistentSignature, 1309); + R_DEFINE_ERROR_RESULT(InternalFileDataVerificationUnsupportedOrientation, 1310); + R_DEFINE_ERROR_RESULT(InternalFileDataVerificationInvalidDataDimension, 1311); + R_DEFINE_ERROR_RESULT(InternalFileDataVerificationInconsistentOrientation, 1312); + + R_DEFINE_ERROR_RANGE(InternalAlbumLimitationError, 1400, 1499); + R_DEFINE_ERROR_RESULT(InternalAlbumLimitationFileCountLimit, 1401); + + R_DEFINE_ERROR_RANGE(InternalSignatureError, 1500, 1599); + R_DEFINE_ERROR_RESULT(InternalSignatureExifExtractionFailed, 1501); + R_DEFINE_ERROR_RESULT(InternalSignatureMakerNoteExtractionFailed, 1502); + + R_DEFINE_ERROR_RANGE(InternalAlbumSessionError, 1700, 1799); + R_DEFINE_ERROR_RESULT(InternalAlbumLimitationSessionCountLimit, 1701); + + R_DEFINE_ERROR_RANGE(InternalAlbumTemporaryFileError, 1900, 1999); + R_DEFINE_ERROR_RESULT(InternalAlbumTemporaryFileCountLimit, 1901); + R_DEFINE_ERROR_RESULT(InternalAlbumTemporaryFileCreateError, 1902); + R_DEFINE_ERROR_RESULT(InternalAlbumTemporaryFileCreateRetryCountLimit, 1903); + R_DEFINE_ERROR_RESULT(InternalAlbumTemporaryFileOpenError, 1904); + R_DEFINE_ERROR_RESULT(InternalAlbumTemporaryFileGetFileSizeError, 1905); + R_DEFINE_ERROR_RESULT(InternalAlbumTemporaryFileSetFileSizeError, 1906); + R_DEFINE_ERROR_RESULT(InternalAlbumTemporaryFileReadFileError, 1907); + R_DEFINE_ERROR_RESULT(InternalAlbumTemporaryFileWriteFileError, 1908); + +} diff --git a/lib/NintendoSDK/include/vapours/results/creport_results.hpp b/lib/NintendoSDK/include/vapours/results/creport_results.hpp new file mode 100644 index 00000000..6a924b6c --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/creport_results.hpp @@ -0,0 +1,37 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::creport { + + R_DEFINE_NAMESPACE_RESULT_MODULE(168); + + R_DEFINE_ERROR_RESULT(UndefinedInstruction, 0); + R_DEFINE_ERROR_RESULT(InstructionAbort, 1); + R_DEFINE_ERROR_RESULT(DataAbort, 2); + R_DEFINE_ERROR_RESULT(AlignmentFault, 3); + R_DEFINE_ERROR_RESULT(DebuggerAttached, 4); + R_DEFINE_ERROR_RESULT(BreakPoint, 5); + R_DEFINE_ERROR_RESULT(UserBreak, 6); + R_DEFINE_ERROR_RESULT(DebuggerBreak, 7); + R_DEFINE_ERROR_RESULT(UndefinedSystemCall, 8); + R_DEFINE_ERROR_RESULT(MemorySystemError, 9); + + R_DEFINE_ERROR_RESULT(IncompleteReport, 99); + +} diff --git a/lib/NintendoSDK/include/vapours/results/debug_results.hpp b/lib/NintendoSDK/include/vapours/results/debug_results.hpp new file mode 100644 index 00000000..da2ed640 --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/debug_results.hpp @@ -0,0 +1,28 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::dbg { + + R_DEFINE_NAMESPACE_RESULT_MODULE(183); + + R_DEFINE_ERROR_RESULT(CannotDebug, 1); + R_DEFINE_ERROR_RESULT(AlreadyAttached, 2); + R_DEFINE_ERROR_RESULT(Cancelled, 3); + +} diff --git a/lib/NintendoSDK/include/vapours/results/dmnt_results.hpp b/lib/NintendoSDK/include/vapours/results/dmnt_results.hpp new file mode 100644 index 00000000..95e2ed3c --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/dmnt_results.hpp @@ -0,0 +1,50 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::dmnt { + + R_DEFINE_NAMESPACE_RESULT_MODULE(13); + + R_DEFINE_ERROR_RESULT(Unknown, 1); + R_DEFINE_ERROR_RESULT(DebuggingDisabled, 2); + + /* Atmosphere extension. */ + namespace cheat { + + R_DEFINE_ABSTRACT_ERROR_RANGE(CheatError, 6500, 6599); + R_DEFINE_ERROR_RESULT(CheatNotAttached, 6500); + R_DEFINE_ERROR_RESULT(CheatNullBuffer, 6501); + R_DEFINE_ERROR_RESULT(CheatInvalidBuffer, 6502); + R_DEFINE_ERROR_RESULT(CheatUnknownId, 6503); + R_DEFINE_ERROR_RESULT(CheatOutOfResource, 6504); + R_DEFINE_ERROR_RESULT(CheatInvalid, 6505); + R_DEFINE_ERROR_RESULT(CheatCannotDisable, 6506); + + R_DEFINE_ABSTRACT_ERROR_RANGE(FrozenAddressError, 6600, 6699); + R_DEFINE_ERROR_RESULT(FrozenAddressInvalidWidth, 6600); + R_DEFINE_ERROR_RESULT(FrozenAddressAlreadyExists, 6601); + R_DEFINE_ERROR_RESULT(FrozenAddressNotFound, 6602); + R_DEFINE_ERROR_RESULT(FrozenAddressOutOfResource, 6603); + + R_DEFINE_ABSTRACT_ERROR_RANGE(VirtualMachineError, 6700, 6799); + R_DEFINE_ERROR_RESULT(VirtualMachineInvalidConditionDepth, 6700); + + } + +} diff --git a/lib/NintendoSDK/include/vapours/results/erpt_results.hpp b/lib/NintendoSDK/include/vapours/results/erpt_results.hpp new file mode 100644 index 00000000..4993474d --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/erpt_results.hpp @@ -0,0 +1,43 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::erpt { + + R_DEFINE_NAMESPACE_RESULT_MODULE(147); + + R_DEFINE_ERROR_RESULT(NotInitialized, 1); + R_DEFINE_ERROR_RESULT(AlreadyInitialized, 2); + R_DEFINE_ERROR_RESULT(OutOfArraySpace, 3); + R_DEFINE_ERROR_RESULT(OutOfFieldSpace, 4); + R_DEFINE_ERROR_RESULT(OutOfMemory, 5); + R_DEFINE_ERROR_RESULT(InvalidArgument, 7); + R_DEFINE_ERROR_RESULT(NotFound, 8); + R_DEFINE_ERROR_RESULT(FieldCategoryMismatch, 9); + R_DEFINE_ERROR_RESULT(FieldTypeMismatch, 10); + R_DEFINE_ERROR_RESULT(AlreadyExists, 11); + R_DEFINE_ERROR_RESULT(CorruptJournal, 12); + R_DEFINE_ERROR_RESULT(CategoryNotFound, 13); + R_DEFINE_ERROR_RESULT(RequiredContextMissing, 14); + R_DEFINE_ERROR_RESULT(RequiredFieldMissing, 15); + R_DEFINE_ERROR_RESULT(FormatterError, 16); + R_DEFINE_ERROR_RESULT(InvalidPowerState, 17); + R_DEFINE_ERROR_RESULT(ArrayFieldTooLarge, 18); + R_DEFINE_ERROR_RESULT(AlreadyOwned, 19); + +} diff --git a/lib/NintendoSDK/include/vapours/results/err_results.hpp b/lib/NintendoSDK/include/vapours/results/err_results.hpp new file mode 100644 index 00000000..9aa60c01 --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/err_results.hpp @@ -0,0 +1,27 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::err { + + R_DEFINE_NAMESPACE_RESULT_MODULE(162); + + R_DEFINE_ERROR_RESULT(ApplicationAborted, 1); + R_DEFINE_ERROR_RESULT(SystemModuleAborted, 2); + +} diff --git a/lib/NintendoSDK/include/vapours/results/exosphere_results.hpp b/lib/NintendoSDK/include/vapours/results/exosphere_results.hpp new file mode 100644 index 00000000..c89c5d13 --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/exosphere_results.hpp @@ -0,0 +1,30 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::exosphere { + + /* Please note: These results are all custom, and not official. */ + R_DEFINE_NAMESPACE_RESULT_MODULE(444); + + + /* Result 1-1000 reserved for Atmosphere. */ + R_DEFINE_ERROR_RESULT(NotPresent, 1); + R_DEFINE_ERROR_RESULT(VersionMismatch, 2); + +} diff --git a/lib/NintendoSDK/include/vapours/results/fatal_results.hpp b/lib/NintendoSDK/include/vapours/results/fatal_results.hpp new file mode 100644 index 00000000..27105d88 --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/fatal_results.hpp @@ -0,0 +1,31 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::fatal { + + R_DEFINE_NAMESPACE_RESULT_MODULE(163); + + R_DEFINE_ERROR_RESULT(AllocationFailed, 1); + R_DEFINE_ERROR_RESULT(NullGraphicsBuffer, 2); + R_DEFINE_ERROR_RESULT(AlreadyThrown, 3); + R_DEFINE_ERROR_RESULT(TooManyEvents, 4); + R_DEFINE_ERROR_RESULT(InRepairWithoutVolHeld, 5); + R_DEFINE_ERROR_RESULT(InRepairWithoutTimeReviserCartridge, 6); + +} diff --git a/lib/NintendoSDK/include/vapours/results/fs_results.hpp b/lib/NintendoSDK/include/vapours/results/fs_results.hpp new file mode 100644 index 00000000..5128fb63 --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/fs_results.hpp @@ -0,0 +1,409 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::fs { + + R_DEFINE_NAMESPACE_RESULT_MODULE(2); + + R_DEFINE_ERROR_RANGE(HandledByAllProcess, 0, 999); + R_DEFINE_ERROR_RESULT(PathNotFound, 1); + R_DEFINE_ERROR_RESULT(PathAlreadyExists, 2); + + R_DEFINE_ERROR_RESULT(TargetLocked, 7); + R_DEFINE_ERROR_RESULT(DirectoryNotEmpty, 8); + + R_DEFINE_ERROR_RANGE (NotEnoughFreeSpace, 30, 45); + R_DEFINE_ERROR_RANGE(NotEnoughFreeSpaceBis, 34, 38); + R_DEFINE_ERROR_RESULT(NotEnoughFreeSpaceBisCalibration, 35); + R_DEFINE_ERROR_RESULT(NotEnoughFreeSpaceBisSafe, 36); + R_DEFINE_ERROR_RESULT(NotEnoughFreeSpaceBisUser, 37); + R_DEFINE_ERROR_RESULT(NotEnoughFreeSpaceBisSystem, 38); + R_DEFINE_ERROR_RESULT(NotEnoughFreeSpaceSdCard, 39); + + R_DEFINE_ERROR_RESULT(UnsupportedSdkVersion, 50); + + R_DEFINE_ERROR_RESULT(MountNameAlreadyExists, 60); + + R_DEFINE_ERROR_RANGE(HandledBySystemProcess, 1000, 2999); + R_DEFINE_ERROR_RESULT(PartitionNotFound, 1001); + R_DEFINE_ERROR_RESULT(TargetNotFound, 1002); + + R_DEFINE_ERROR_RANGE(SdCardAccessFailed, 2000, 2499); + R_DEFINE_ERROR_RESULT(SdCardNotPresent, 2001); + + R_DEFINE_ERROR_RANGE(GameCardAccessFailed, 2500, 2999); + + R_DEFINE_ERROR_RESULT(NotImplemented, 3001); + R_DEFINE_ERROR_RESULT(UnsupportedVersion, 3002); + R_DEFINE_ERROR_RESULT(OutOfRange, 3005); + + R_DEFINE_ERROR_RESULT(SystemPartitionNotReady, 3100); + + R_DEFINE_ERROR_RANGE(AllocationFailure, 3200, 3499); + R_DEFINE_ERROR_RESULT(AllocationFailureInFileSystemAccessorA, 3211); + R_DEFINE_ERROR_RESULT(AllocationFailureInFileSystemAccessorB, 3212); + R_DEFINE_ERROR_RESULT(AllocationFailureInApplicationA, 3213); + R_DEFINE_ERROR_RESULT(AllocationFailureInBisA, 3215); + R_DEFINE_ERROR_RESULT(AllocationFailureInBisB, 3216); + R_DEFINE_ERROR_RESULT(AllocationFailureInBisC, 3217); + R_DEFINE_ERROR_RESULT(AllocationFailureInCodeA, 3218); + R_DEFINE_ERROR_RESULT(AllocationFailureInContentA, 3219); + R_DEFINE_ERROR_RESULT(AllocationFailureInContentStorageA, 3220); + R_DEFINE_ERROR_RESULT(AllocationFailureInContentStorageB, 3221); + R_DEFINE_ERROR_RESULT(AllocationFailureInDataA, 3222); + R_DEFINE_ERROR_RESULT(AllocationFailureInDataB, 3223); + R_DEFINE_ERROR_RESULT(AllocationFailureInDeviceSaveDataA, 3224); + R_DEFINE_ERROR_RESULT(AllocationFailureInGameCardA, 3225); + R_DEFINE_ERROR_RESULT(AllocationFailureInGameCardB, 3226); + R_DEFINE_ERROR_RESULT(AllocationFailureInGameCardC, 3227); + R_DEFINE_ERROR_RESULT(AllocationFailureInGameCardD, 3228); + R_DEFINE_ERROR_RESULT(AllocationFailureInImageDirectoryA, 3232); + R_DEFINE_ERROR_RESULT(AllocationFailureInSdCardA, 3244); + R_DEFINE_ERROR_RESULT(AllocationFailureInSdCardB, 3245); + R_DEFINE_ERROR_RESULT(AllocationFailureInSystemSaveDataA, 3246); + R_DEFINE_ERROR_RESULT(AllocationFailureInRomFsFileSystemA, 3247); + R_DEFINE_ERROR_RESULT(AllocationFailureInRomFsFileSystemB, 3248); + R_DEFINE_ERROR_RESULT(AllocationFailureInRomFsFileSystemC, 3249); + R_DEFINE_ERROR_RESULT(AllocationFailureInFileSystemProxyCoreImplD, 3256); + R_DEFINE_ERROR_RESULT(AllocationFailureInFileSystemProxyCoreImplE, 3257); + R_DEFINE_ERROR_RESULT(AllocationFailureInPartitionFileSystemCreatorA, 3280); + R_DEFINE_ERROR_RESULT(AllocationFailureInRomFileSystemCreatorA, 3281); + R_DEFINE_ERROR_RESULT(AllocationFailureInStorageOnNcaCreatorA, 3288); + R_DEFINE_ERROR_RESULT(AllocationFailureInStorageOnNcaCreatorB, 3289); + R_DEFINE_ERROR_RESULT(AllocationFailureInFileSystemBuddyHeapA, 3294); + R_DEFINE_ERROR_RESULT(AllocationFailureInFileSystemBufferManagerA, 3295); + R_DEFINE_ERROR_RESULT(AllocationFailureInBlockCacheBufferedStorageA, 3296); + R_DEFINE_ERROR_RESULT(AllocationFailureInBlockCacheBufferedStorageB, 3297); + R_DEFINE_ERROR_RESULT(AllocationFailureInIntegrityVerificationStorageA, 3304); + R_DEFINE_ERROR_RESULT(AllocationFailureInIntegrityVerificationStorageB, 3305); + R_DEFINE_ERROR_RESULT(AllocationFailureInDirectorySaveDataFileSystem, 3321); + R_DEFINE_ERROR_RESULT(AllocationFailureInNcaFileSystemDriverI, 3341); + R_DEFINE_ERROR_RESULT(AllocationFailureInPartitionFileSystemA, 3347); + R_DEFINE_ERROR_RESULT(AllocationFailureInPartitionFileSystemB, 3348); + R_DEFINE_ERROR_RESULT(AllocationFailureInPartitionFileSystemC, 3349); + R_DEFINE_ERROR_RESULT(AllocationFailureInPartitionFileSystemMetaA, 3350); + R_DEFINE_ERROR_RESULT(AllocationFailureInPartitionFileSystemMetaB, 3351); + R_DEFINE_ERROR_RESULT(AllocationFailureInRomFsFileSystemD, 3352); + R_DEFINE_ERROR_RESULT(AllocationFailureInSubDirectoryFileSystem, 3355); + R_DEFINE_ERROR_RESULT(AllocationFailureInNcaReaderA, 3363); + R_DEFINE_ERROR_RESULT(AllocationFailureInRegisterA, 3365); + R_DEFINE_ERROR_RESULT(AllocationFailureInRegisterB, 3366); + R_DEFINE_ERROR_RESULT(AllocationFailureInPathNormalizer, 3367); + R_DEFINE_ERROR_RESULT(AllocationFailureInDbmRomKeyValueStorage, 3375); + R_DEFINE_ERROR_RESULT(AllocationFailureInRomFsFileSystemE, 3377); + R_DEFINE_ERROR_RESULT(AllocationFailureInReadOnlyFileSystemA, 3386); + R_DEFINE_ERROR_RESULT(AllocationFailureInAesCtrCounterExtendedStorageA, 3399); + R_DEFINE_ERROR_RESULT(AllocationFailureInAesCtrCounterExtendedStorageB, 3400); + R_DEFINE_ERROR_RESULT(AllocationFailureInFileSystemInterfaceAdapter, 3407); + R_DEFINE_ERROR_RESULT(AllocationFailureInBufferedStorageA, 3411); + R_DEFINE_ERROR_RESULT(AllocationFailureInIntegrityRomFsStorageA, 3412); + R_DEFINE_ERROR_RESULT(AllocationFailureInNew, 3420); + R_DEFINE_ERROR_RESULT(AllocationFailureInMakeUnique, 3422); + R_DEFINE_ERROR_RESULT(AllocationFailureInAllocateShared, 3423); + R_DEFINE_ERROR_RESULT(AllocationFailurePooledBufferNotEnoughSize, 3424); + + R_DEFINE_ERROR_RANGE(Internal, 3000, 7999); + R_DEFINE_ERROR_RANGE(MmcAccessFailed, 3500, 3999); + + R_DEFINE_ERROR_RANGE(DataCorrupted, 4000, 4999); + R_DEFINE_ERROR_RANGE(RomCorrupted, 4001, 4299); + R_DEFINE_ERROR_RESULT(UnsupportedRomVersion, 4002); + + R_DEFINE_ERROR_RANGE(AesCtrCounterExtendedStorageCorrupted, 4011, 4019); + R_DEFINE_ERROR_RESULT(InvalidAesCtrCounterExtendedEntryOffset, 4012); + R_DEFINE_ERROR_RESULT(InvalidAesCtrCounterExtendedTableSize, 4013); + R_DEFINE_ERROR_RESULT(InvalidAesCtrCounterExtendedGeneration, 4014); + R_DEFINE_ERROR_RESULT(InvalidAesCtrCounterExtendedOffset, 4015); + + R_DEFINE_ERROR_RANGE(IndirectStorageCorrupted, 4021, 4029); + R_DEFINE_ERROR_RESULT(InvalidIndirectEntryOffset, 4022); + R_DEFINE_ERROR_RESULT(InvalidIndirectEntryStorageIndex, 4023); + R_DEFINE_ERROR_RESULT(InvalidIndirectStorageSize, 4024); + R_DEFINE_ERROR_RESULT(InvalidIndirectVirtualOffset, 4025); + R_DEFINE_ERROR_RESULT(InvalidIndirectPhysicalOffset, 4026); + R_DEFINE_ERROR_RESULT(InvalidIndirectStorageIndex, 4027); + + R_DEFINE_ERROR_RANGE(BucketTreeCorrupted, 4031, 4039); + R_DEFINE_ERROR_RESULT(InvalidBucketTreeSignature, 4032); + R_DEFINE_ERROR_RESULT(InvalidBucketTreeEntryCount, 4033); + R_DEFINE_ERROR_RESULT(InvalidBucketTreeNodeEntryCount, 4034); + R_DEFINE_ERROR_RESULT(InvalidBucketTreeNodeOffset, 4035); + R_DEFINE_ERROR_RESULT(InvalidBucketTreeEntryOffset, 4036); + R_DEFINE_ERROR_RESULT(InvalidBucketTreeEntrySetOffset, 4037); + R_DEFINE_ERROR_RESULT(InvalidBucketTreeNodeIndex, 4038); + R_DEFINE_ERROR_RESULT(InvalidBucketTreeVirtualOffset, 4039); + + R_DEFINE_ERROR_RANGE(RomNcaCorrupted, 4041, 4139); + R_DEFINE_ERROR_RANGE(RomNcaFileSystemCorrupted, 4051, 4069); + R_DEFINE_ERROR_RESULT(InvalidRomNcaFileSystemType, 4052); + R_DEFINE_ERROR_RESULT(InvalidRomAcidFileSize, 4053); + R_DEFINE_ERROR_RESULT(InvalidRomAcidSize, 4054); + R_DEFINE_ERROR_RESULT(InvalidRomAcid, 4055); + R_DEFINE_ERROR_RESULT(RomAcidVerificationFailed, 4056); + R_DEFINE_ERROR_RESULT(InvalidRomNcaSignature, 4057); + R_DEFINE_ERROR_RESULT(RomNcaHeaderSignature1VerificationFailed, 4058); + R_DEFINE_ERROR_RESULT(RomNcaHeaderSignature2VerificationFailed, 4059); + R_DEFINE_ERROR_RESULT(RomNcaFsHeaderHashVerificationFailed, 4060); + R_DEFINE_ERROR_RESULT(InvalidRomNcaKeyIndex, 4061); + R_DEFINE_ERROR_RESULT(InvalidRomNcaFsHeaderHashType, 4062); + R_DEFINE_ERROR_RESULT(InvalidRomNcaFsHeaderEncryptionType, 4063); + + R_DEFINE_ERROR_RANGE(RomNcaHierarchicalSha256StorageCorrupted, 4071, 4079); + R_DEFINE_ERROR_RESULT(InvalidRomHierarchicalSha256BlockSize, 4072); + R_DEFINE_ERROR_RESULT(InvalidRomHierarchicalSha256LayerCount, 4073); + R_DEFINE_ERROR_RESULT(RomHierarchicalSha256BaseStorageTooLarge, 4074); + R_DEFINE_ERROR_RESULT(RomHierarchicalSha256HashVerificationFailed, 4075); + + R_DEFINE_ERROR_RANGE(RomIntegrityVerificationStorageCorrupted, 4141, 4179); + R_DEFINE_ERROR_RESULT(IncorrectRomIntegrityVerificationMagic, 4142); + R_DEFINE_ERROR_RESULT(InvalidRomZeroHash, 4143); + R_DEFINE_ERROR_RESULT(RomNonRealDataVerificationFailed, 4144); + R_DEFINE_ERROR_RESULT(InvalidRomHierarchicalIntegrityVerificationLayerCount, 4145); + + R_DEFINE_ERROR_RANGE(RomRealDataVerificationFailed, 4151, 4159); + R_DEFINE_ERROR_RESULT(ClearedRomRealDataVerificationFailed, 4152); + R_DEFINE_ERROR_RESULT(UnclearedRomRealDataVerificationFailed, 4153); + + R_DEFINE_ERROR_RANGE(RomPartitionFileSystemCorrupted, 4181, 4199); + R_DEFINE_ERROR_RESULT(InvalidRomSha256PartitionHashTarget, 4182); + R_DEFINE_ERROR_RESULT(RomSha256PartitionHashVerificationFailed, 4183); + R_DEFINE_ERROR_RESULT(RomPartitionSignatureVerificationFailed, 4184); + R_DEFINE_ERROR_RESULT(RomSha256PartitionSignatureVerificationFailed, 4185); + R_DEFINE_ERROR_RESULT(InvalidRomPartitionEntryOffset, 4186); + R_DEFINE_ERROR_RESULT(InvalidRomSha256PartitionMetaDataSize, 4187); + + R_DEFINE_ERROR_RANGE(RomBuiltInStorageCorrupted, 4201, 4219); + R_DEFINE_ERROR_RESULT(RomGptHeaderVerificationFailed, 4202); + + R_DEFINE_ERROR_RANGE(RomHostFileSystemCorrupted, 4241, 4259); + R_DEFINE_ERROR_RESULT(RomHostEntryCorrupted, 4242); + R_DEFINE_ERROR_RESULT(RomHostFileDataCorrupted, 4243); + R_DEFINE_ERROR_RESULT(RomHostFileCorrupted, 4244); + R_DEFINE_ERROR_RESULT(InvalidRomHostHandle, 4245); + + R_DEFINE_ERROR_RANGE(RomDatabaseCorrupted, 4261, 4279); + R_DEFINE_ERROR_RESULT(InvalidRomAllocationTableBlock, 4262); + R_DEFINE_ERROR_RESULT(InvalidRomKeyValueListElementIndex, 4263); + + R_DEFINE_ERROR_RANGE(SaveDataCorrupted, 4301, 4499); + R_DEFINE_ERROR_RANGE(NcaCorrupted, 4501, 4599); + R_DEFINE_ERROR_RESULT(NcaBaseStorageOutOfRangeA, 4508); + R_DEFINE_ERROR_RESULT(NcaBaseStorageOutOfRangeB, 4509); + + R_DEFINE_ERROR_RANGE(NcaFileSystemCorrupted, 4511, 4529); + R_DEFINE_ERROR_RESULT(InvalidNcaFileSystemType, 4512); + R_DEFINE_ERROR_RESULT(InvalidAcidFileSize, 4513); + R_DEFINE_ERROR_RESULT(InvalidAcidSize, 4514); + R_DEFINE_ERROR_RESULT(InvalidAcid, 4515); + R_DEFINE_ERROR_RESULT(AcidVerificationFailed, 4516); + R_DEFINE_ERROR_RESULT(InvalidNcaSignature, 4517); + R_DEFINE_ERROR_RESULT(NcaHeaderSignature1VerificationFailed, 4518); + R_DEFINE_ERROR_RESULT(NcaHeaderSignature2VerificationFailed, 4519); + R_DEFINE_ERROR_RESULT(NcaFsHeaderHashVerificationFailed, 4520); + R_DEFINE_ERROR_RESULT(InvalidNcaKeyIndex, 4521); + R_DEFINE_ERROR_RESULT(InvalidNcaFsHeaderHashType, 4522); + R_DEFINE_ERROR_RESULT(InvalidNcaFsHeaderEncryptionType, 4523); + R_DEFINE_ERROR_RESULT(InvalidNcaPatchInfoIndirectSize, 4524); + R_DEFINE_ERROR_RESULT(InvalidNcaPatchInfoAesCtrExSize, 4525); + R_DEFINE_ERROR_RESULT(InvalidNcaPatchInfoAesCtrExOffset, 4526); + R_DEFINE_ERROR_RESULT(InvalidNcaId, 4527); + R_DEFINE_ERROR_RESULT(InvalidNcaHeader, 4528); + R_DEFINE_ERROR_RESULT(InvalidNcaFsHeader, 4529); + + R_DEFINE_ERROR_RANGE(NcaHierarchicalSha256StorageCorrupted, 4531, 4539); + R_DEFINE_ERROR_RESULT(InvalidHierarchicalSha256BlockSize, 4532); + R_DEFINE_ERROR_RESULT(InvalidHierarchicalSha256LayerCount, 4533); + R_DEFINE_ERROR_RESULT(HierarchicalSha256BaseStorageTooLarge, 4534); + R_DEFINE_ERROR_RESULT(HierarchicalSha256HashVerificationFailed, 4535); + + /* TODO: Range? */ + R_DEFINE_ERROR_RESULT(InvalidNcaHeader1SignatureKeyGeneration, 4543); + + R_DEFINE_ERROR_RANGE(IntegrityVerificationStorageCorrupted, 4601, 4639); + R_DEFINE_ERROR_RESULT(IncorrectIntegrityVerificationMagic, 4602); + R_DEFINE_ERROR_RESULT(InvalidZeroHash, 4603); + R_DEFINE_ERROR_RESULT(NonRealDataVerificationFailed, 4604); + R_DEFINE_ERROR_RESULT(InvalidHierarchicalIntegrityVerificationLayerCount, 4605); + + R_DEFINE_ERROR_RANGE(RealDataVerificationFailed, 4611, 4619); + R_DEFINE_ERROR_RESULT(ClearedRealDataVerificationFailed, 4612); + R_DEFINE_ERROR_RESULT(UnclearedRealDataVerificationFailed, 4613); + + R_DEFINE_ERROR_RANGE(PartitionFileSystemCorrupted, 4641, 4659); + R_DEFINE_ERROR_RESULT(InvalidSha256PartitionHashTarget, 4642); + R_DEFINE_ERROR_RESULT(Sha256PartitionHashVerificationFailed, 4643); + R_DEFINE_ERROR_RESULT(PartitionSignatureVerificationFailed, 4644); + R_DEFINE_ERROR_RESULT(Sha256PartitionSignatureVerificationFailed, 4645); + R_DEFINE_ERROR_RESULT(InvalidPartitionEntryOffset, 4646); + R_DEFINE_ERROR_RESULT(InvalidSha256PartitionMetaDataSize, 4647); + + R_DEFINE_ERROR_RANGE(BuiltInStorageCorrupted, 4661, 4679); + R_DEFINE_ERROR_RESULT(GptHeaderVerificationFailed, 4662); + + R_DEFINE_ERROR_RANGE(FatFileSystemCorrupted, 4681, 4699); + + R_DEFINE_ERROR_RANGE(HostFileSystemCorrupted, 4701, 4719); + R_DEFINE_ERROR_RESULT(HostEntryCorrupted, 4702); + R_DEFINE_ERROR_RESULT(HostFileDataCorrupted, 4703); + R_DEFINE_ERROR_RESULT(HostFileCorrupted, 4704); + R_DEFINE_ERROR_RESULT(InvalidHostHandle, 4705); + + R_DEFINE_ERROR_RANGE(DatabaseCorrupted, 4721, 4739); + R_DEFINE_ERROR_RESULT(InvalidAllocationTableBlock, 4722); + R_DEFINE_ERROR_RESULT(InvalidKeyValueListElementIndex, 4723); + + R_DEFINE_ERROR_RANGE(AesXtsFileSystemCorrupted, 4741, 4759); + R_DEFINE_ERROR_RANGE(SaveDataTransferDataCorrupted, 4761, 4769); + R_DEFINE_ERROR_RANGE(SignedSystemPartitionDataCorrupted, 4771, 4779); + + R_DEFINE_ERROR_RESULT(GameCardLogoDataCorrupted, 4781); + + R_DEFINE_ERROR_RANGE(Unexpected, 5000, 5999); + R_DEFINE_ERROR_RESULT(UnexpectedInAesCtrStorageA, 5315); + R_DEFINE_ERROR_RESULT(UnexpectedInAesXtsStorageA, 5316); + R_DEFINE_ERROR_RESULT(UnexpectedInFindFileSystemA, 5319); + + R_DEFINE_ERROR_RANGE(PreconditionViolation, 6000, 6499); + R_DEFINE_ERROR_RANGE(InvalidArgument, 6001, 6199); + R_DEFINE_ERROR_RANGE(InvalidPath, 6002, 6029); + R_DEFINE_ERROR_RESULT(TooLongPath, 6003); + R_DEFINE_ERROR_RESULT(InvalidCharacter, 6004); + R_DEFINE_ERROR_RESULT(InvalidPathFormat, 6005); + R_DEFINE_ERROR_RESULT(DirectoryUnobtainable, 6006); + R_DEFINE_ERROR_RESULT(NotNormalized, 6007); + + R_DEFINE_ERROR_RANGE(InvalidPathForOperation, 6030, 6059); + R_DEFINE_ERROR_RESULT(DirectoryNotDeletable, 6031); + R_DEFINE_ERROR_RESULT(DirectoryNotRenamable, 6032); + R_DEFINE_ERROR_RESULT(IncompatiblePath, 6033); + R_DEFINE_ERROR_RESULT(RenameToOtherFileSystem, 6034); + + R_DEFINE_ERROR_RESULT(InvalidOffset, 6061); + R_DEFINE_ERROR_RESULT(InvalidSize, 6062); + R_DEFINE_ERROR_RESULT(NullptrArgument, 6063); + R_DEFINE_ERROR_RESULT(InvalidAlignment, 6064); + R_DEFINE_ERROR_RESULT(InvalidMountName, 6065); + + R_DEFINE_ERROR_RESULT(ExtensionSizeTooLarge, 6066); + R_DEFINE_ERROR_RESULT(ExtensionSizeInvalid, 6067); + + R_DEFINE_ERROR_RESULT(InvalidOpenMode, 6072); + + R_DEFINE_ERROR_RANGE(InvalidEnumValue, 6080, 6099); + R_DEFINE_ERROR_RESULT(InvalidSaveDataState, 6081); + R_DEFINE_ERROR_RESULT(InvalidSaveDataSpaceId, 6082); + + R_DEFINE_ERROR_RANGE(InvalidOperationForOpenMode, 6200, 6299); + R_DEFINE_ERROR_RESULT(FileExtensionWithoutOpenModeAllowAppend, 6201); + R_DEFINE_ERROR_RESULT(ReadNotPermitted, 6202); + R_DEFINE_ERROR_RESULT(WriteNotPermitted, 6203); + + R_DEFINE_ERROR_RANGE(UnsupportedOperation, 6300, 6399); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInSubStorageA, 6302); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInSubStorageB, 6303); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInMemoryStorageA, 6304); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInMemoryStorageB, 6305); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInFileStorageA, 6306); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInFileStorageB, 6307); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInSwitchStorageA, 6308); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInAesCtrCounterExtendedStorageA, 6310); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInAesCtrCounterExtendedStorageB, 6311); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInAesCtrCounterExtendedStorageC, 6312); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInAesCtrStorageExternalA, 6313); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInAesCtrStorageExternalB, 6314); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInAesCtrStorageA, 6315); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInHierarchicalIntegrityVerificationStorageA, 6316); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInHierarchicalIntegrityVerificationStorageB, 6317); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInIntegrityVerificationStorageA, 6318); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInIntegrityVerificationStorageB, 6319); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInIntegrityVerificationStorageC, 6320); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInBlockCacheBufferedStorageA, 6321); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInBlockCacheBufferedStorageB, 6322); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInBlockCacheBufferedStorageC, 6323); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInIndirectStorageA, 6324); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInIndirectStorageB, 6325); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInIndirectStorageC, 6326); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInZeroStorageA, 6327); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInZeroStorageB, 6328); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInHierarchicalSha256StorageA, 6329); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInReadOnlyBlockCacheStorageA, 6330); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInReadOnlyBlockCacheStorageB, 6331); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInIntegrityRomFsStorageA , 6332); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInFileServiceObjectAdapterA, 6362); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInRomFsFileSystemA, 6364); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInRomFsFileSystemB, 6365); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInRomFsFileSystemC, 6366); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInRomFsFileA, 6367); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInRomFsFileB, 6368); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInReadOnlyFileSystemTemplateA, 6369); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInReadOnlyFileSystemTemplateB, 6370); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInReadOnlyFileSystemTemplateC, 6371); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInReadOnlyFileA, 6372); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInReadOnlyFileB, 6373); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInPartitionFileSystemA, 6374); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInPartitionFileSystemB, 6375); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInPartitionFileA, 6376); + R_DEFINE_ERROR_RESULT(UnsupportedOperationInPartitionFileB, 6377); + + R_DEFINE_ERROR_RANGE(PermissionDenied, 6400, 6449); + + R_DEFINE_ERROR_RESULT(NeedFlush, 6454); + R_DEFINE_ERROR_RESULT(FileNotClosed, 6455); + R_DEFINE_ERROR_RESULT(DirectoryNotClosed, 6456); + R_DEFINE_ERROR_RESULT(WriteModeFileNotClosed, 6457); + R_DEFINE_ERROR_RESULT(AllocatorAlreadyRegistered, 6458); + R_DEFINE_ERROR_RESULT(DefaultAllocatorUsed, 6459); + R_DEFINE_ERROR_RESULT(AllocatorAlignmentViolation, 6461); + R_DEFINE_ERROR_RESULT(UserNotExist, 6465); + + R_DEFINE_ERROR_RANGE(NotFound, 6600, 6699); + + R_DEFINE_ERROR_RANGE(OutOfResource, 6700, 6799); + R_DEFINE_ERROR_RESULT(BufferAllocationFailed, 6705); + R_DEFINE_ERROR_RESULT(MappingTableFull, 6706); + R_DEFINE_ERROR_RESULT(OpenCountLimit, 6709); + + R_DEFINE_ERROR_RANGE(MappingFailed, 6800, 6899); + R_DEFINE_ERROR_RESULT(MapFull, 6811); + + R_DEFINE_ERROR_RANGE(BadState, 6900, 6999); + R_DEFINE_ERROR_RESULT(NotInitialized, 6902); + R_DEFINE_ERROR_RESULT(NotMounted, 6905); + + + R_DEFINE_ERROR_RANGE(DbmNotFound, 7901, 7904); + R_DEFINE_ERROR_RESULT(DbmKeyNotFound, 7902); + R_DEFINE_ERROR_RESULT(DbmFileNotFound, 7903); + R_DEFINE_ERROR_RESULT(DbmDirectoryNotFound, 7904); + + R_DEFINE_ERROR_RESULT(DbmAlreadyExists, 7906); + R_DEFINE_ERROR_RESULT(DbmKeyFull, 7907); + R_DEFINE_ERROR_RESULT(DbmDirectoryEntryFull, 7908); + R_DEFINE_ERROR_RESULT(DbmFileEntryFull, 7909); + + R_DEFINE_ERROR_RANGE(DbmFindFinished, 7910, 7912); + R_DEFINE_ERROR_RESULT(DbmFindKeyFinished, 7911); + R_DEFINE_ERROR_RESULT(DbmIterationFinished, 7912); + + R_DEFINE_ERROR_RESULT(DbmInvalidOperation, 7914); + R_DEFINE_ERROR_RESULT(DbmInvalidPathFormat, 7915); + R_DEFINE_ERROR_RESULT(DbmDirectoryNameTooLong, 7916); + R_DEFINE_ERROR_RESULT(DbmFileNameTooLong, 7917); + +} diff --git a/lib/NintendoSDK/include/vapours/results/hipc_results.hpp b/lib/NintendoSDK/include/vapours/results/hipc_results.hpp new file mode 100644 index 00000000..dec237e1 --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/hipc_results.hpp @@ -0,0 +1,41 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::sf::hipc { + + R_DEFINE_NAMESPACE_RESULT_MODULE(11); + + R_DEFINE_ABSTRACT_ERROR_RANGE(OutOfResource, 100, 299); + R_DEFINE_ERROR_RESULT(OutOfSessionMemory, 102); + R_DEFINE_ERROR_RANGE (OutOfSessions, 131, 139); + R_DEFINE_ERROR_RESULT(PointerBufferTooSmall, 141); + + R_DEFINE_ERROR_RESULT(OutOfDomains, 200); + + R_DEFINE_ERROR_RESULT(SessionClosed, 301); + + R_DEFINE_ERROR_RESULT(InvalidRequestSize, 402); + R_DEFINE_ERROR_RESULT(UnknownCommandType, 403); + + R_DEFINE_ERROR_RESULT(InvalidCmifRequest, 420); + + R_DEFINE_ERROR_RESULT(TargetNotDomain, 491); + R_DEFINE_ERROR_RESULT(DomainObjectNotFound, 492); + +} diff --git a/lib/NintendoSDK/include/vapours/results/i2c_results.hpp b/lib/NintendoSDK/include/vapours/results/i2c_results.hpp new file mode 100644 index 00000000..62cb26eb --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/i2c_results.hpp @@ -0,0 +1,30 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::i2c { + + R_DEFINE_NAMESPACE_RESULT_MODULE(101); + + R_DEFINE_ERROR_RESULT(NoAck, 1); + R_DEFINE_ERROR_RESULT(BusBusy, 2); + R_DEFINE_ERROR_RESULT(FullCommandList, 3); + R_DEFINE_ERROR_RESULT(TimedOut, 4); + R_DEFINE_ERROR_RESULT(UnknownDevice, 5); + +} diff --git a/lib/NintendoSDK/include/vapours/results/kvdb_results.hpp b/lib/NintendoSDK/include/vapours/results/kvdb_results.hpp new file mode 100644 index 00000000..ba6731b5 --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/kvdb_results.hpp @@ -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 . + */ + +#pragma once +#include + +namespace ams::kvdb { + + R_DEFINE_NAMESPACE_RESULT_MODULE(20); + + R_DEFINE_ERROR_RESULT(OutOfKeyResource, 1); + R_DEFINE_ERROR_RESULT(KeyNotFound, 2); + R_DEFINE_ERROR_RESULT(AllocationFailed, 4); + R_DEFINE_ERROR_RESULT(InvalidKeyValue, 5); + R_DEFINE_ERROR_RESULT(BufferInsufficient, 6); + + R_DEFINE_ERROR_RESULT(InvalidFilesystemState, 8); + R_DEFINE_ERROR_RESULT(NotCreated, 9); + +} diff --git a/lib/NintendoSDK/include/vapours/results/loader_results.hpp b/lib/NintendoSDK/include/vapours/results/loader_results.hpp new file mode 100644 index 00000000..1ffa7ae1 --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/loader_results.hpp @@ -0,0 +1,65 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::ldr { + + R_DEFINE_NAMESPACE_RESULT_MODULE(9); + + R_DEFINE_ERROR_RESULT(TooLongArgument, 1); + R_DEFINE_ERROR_RESULT(TooManyArguments, 2); + R_DEFINE_ERROR_RESULT(TooLargeMeta, 3); + R_DEFINE_ERROR_RESULT(InvalidMeta, 4); + R_DEFINE_ERROR_RESULT(InvalidNso, 5); + R_DEFINE_ERROR_RESULT(InvalidPath, 6); + R_DEFINE_ERROR_RESULT(TooManyProcesses, 7); + R_DEFINE_ERROR_RESULT(NotPinned, 8); + R_DEFINE_ERROR_RESULT(InvalidProgramId, 9); + R_DEFINE_ERROR_RESULT(InvalidVersion, 10); + R_DEFINE_ERROR_RESULT(InvalidAcidSignature, 11); + R_DEFINE_ERROR_RESULT(InvalidNcaSignature, 12); + + R_DEFINE_ERROR_RESULT(InsufficientAddressSpace, 51); + R_DEFINE_ERROR_RESULT(InvalidNro, 52); + R_DEFINE_ERROR_RESULT(InvalidNrr, 53); + R_DEFINE_ERROR_RESULT(InvalidSignature, 54); + R_DEFINE_ERROR_RESULT(InsufficientNroRegistrations, 55); + R_DEFINE_ERROR_RESULT(InsufficientNrrRegistrations, 56); + R_DEFINE_ERROR_RESULT(NroAlreadyLoaded, 57); + + R_DEFINE_ERROR_RESULT(InvalidAddress, 81); + R_DEFINE_ERROR_RESULT(InvalidSize, 82); + R_DEFINE_ERROR_RESULT(NotLoaded, 84); + R_DEFINE_ERROR_RESULT(NotRegistered, 85); + R_DEFINE_ERROR_RESULT(InvalidSession, 86); + R_DEFINE_ERROR_RESULT(InvalidProcess, 87); + + R_DEFINE_ERROR_RESULT(UnknownCapability, 100); + R_DEFINE_ERROR_RESULT(InvalidCapabilityKernelFlags, 103); + R_DEFINE_ERROR_RESULT(InvalidCapabilitySyscallMask, 104); + R_DEFINE_ERROR_RESULT(InvalidCapabilityMapRange, 106); + R_DEFINE_ERROR_RESULT(InvalidCapabilityMapPage, 107); + R_DEFINE_ERROR_RESULT(InvalidCapabilityInterruptPair, 111); + R_DEFINE_ERROR_RESULT(InvalidCapabilityApplicationType, 113); + R_DEFINE_ERROR_RESULT(InvalidCapabilityKernelVersion, 114); + R_DEFINE_ERROR_RESULT(InvalidCapabilityHandleTable, 115); + R_DEFINE_ERROR_RESULT(InvalidCapabilityDebugFlags, 116); + + R_DEFINE_ERROR_RESULT(InternalError, 200); + +} diff --git a/lib/NintendoSDK/include/vapours/results/lr_results.hpp b/lib/NintendoSDK/include/vapours/results/lr_results.hpp new file mode 100644 index 00000000..7458730f --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/lr_results.hpp @@ -0,0 +1,35 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::lr { + + R_DEFINE_NAMESPACE_RESULT_MODULE(8); + + R_DEFINE_ERROR_RESULT(ProgramNotFound, 2); + R_DEFINE_ERROR_RESULT(DataNotFound, 3); + R_DEFINE_ERROR_RESULT(UnknownStorageId, 4); + R_DEFINE_ERROR_RESULT(HtmlDocumentNotFound, 6); + R_DEFINE_ERROR_RESULT(AddOnContentNotFound, 7); + R_DEFINE_ERROR_RESULT(ControlNotFound, 8); + R_DEFINE_ERROR_RESULT(LegalInformationNotFound, 9); + R_DEFINE_ERROR_RESULT(DebugProgramNotFound, 10); + + R_DEFINE_ERROR_RESULT(TooManyRegisteredPaths, 90); + +} diff --git a/lib/NintendoSDK/include/vapours/results/ncm_results.hpp b/lib/NintendoSDK/include/vapours/results/ncm_results.hpp new file mode 100644 index 00000000..a1885b39 --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/ncm_results.hpp @@ -0,0 +1,75 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::ncm { + + R_DEFINE_NAMESPACE_RESULT_MODULE(5); + + R_DEFINE_ERROR_RESULT(InvalidContentStorageBase, 1); + R_DEFINE_ERROR_RESULT(PlaceHolderAlreadyExists, 2); + R_DEFINE_ERROR_RESULT(PlaceHolderNotFound, 3); + R_DEFINE_ERROR_RESULT(ContentAlreadyExists, 4); + R_DEFINE_ERROR_RESULT(ContentNotFound, 5); + R_DEFINE_ERROR_RESULT(ContentMetaNotFound, 7); + R_DEFINE_ERROR_RESULT(AllocationFailed, 8); + R_DEFINE_ERROR_RESULT(UnknownStorage, 12); + + R_DEFINE_ERROR_RESULT(InvalidContentStorage, 100); + R_DEFINE_ERROR_RESULT(InvalidContentMetaDatabase, 110); + R_DEFINE_ERROR_RESULT(InvalidPackageFormat, 130); + R_DEFINE_ERROR_RESULT(InvalidContentHash, 140); + + R_DEFINE_ERROR_RESULT(InvalidInstallTaskState, 160); + R_DEFINE_ERROR_RESULT(InvalidPlaceHolderFile, 170); + R_DEFINE_ERROR_RESULT(BufferInsufficient, 180); + R_DEFINE_ERROR_RESULT(WriteToReadOnlyContentStorage, 190); + R_DEFINE_ERROR_RESULT(NotEnoughInstallSpace, 200); + R_DEFINE_ERROR_RESULT(SystemUpdateNotFoundInPackage, 210); + R_DEFINE_ERROR_RESULT(ContentInfoNotFound, 220); + R_DEFINE_ERROR_RESULT(DeltaNotFound, 237); + R_DEFINE_ERROR_RESULT(InvalidContentMetaKey, 240); + R_DEFINE_ERROR_RESULT(IgnorableInstallTicketFailure, 280); + + R_DEFINE_ERROR_RESULT(ContentStorageBaseNotFound, 310); + R_DEFINE_ERROR_RESULT(ListPartiallyNotCommitted, 330); + R_DEFINE_ERROR_RESULT(UnexpectedContentMetaPrepared, 360); + R_DEFINE_ERROR_RESULT(InvalidFirmwareVariation, 380); + + R_DEFINE_ERROR_RANGE(ContentStorageNotActive, 250, 258); + R_DEFINE_ERROR_RESULT(GameCardContentStorageNotActive, 251); + R_DEFINE_ERROR_RESULT(BuiltInSystemContentStorageNotActive, 252); + R_DEFINE_ERROR_RESULT(BuiltInUserContentStorageNotActive, 253); + R_DEFINE_ERROR_RESULT(SdCardContentStorageNotActive, 254); + R_DEFINE_ERROR_RESULT(UnknownContentStorageNotActive, 258); + + R_DEFINE_ERROR_RANGE(ContentMetaDatabaseNotActive, 260, 268); + R_DEFINE_ERROR_RESULT(GameCardContentMetaDatabaseNotActive, 261); + R_DEFINE_ERROR_RESULT(BuiltInSystemContentMetaDatabaseNotActive, 262); + R_DEFINE_ERROR_RESULT(BuiltInUserContentMetaDatabaseNotActive, 263); + R_DEFINE_ERROR_RESULT(SdCardContentMetaDatabaseNotActive, 264); + R_DEFINE_ERROR_RESULT(UnknownContentMetaDatabaseNotActive, 268); + + R_DEFINE_ERROR_RANGE(InstallTaskCancelled, 290, 299); + R_DEFINE_ERROR_RESULT(CreatePlaceHolderCancelled, 291); + R_DEFINE_ERROR_RESULT(WritePlaceHolderCancelled, 292); + + R_DEFINE_ERROR_RANGE(InvalidArgument, 8181, 8191); + R_DEFINE_ERROR_RESULT(InvalidOffset, 8182); + +} diff --git a/lib/NintendoSDK/include/vapours/results/nim_results.hpp b/lib/NintendoSDK/include/vapours/results/nim_results.hpp new file mode 100644 index 00000000..c0607726 --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/nim_results.hpp @@ -0,0 +1,26 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::nim { + + R_DEFINE_NAMESPACE_RESULT_MODULE(137); + + R_DEFINE_ERROR_RESULT(HttpConnectionCanceled, 70); + +} diff --git a/lib/NintendoSDK/include/vapours/results/ns_results.hpp b/lib/NintendoSDK/include/vapours/results/ns_results.hpp new file mode 100644 index 00000000..32f95422 --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/ns_results.hpp @@ -0,0 +1,31 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::ns { + + R_DEFINE_NAMESPACE_RESULT_MODULE(16); + + R_DEFINE_ERROR_RESULT(Canceled, 90); + R_DEFINE_ERROR_RESULT(OutOfMaxRunningTask, 110); + R_DEFINE_ERROR_RESULT(CardUpdateNotSetup, 270); + R_DEFINE_ERROR_RESULT(CardUpdateNotPrepared, 280); + R_DEFINE_ERROR_RESULT(CardUpdateAlreadySetup, 290); + R_DEFINE_ERROR_RESULT(PrepareCardUpdateAlreadyRequested, 460); + +} diff --git a/lib/NintendoSDK/include/vapours/results/os_results.hpp b/lib/NintendoSDK/include/vapours/results/os_results.hpp new file mode 100644 index 00000000..05479e26 --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/os_results.hpp @@ -0,0 +1,40 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::os { + + R_DEFINE_NAMESPACE_RESULT_MODULE(3); + + R_DEFINE_ERROR_RESULT(Busy, 4); + + R_DEFINE_ERROR_RESULT(OutOfMemory, 8); + R_DEFINE_ERROR_RESULT(OutOfResource, 9); + + R_DEFINE_ERROR_RESULT(OutOfVirtualAddressSpace, 12); + R_DEFINE_ERROR_RESULT(ResourceLimit, 13); + + R_DEFINE_ERROR_RESULT(OutOfHandles, 500); + R_DEFINE_ERROR_RESULT(InvalidHandle, 501); + R_DEFINE_ERROR_RESULT(InvalidCurrentMemoryState, 502); + R_DEFINE_ERROR_RESULT(InvalidTransferMemoryState, 503); + R_DEFINE_ERROR_RESULT(InvalidTransferMemorySize, 504); + R_DEFINE_ERROR_RESULT(OutOfTransferMemory, 505); + R_DEFINE_ERROR_RESULT(OutOfAddressSpace, 506); + +} diff --git a/lib/NintendoSDK/include/vapours/results/pgl_results.hpp b/lib/NintendoSDK/include/vapours/results/pgl_results.hpp new file mode 100644 index 00000000..93e4eb1a --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/pgl_results.hpp @@ -0,0 +1,30 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::pgl { + + R_DEFINE_NAMESPACE_RESULT_MODULE(228); + + R_DEFINE_ERROR_RESULT(NotAvailable, 2); + R_DEFINE_ERROR_RESULT(ApplicationNotRunning, 3); + R_DEFINE_ERROR_RESULT(BufferNotEnough, 4); + R_DEFINE_ERROR_RESULT(ApplicationContentNotFound, 5); + R_DEFINE_ERROR_RESULT(ContentMetaNotFound, 6); + +} diff --git a/lib/NintendoSDK/include/vapours/results/pm_results.hpp b/lib/NintendoSDK/include/vapours/results/pm_results.hpp new file mode 100644 index 00000000..84d7dfc1 --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/pm_results.hpp @@ -0,0 +1,31 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::pm { + + R_DEFINE_NAMESPACE_RESULT_MODULE(15); + + R_DEFINE_ERROR_RESULT(ProcessNotFound, 1); + R_DEFINE_ERROR_RESULT(AlreadyStarted, 2); + R_DEFINE_ERROR_RESULT(NotTerminated, 3); + R_DEFINE_ERROR_RESULT(DebugHookInUse, 4); + R_DEFINE_ERROR_RESULT(ApplicationRunning, 5); + R_DEFINE_ERROR_RESULT(InvalidSize, 6); + +} diff --git a/lib/NintendoSDK/include/vapours/results/psc_results.hpp b/lib/NintendoSDK/include/vapours/results/psc_results.hpp new file mode 100644 index 00000000..883e1b32 --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/psc_results.hpp @@ -0,0 +1,27 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::psc { + + R_DEFINE_NAMESPACE_RESULT_MODULE(138); + + R_DEFINE_ERROR_RESULT(AlreadyInitialized, 2); + R_DEFINE_ERROR_RESULT(NotInitialized, 3); + +} diff --git a/lib/NintendoSDK/include/vapours/results/results_common.hpp b/lib/NintendoSDK/include/vapours/results/results_common.hpp new file mode 100644 index 00000000..fe0b716e --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/results_common.hpp @@ -0,0 +1,196 @@ +#pragma once +#include +#include +#include + +namespace nn { + + namespace result::detail { + + class ResultTraits { + public: + using BaseType = std::uint32_t; + static const BaseType SuccessValue = BaseType(); + static const int ModuleBits = 9; + static const int DescriptionBits = 13; + static const int ReservedBits = 10; + static_assert(ModuleBits + DescriptionBits + ReservedBits == sizeof(BaseType) * CHAR_BIT, "ModuleBits + DescriptionBits + ReservedBits == sizeof(BaseType) * CHAR_BIT"); + private: + static BaseType GetBitsValue(BaseType v, int ofs, int num) noexcept { + return (v >> ofs) & ~(~BaseType() << num); + } + public: + template + struct MakeInnerValueStatic : public std::integral_constant { + static_assert(M < (1 << ModuleBits), "Invalid Module"); + static_assert(D < (1 << DescriptionBits), "Invalid Description"); + }; + + static BaseType MakeInnerValue(int m, int d) noexcept { + return (static_cast(m) << 0) | (static_cast(d) << ModuleBits); + } + + static BaseType GetModuleFromValue(BaseType value) noexcept { + return GetBitsValue(value, 0, ModuleBits); + } + + static BaseType GetDescriptionFromValue(BaseType value) noexcept { + return GetBitsValue(value, ModuleBits, DescriptionBits); + } + }; + + /* Use CRTP for Results. */ + template + class ResultBase { + public: + using BaseType = typename ResultTraits::BaseType; + static const BaseType SuccessValue = ResultTraits::SuccessValue; + + int GetModule() const noexcept { + return static_cast(ResultTraits::GetModuleFromValue(static_cast(*this).GetInnerValueForDebug())); + } + + int GetDescription() const noexcept { + return static_cast(ResultTraits::GetDescriptionFromValue(static_cast(*this).GetInnerValueForDebug())); + } + }; + + class ResultInternalAccessor; + + } + + class ResultSuccess; + + class Result : public result::detail::ResultBase { + friend class result::detail::ResultInternalAccessor; + private: + using Base = typename result::detail::ResultBase; + private: + BaseType m_value; + private: + explicit Result(BaseType v) noexcept : m_value(v) { /* ... */ } + public: + Result() noexcept { /* ... */ } + + BaseType GetInnerValueForDebug() const noexcept { return m_value; } + + bool IsSuccess() const noexcept { return m_value == SuccessValue; } + bool IsFailure() const noexcept { return !IsSuccess(); } + + operator ResultSuccess() const noexcept; + static bool CanAccept(Result result) noexcept; + + int GetModule() const noexcept { return Base::GetModule(); } + int GetDescription() const noexcept { return Base::GetDescription(); } + }; + static_assert(sizeof(Result) == sizeof(result::detail::ResultTraits::BaseType), "sizeof(Result) == sizeof(detail::ResultTraits::BaseType)"); + static_assert(std::is_trivially_destructible::value, "std::is_trivially_destructible::value"); + + inline bool Result::CanAccept(Result result) noexcept { + (void)(result); + return true; + } + + namespace result::detail { + + class ResultInternalAccessor { + public: + static Result ConstructResult(ResultTraits::BaseType v) noexcept { return Result(v); } + }; + + inline Result ConstructResult(ResultTraits::BaseType v) noexcept { return ResultInternalAccessor::ConstructResult(v); } + + } + + class ResultSuccess : public result::detail::ResultBase { + public: + using Base = typename result::detail::ResultBase; + public: + operator Result() const noexcept { return result::detail::ConstructResult(SuccessValue); } + + BaseType GetInnerValueForDebug() const noexcept { return SuccessValue; } + + bool IsSuccess() const noexcept { return true; } + + static bool CanAccept(Result result) noexcept { return result.IsSuccess(); } + + int GetModule() const noexcept { return Base::GetModule(); } + int GetDescription() const noexcept { return Base::GetDescription(); } + }; + + namespace result::detail { + + __attribute__((noreturn)) void OnUnhandledResult(Result result) noexcept; + + } + + inline Result::operator ResultSuccess() const noexcept { + if (!ResultSuccess::CanAccept(*this)) { + result::detail::OnUnhandledResult(*this); + } + return ResultSuccess(); + } + + namespace result::detail { + + template + class ErrorResultBase : public ResultBase> { + private: + using Base = ResultBase>; + public: + static constexpr int Module = Module_; + static constexpr int Description = Description_; + static constexpr typename Base::BaseType InnerValue = ResultTraits::MakeInnerValueStatic::value; + static_assert(InnerValue != Base::SuccessValue, "InnerValue != Base::SuccessValue"); + public: + operator Result() const noexcept { return ConstructResult(InnerValue); } + operator ResultSuccess() const noexcept { OnUnhandledResult(*this); } + + bool IsSuccess() const noexcept { return false; } + + typename Base::BaseType GetInnerValueForDebug() const noexcept { return InnerValue; } + }; + + template + class ErrorRange { + public: + static const int Module = Module_; + static const int DescriptionStart = DescStart; + static const int DescriptionEnd = DescEnd; + static_assert(DescriptionStart < DescriptionEnd, "DescriptionStart < DescriptionEnd"); + public: + static bool Includes(Result result) noexcept { + return result.GetModule() == Module && DescriptionStart <= result.GetDescription() && result.GetDescription() < DescriptionEnd; + } + + friend bool operator <=(Result result, ErrorRange) noexcept { + return Includes(result); + } + }; + + } + +} + +/* Macros for defining new results. */ +#define R_DEFINE_NAMESPACE_RESULT_MODULE(value) namespace detail::result { using ResultModuleId = std::integral_constant; } +#define R_CURRENT_NAMESPACE_RESULT_MODULE detail::result::ResultModuleId::value +#define R_NAMESPACE_MODULE_ID(nmspc) nmspc::R_CURRENT_NAMESPACE_RESULT_MODULE + +#define R_DEFINE_ERROR_RESULT_IMPL(name, desc_start, desc_end) \ + class Result##name : \ + public ::nn::result::detail::ErrorResultBase, \ + public ::nn::result::detail::ErrorRange \ + {} + +#define R_DEFINE_ABSTRACT_ERROR_RESULT_IMPL(name, desc_start, desc_end) \ + class Result##name : \ + public ::nn::result::detail::ErrorRange \ + {} + + +#define R_DEFINE_ERROR_RESULT(name, desc) R_DEFINE_ERROR_RESULT_IMPL(name, desc, desc) +#define R_DEFINE_ERROR_RANGE(name, start, end) R_DEFINE_ERROR_RESULT_IMPL(name, start, end) + +#define R_DEFINE_ABSTRACT_ERROR_RESULT(name, desc) R_DEFINE_ABSTRACT_ERROR_RESULT_IMPL(name, desc, desc) +#define R_DEFINE_ABSTRACT_ERROR_RANGE(name, start, end) R_DEFINE_ABSTRACT_ERROR_RESULT_IMPL(name, start, end) diff --git a/lib/NintendoSDK/include/vapours/results/ro_results.hpp b/lib/NintendoSDK/include/vapours/results/ro_results.hpp new file mode 100644 index 00000000..fc4dbe16 --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/ro_results.hpp @@ -0,0 +1,45 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::ro { + + R_DEFINE_NAMESPACE_RESULT_MODULE(22); + + R_DEFINE_ERROR_RANGE(RoError, 1, 1023); + R_DEFINE_ERROR_RESULT(OutOfAddressSpace, 2); + R_DEFINE_ERROR_RESULT(AlreadyLoaded, 3); + R_DEFINE_ERROR_RESULT(InvalidNro, 4); + + R_DEFINE_ERROR_RESULT(InvalidNrr, 6); + R_DEFINE_ERROR_RESULT(TooManyNro, 7); + R_DEFINE_ERROR_RESULT(TooManyNrr, 8); + R_DEFINE_ERROR_RESULT(NotAuthorized, 9); + R_DEFINE_ERROR_RESULT(InvalidNrrType, 10); + + R_DEFINE_ERROR_RESULT(InternalError, 1023); + + R_DEFINE_ERROR_RESULT(InvalidAddress, 1025); + R_DEFINE_ERROR_RESULT(InvalidSize, 1026); + + R_DEFINE_ERROR_RESULT(NotLoaded, 1028); + R_DEFINE_ERROR_RESULT(NotRegistered, 1029); + R_DEFINE_ERROR_RESULT(InvalidSession, 1030); + R_DEFINE_ERROR_RESULT(InvalidProcess, 1031); + +} diff --git a/lib/NintendoSDK/include/vapours/results/settings_results.hpp b/lib/NintendoSDK/include/vapours/results/settings_results.hpp new file mode 100644 index 00000000..e704371b --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/settings_results.hpp @@ -0,0 +1,47 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::settings { + + R_DEFINE_NAMESPACE_RESULT_MODULE(105); + + R_DEFINE_ERROR_RESULT(SettingsItemNotFound, 11); + + R_DEFINE_ERROR_RANGE(InternalError, 100, 149); + R_DEFINE_ERROR_RESULT(SettingsItemKeyAllocationFailed, 101); + R_DEFINE_ERROR_RESULT(SettingsItemValueAllocationFailed, 102); + + R_DEFINE_ERROR_RANGE(InvalidArgument, 200, 399); + R_DEFINE_ERROR_RESULT(SettingsNameNull, 201); + R_DEFINE_ERROR_RESULT(SettingsItemKeyNull, 202); + R_DEFINE_ERROR_RESULT(SettingsItemValueNull, 203); + R_DEFINE_ERROR_RESULT(SettingsItemKeyBufferNull, 204); + R_DEFINE_ERROR_RESULT(SettingsItemValueBufferNull, 205); + + R_DEFINE_ERROR_RESULT(SettingsNameEmpty, 221); + R_DEFINE_ERROR_RESULT(SettingsItemKeyEmpty, 222); + + R_DEFINE_ERROR_RESULT(SettingsNameTooLong, 241); + R_DEFINE_ERROR_RESULT(SettingsItemKeyTooLong, 242); + + R_DEFINE_ERROR_RESULT(SettingsNameInvalidFormat, 261); + R_DEFINE_ERROR_RESULT(SettingsItemKeyInvalidFormat, 262); + R_DEFINE_ERROR_RESULT(SettingsItemValueInvalidFormat, 263); + +} diff --git a/lib/NintendoSDK/include/vapours/results/sf_results.hpp b/lib/NintendoSDK/include/vapours/results/sf_results.hpp new file mode 100644 index 00000000..516cb24c --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/sf_results.hpp @@ -0,0 +1,54 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::sf { + + R_DEFINE_NAMESPACE_RESULT_MODULE(10); + + R_DEFINE_ERROR_RESULT(NotSupported, 1); + R_DEFINE_ERROR_RESULT(PreconditionViolation, 3); + + namespace cmif { + + R_DEFINE_ERROR_RESULT(InvalidHeaderSize, 202); + R_DEFINE_ERROR_RESULT(InvalidInHeader, 211); + R_DEFINE_ERROR_RESULT(UnknownCommandId, 221); + R_DEFINE_ERROR_RESULT(InvalidOutRawSize, 232); + R_DEFINE_ERROR_RESULT(InvalidNumInObjects, 235); + R_DEFINE_ERROR_RESULT(InvalidNumOutObjects, 236); + R_DEFINE_ERROR_RESULT(InvalidInObject, 239); + + R_DEFINE_ERROR_RESULT(TargetNotFound, 261); + + R_DEFINE_ERROR_RESULT(OutOfDomainEntries, 301); + + } + + namespace impl { + + R_DEFINE_ABSTRACT_ERROR_RANGE(RequestContextChanged, 800, 899); + R_DEFINE_ABSTRACT_ERROR_RANGE(RequestInvalidated, 801, 809); + R_DEFINE_ERROR_RESULT(RequestInvalidatedByUser, 802); + + } + + R_DEFINE_ABSTRACT_ERROR_RANGE(RequestDeferred, 811, 819); + R_DEFINE_ERROR_RESULT(RequestDeferredByUser, 812); + +} diff --git a/lib/NintendoSDK/include/vapours/results/sm_results.hpp b/lib/NintendoSDK/include/vapours/results/sm_results.hpp new file mode 100644 index 00000000..45d93498 --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/sm_results.hpp @@ -0,0 +1,42 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::sm { + + R_DEFINE_NAMESPACE_RESULT_MODULE(21); + + R_DEFINE_ERROR_RESULT(OutOfProcesses, 1); + R_DEFINE_ERROR_RESULT(InvalidClient, 2); + R_DEFINE_ERROR_RESULT(OutOfSessions, 3); + R_DEFINE_ERROR_RESULT(AlreadyRegistered, 4); + R_DEFINE_ERROR_RESULT(OutOfServices, 5); + R_DEFINE_ERROR_RESULT(InvalidServiceName, 6); + R_DEFINE_ERROR_RESULT(NotRegistered, 7); + R_DEFINE_ERROR_RESULT(NotAllowed, 8); + R_DEFINE_ERROR_RESULT(TooLargeAccessControl, 9); + + /* Results 1000-2000 used as extension for Atmosphere Mitm. */ + namespace mitm { + + R_DEFINE_ERROR_RESULT(ShouldForwardToSession, 1000); + R_DEFINE_ERROR_RESULT(ProcessNotAssociated, 1100); + + } + +} diff --git a/lib/NintendoSDK/include/vapours/results/spl_results.hpp b/lib/NintendoSDK/include/vapours/results/spl_results.hpp new file mode 100644 index 00000000..f8d857e1 --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/spl_results.hpp @@ -0,0 +1,43 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::spl { + + R_DEFINE_NAMESPACE_RESULT_MODULE(26); + + R_DEFINE_ERROR_RANGE(SecureMonitorError, 0, 99); + R_DEFINE_ERROR_RESULT(SecureMonitorNotImplemented, 1); + R_DEFINE_ERROR_RESULT(SecureMonitorInvalidArgument, 2); + R_DEFINE_ERROR_RESULT(SecureMonitorBusy, 3); + R_DEFINE_ERROR_RESULT(SecureMonitorNoAsyncOperation, 4); + R_DEFINE_ERROR_RESULT(SecureMonitorInvalidAsyncOperation, 5); + R_DEFINE_ERROR_RESULT(SecureMonitorNotPermitted, 6); + R_DEFINE_ERROR_RESULT(SecureMonitorNotInitialized, 7); + + R_DEFINE_ERROR_RESULT(InvalidSize, 100); + R_DEFINE_ERROR_RESULT(UnknownSecureMonitorError, 101); + R_DEFINE_ERROR_RESULT(DecryptionFailed, 102); + + R_DEFINE_ERROR_RESULT(OutOfKeySlots, 104); + R_DEFINE_ERROR_RESULT(InvalidKeySlot, 105); + R_DEFINE_ERROR_RESULT(BootReasonAlreadySet, 106); + R_DEFINE_ERROR_RESULT(BootReasonNotSet, 107); + R_DEFINE_ERROR_RESULT(InvalidArgument, 108); + +} diff --git a/lib/NintendoSDK/include/vapours/results/svc_results.hpp b/lib/NintendoSDK/include/vapours/results/svc_results.hpp new file mode 100644 index 00000000..e73beb86 --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/svc_results.hpp @@ -0,0 +1,81 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::svc { + + R_DEFINE_NAMESPACE_RESULT_MODULE(1); + + R_DEFINE_ERROR_RESULT(OutOfSessions, 7); + + R_DEFINE_ERROR_RESULT(InvalidArgument, 14); + + R_DEFINE_ERROR_RESULT(NotImplemented, 33); + + R_DEFINE_ERROR_RESULT(StopProcessingException, 54); + + R_DEFINE_ERROR_RESULT(NoSynchronizationObject, 57); + + R_DEFINE_ERROR_RESULT(TerminationRequested, 59); + + R_DEFINE_ERROR_RESULT(NoEvent, 70); + + R_DEFINE_ERROR_RESULT(InvalidSize, 101); + R_DEFINE_ERROR_RESULT(InvalidAddress, 102); + R_DEFINE_ERROR_RESULT(OutOfResource, 103); + R_DEFINE_ERROR_RESULT(OutOfMemory, 104); + R_DEFINE_ERROR_RESULT(OutOfHandles, 105); + R_DEFINE_ERROR_RESULT(InvalidCurrentMemory, 106); + + R_DEFINE_ERROR_RESULT(InvalidNewMemoryPermission, 108); + + R_DEFINE_ERROR_RESULT(InvalidMemoryRegion, 110); + + R_DEFINE_ERROR_RESULT(InvalidPriority, 112); + R_DEFINE_ERROR_RESULT(InvalidCoreId, 113); + R_DEFINE_ERROR_RESULT(InvalidHandle, 114); + R_DEFINE_ERROR_RESULT(InvalidPointer, 115); + R_DEFINE_ERROR_RESULT(InvalidCombination, 116); + R_DEFINE_ERROR_RESULT(TimedOut, 117); + R_DEFINE_ERROR_RESULT(Cancelled, 118); + R_DEFINE_ERROR_RESULT(OutOfRange, 119); + R_DEFINE_ERROR_RESULT(InvalidEnumValue, 120); + R_DEFINE_ERROR_RESULT(NotFound, 121); + R_DEFINE_ERROR_RESULT(Busy, 122); + R_DEFINE_ERROR_RESULT(SessionClosed, 123); + R_DEFINE_ERROR_RESULT(NotHandled, 124); + R_DEFINE_ERROR_RESULT(InvalidState, 125); + R_DEFINE_ERROR_RESULT(ReservedUsed, 126); + R_DEFINE_ERROR_RESULT(NotSupported, 127); + R_DEFINE_ERROR_RESULT(Debug, 128); + R_DEFINE_ERROR_RESULT(NoThread, 129); + R_DEFINE_ERROR_RESULT(UnknownThread, 130); + R_DEFINE_ERROR_RESULT(PortClosed, 131); + R_DEFINE_ERROR_RESULT(LimitReached, 132); + R_DEFINE_ERROR_RESULT(InvalidMemoryPool, 133); + + R_DEFINE_ERROR_RESULT(ReceiveListBroken, 258); + R_DEFINE_ERROR_RESULT(OutOfAddressSpace, 259); + R_DEFINE_ERROR_RESULT(MessageTooLarge, 260); + + R_DEFINE_ERROR_RESULT(InvalidProcessId, 517); + R_DEFINE_ERROR_RESULT(InvalidThreadId, 518); + R_DEFINE_ERROR_RESULT(InvalidId, 519); + R_DEFINE_ERROR_RESULT(ProcessTerminated, 520); + +} diff --git a/lib/NintendoSDK/include/vapours/results/time_results.hpp b/lib/NintendoSDK/include/vapours/results/time_results.hpp new file mode 100644 index 00000000..f82e0556 --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/time_results.hpp @@ -0,0 +1,32 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::time { + + R_DEFINE_NAMESPACE_RESULT_MODULE(116); + + R_DEFINE_ERROR_RESULT(NotInitialized, 0); + + R_DEFINE_ERROR_RESULT(NotComparable, 200); + R_DEFINE_ERROR_RESULT(Overflowed, 201); + + R_DEFINE_ABSTRACT_ERROR_RANGE(InvalidArgument, 900, 919); + R_DEFINE_ERROR_RESULT(InvalidPointer, 901); + +} diff --git a/lib/NintendoSDK/include/vapours/results/updater_results.hpp b/lib/NintendoSDK/include/vapours/results/updater_results.hpp new file mode 100644 index 00000000..ec0f0fde --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/updater_results.hpp @@ -0,0 +1,30 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::updater { + + R_DEFINE_NAMESPACE_RESULT_MODULE(158); + + R_DEFINE_ERROR_RESULT(BootImagePackageNotFound, 2); + R_DEFINE_ERROR_RESULT(InvalidBootImagePackage, 3); + R_DEFINE_ERROR_RESULT(TooSmallWorkBuffer, 4); + R_DEFINE_ERROR_RESULT(NotAlignedWorkBuffer, 5); + R_DEFINE_ERROR_RESULT(NeedsRepairBootImages, 6); + +} diff --git a/lib/NintendoSDK/include/vapours/results/vi_results.hpp b/lib/NintendoSDK/include/vapours/results/vi_results.hpp new file mode 100644 index 00000000..833bdd5e --- /dev/null +++ b/lib/NintendoSDK/include/vapours/results/vi_results.hpp @@ -0,0 +1,28 @@ +/* + * 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 . + */ + +#pragma once +#include + +namespace ams::vi { + + R_DEFINE_NAMESPACE_RESULT_MODULE(114); + + R_DEFINE_ERROR_RESULT(OperationFailed, 1); + R_DEFINE_ERROR_RESULT(NotSupported, 6); + R_DEFINE_ERROR_RESULT(NotFound, 7); + +} diff --git a/lib/NintendoSDK/modules/nvn/nvnInit.cpp b/lib/NintendoSDK/modules/nvn/nvnInit.cpp new file mode 100644 index 00000000..72aebcae --- /dev/null +++ b/lib/NintendoSDK/modules/nvn/nvnInit.cpp @@ -0,0 +1,1194 @@ +#include + +extern "C" { +void nvnLoadCProcs(const NVNdevice* device, nvnDeviceGetProcAddressFunction deviceGetProcAddress) { + pfnc_nvnDeviceBuilderSetDefaults = (nvnDeviceBuilderSetDefaultsFunction)deviceGetProcAddress( + device, "nvnDeviceBuilderSetDefaults"); + pfnc_nvnDeviceBuilderSetFlags = + (nvnDeviceBuilderSetFlagsFunction)deviceGetProcAddress(device, "nvnDeviceBuilderSetFlags"); + pfnc_nvnDeviceInitialize = + (nvnDeviceInitializeFunction)deviceGetProcAddress(device, "nvnDeviceInitialize"); + pfnc_nvnDeviceFinalize = + (nvnDeviceFinalizeFunction)deviceGetProcAddress(device, "nvnDeviceFinalize"); + pfnc_nvnDeviceSetDebugLabel = + (nvnDeviceSetDebugLabelFunction)deviceGetProcAddress(device, "nvnDeviceSetDebugLabel"); + pfnc_nvnDeviceGetProcAddress = + (nvnDeviceGetProcAddressFunction)deviceGetProcAddress(device, "nvnDeviceGetProcAddress"); + pfnc_nvnDeviceGetInteger = + (nvnDeviceGetIntegerFunction)deviceGetProcAddress(device, "nvnDeviceGetInteger"); + pfnc_nvnDeviceGetCurrentTimestampInNanoseconds = + (nvnDeviceGetCurrentTimestampInNanosecondsFunction)deviceGetProcAddress( + device, "nvnDeviceGetCurrentTimestampInNanoseconds"); + pfnc_nvnDeviceSetIntermediateShaderCache = + (nvnDeviceSetIntermediateShaderCacheFunction)deviceGetProcAddress( + device, "nvnDeviceSetIntermediateShaderCache"); + pfnc_nvnDeviceGetTextureHandle = (nvnDeviceGetTextureHandleFunction)deviceGetProcAddress( + device, "nvnDeviceGetTextureHandle"); + pfnc_nvnDeviceGetTexelFetchHandle = (nvnDeviceGetTexelFetchHandleFunction)deviceGetProcAddress( + device, "nvnDeviceGetTexelFetchHandle"); + pfnc_nvnDeviceGetImageHandle = + (nvnDeviceGetImageHandleFunction)deviceGetProcAddress(device, "nvnDeviceGetImageHandle"); + pfnc_nvnDeviceInstallDebugCallback = + (nvnDeviceInstallDebugCallbackFunction)deviceGetProcAddress( + device, "nvnDeviceInstallDebugCallback"); + pfnc_nvnDeviceGenerateDebugDomainId = + (nvnDeviceGenerateDebugDomainIdFunction)deviceGetProcAddress( + device, "nvnDeviceGenerateDebugDomainId"); + pfnc_nvnDeviceSetWindowOriginMode = (nvnDeviceSetWindowOriginModeFunction)deviceGetProcAddress( + device, "nvnDeviceSetWindowOriginMode"); + pfnc_nvnDeviceSetDepthMode = + (nvnDeviceSetDepthModeFunction)deviceGetProcAddress(device, "nvnDeviceSetDepthMode"); + pfnc_nvnDeviceRegisterFastClearColor = + (nvnDeviceRegisterFastClearColorFunction)deviceGetProcAddress( + device, "nvnDeviceRegisterFastClearColor"); + pfnc_nvnDeviceRegisterFastClearColori = + (nvnDeviceRegisterFastClearColoriFunction)deviceGetProcAddress( + device, "nvnDeviceRegisterFastClearColori"); + pfnc_nvnDeviceRegisterFastClearColorui = + (nvnDeviceRegisterFastClearColoruiFunction)deviceGetProcAddress( + device, "nvnDeviceRegisterFastClearColorui"); + pfnc_nvnDeviceRegisterFastClearDepth = + (nvnDeviceRegisterFastClearDepthFunction)deviceGetProcAddress( + device, "nvnDeviceRegisterFastClearDepth"); + pfnc_nvnDeviceGetWindowOriginMode = (nvnDeviceGetWindowOriginModeFunction)deviceGetProcAddress( + device, "nvnDeviceGetWindowOriginMode"); + pfnc_nvnDeviceGetDepthMode = + (nvnDeviceGetDepthModeFunction)deviceGetProcAddress(device, "nvnDeviceGetDepthMode"); + pfnc_nvnDeviceGetTimestampInNanoseconds = + (nvnDeviceGetTimestampInNanosecondsFunction)deviceGetProcAddress( + device, "nvnDeviceGetTimestampInNanoseconds"); + pfnc_nvnDeviceApplyDeferredFinalizes = + (nvnDeviceApplyDeferredFinalizesFunction)deviceGetProcAddress( + device, "nvnDeviceApplyDeferredFinalizes"); + pfnc_nvnDeviceFinalizeCommandHandle = + (nvnDeviceFinalizeCommandHandleFunction)deviceGetProcAddress( + device, "nvnDeviceFinalizeCommandHandle"); + pfnc_nvnDeviceWalkDebugDatabase = (nvnDeviceWalkDebugDatabaseFunction)deviceGetProcAddress( + device, "nvnDeviceWalkDebugDatabase"); + pfnc_nvnDeviceGetSeparateTextureHandle = + (nvnDeviceGetSeparateTextureHandleFunction)deviceGetProcAddress( + device, "nvnDeviceGetSeparateTextureHandle"); + pfnc_nvnDeviceGetSeparateSamplerHandle = + (nvnDeviceGetSeparateSamplerHandleFunction)deviceGetProcAddress( + device, "nvnDeviceGetSeparateSamplerHandle"); + pfnc_nvnDeviceIsExternalDebuggerAttached = + (nvnDeviceIsExternalDebuggerAttachedFunction)deviceGetProcAddress( + device, "nvnDeviceIsExternalDebuggerAttached"); + pfnc_nvnQueueGetError = + (nvnQueueGetErrorFunction)deviceGetProcAddress(device, "nvnQueueGetError"); + pfnc_nvnQueueGetTotalCommandMemoryUsed = + (nvnQueueGetTotalCommandMemoryUsedFunction)deviceGetProcAddress( + device, "nvnQueueGetTotalCommandMemoryUsed"); + pfnc_nvnQueueGetTotalControlMemoryUsed = + (nvnQueueGetTotalControlMemoryUsedFunction)deviceGetProcAddress( + device, "nvnQueueGetTotalControlMemoryUsed"); + pfnc_nvnQueueGetTotalComputeMemoryUsed = + (nvnQueueGetTotalComputeMemoryUsedFunction)deviceGetProcAddress( + device, "nvnQueueGetTotalComputeMemoryUsed"); + pfnc_nvnQueueResetMemoryUsageCounts = + (nvnQueueResetMemoryUsageCountsFunction)deviceGetProcAddress( + device, "nvnQueueResetMemoryUsageCounts"); + pfnc_nvnQueueBuilderSetDevice = + (nvnQueueBuilderSetDeviceFunction)deviceGetProcAddress(device, "nvnQueueBuilderSetDevice"); + pfnc_nvnQueueBuilderSetDefaults = (nvnQueueBuilderSetDefaultsFunction)deviceGetProcAddress( + device, "nvnQueueBuilderSetDefaults"); + pfnc_nvnQueueBuilderSetFlags = + (nvnQueueBuilderSetFlagsFunction)deviceGetProcAddress(device, "nvnQueueBuilderSetFlags"); + pfnc_nvnQueueBuilderSetCommandMemorySize = + (nvnQueueBuilderSetCommandMemorySizeFunction)deviceGetProcAddress( + device, "nvnQueueBuilderSetCommandMemorySize"); + pfnc_nvnQueueBuilderSetComputeMemorySize = + (nvnQueueBuilderSetComputeMemorySizeFunction)deviceGetProcAddress( + device, "nvnQueueBuilderSetComputeMemorySize"); + pfnc_nvnQueueBuilderSetControlMemorySize = + (nvnQueueBuilderSetControlMemorySizeFunction)deviceGetProcAddress( + device, "nvnQueueBuilderSetControlMemorySize"); + pfnc_nvnQueueBuilderGetQueueMemorySize = + (nvnQueueBuilderGetQueueMemorySizeFunction)deviceGetProcAddress( + device, "nvnQueueBuilderGetQueueMemorySize"); + pfnc_nvnQueueBuilderSetQueueMemory = + (nvnQueueBuilderSetQueueMemoryFunction)deviceGetProcAddress( + device, "nvnQueueBuilderSetQueueMemory"); + pfnc_nvnQueueBuilderSetCommandFlushThreshold = + (nvnQueueBuilderSetCommandFlushThresholdFunction)deviceGetProcAddress( + device, "nvnQueueBuilderSetCommandFlushThreshold"); + pfnc_nvnQueueInitialize = + (nvnQueueInitializeFunction)deviceGetProcAddress(device, "nvnQueueInitialize"); + pfnc_nvnQueueFinalize = + (nvnQueueFinalizeFunction)deviceGetProcAddress(device, "nvnQueueFinalize"); + pfnc_nvnQueueSetDebugLabel = + (nvnQueueSetDebugLabelFunction)deviceGetProcAddress(device, "nvnQueueSetDebugLabel"); + pfnc_nvnQueueSubmitCommands = + (nvnQueueSubmitCommandsFunction)deviceGetProcAddress(device, "nvnQueueSubmitCommands"); + pfnc_nvnQueueFlush = (nvnQueueFlushFunction)deviceGetProcAddress(device, "nvnQueueFlush"); + pfnc_nvnQueueFinish = (nvnQueueFinishFunction)deviceGetProcAddress(device, "nvnQueueFinish"); + pfnc_nvnQueuePresentTexture = + (nvnQueuePresentTextureFunction)deviceGetProcAddress(device, "nvnQueuePresentTexture"); + pfnc_nvnQueueAcquireTexture = + (nvnQueueAcquireTextureFunction)deviceGetProcAddress(device, "nvnQueueAcquireTexture"); + pfnc_nvnWindowBuilderSetDevice = (nvnWindowBuilderSetDeviceFunction)deviceGetProcAddress( + device, "nvnWindowBuilderSetDevice"); + pfnc_nvnWindowBuilderSetDefaults = (nvnWindowBuilderSetDefaultsFunction)deviceGetProcAddress( + device, "nvnWindowBuilderSetDefaults"); + pfnc_nvnWindowBuilderSetNativeWindow = + (nvnWindowBuilderSetNativeWindowFunction)deviceGetProcAddress( + device, "nvnWindowBuilderSetNativeWindow"); + pfnc_nvnWindowBuilderSetTextures = (nvnWindowBuilderSetTexturesFunction)deviceGetProcAddress( + device, "nvnWindowBuilderSetTextures"); + pfnc_nvnWindowBuilderSetPresentInterval = + (nvnWindowBuilderSetPresentIntervalFunction)deviceGetProcAddress( + device, "nvnWindowBuilderSetPresentInterval"); + pfnc_nvnWindowBuilderGetNativeWindow = + (nvnWindowBuilderGetNativeWindowFunction)deviceGetProcAddress( + device, "nvnWindowBuilderGetNativeWindow"); + pfnc_nvnWindowBuilderGetPresentInterval = + (nvnWindowBuilderGetPresentIntervalFunction)deviceGetProcAddress( + device, "nvnWindowBuilderGetPresentInterval"); + pfnc_nvnWindowInitialize = + (nvnWindowInitializeFunction)deviceGetProcAddress(device, "nvnWindowInitialize"); + pfnc_nvnWindowFinalize = + (nvnWindowFinalizeFunction)deviceGetProcAddress(device, "nvnWindowFinalize"); + pfnc_nvnWindowSetDebugLabel = + (nvnWindowSetDebugLabelFunction)deviceGetProcAddress(device, "nvnWindowSetDebugLabel"); + pfnc_nvnWindowAcquireTexture = + (nvnWindowAcquireTextureFunction)deviceGetProcAddress(device, "nvnWindowAcquireTexture"); + pfnc_nvnWindowGetNativeWindow = + (nvnWindowGetNativeWindowFunction)deviceGetProcAddress(device, "nvnWindowGetNativeWindow"); + pfnc_nvnWindowGetPresentInterval = (nvnWindowGetPresentIntervalFunction)deviceGetProcAddress( + device, "nvnWindowGetPresentInterval"); + pfnc_nvnWindowSetPresentInterval = (nvnWindowSetPresentIntervalFunction)deviceGetProcAddress( + device, "nvnWindowSetPresentInterval"); + pfnc_nvnWindowSetCrop = + (nvnWindowSetCropFunction)deviceGetProcAddress(device, "nvnWindowSetCrop"); + pfnc_nvnWindowGetCrop = + (nvnWindowGetCropFunction)deviceGetProcAddress(device, "nvnWindowGetCrop"); + pfnc_nvnProgramInitialize = + (nvnProgramInitializeFunction)deviceGetProcAddress(device, "nvnProgramInitialize"); + pfnc_nvnProgramFinalize = + (nvnProgramFinalizeFunction)deviceGetProcAddress(device, "nvnProgramFinalize"); + pfnc_nvnProgramSetDebugLabel = + (nvnProgramSetDebugLabelFunction)deviceGetProcAddress(device, "nvnProgramSetDebugLabel"); + pfnc_nvnProgramSetShaders = + (nvnProgramSetShadersFunction)deviceGetProcAddress(device, "nvnProgramSetShaders"); + pfnc_nvnMemoryPoolBuilderSetDevice = + (nvnMemoryPoolBuilderSetDeviceFunction)deviceGetProcAddress( + device, "nvnMemoryPoolBuilderSetDevice"); + pfnc_nvnMemoryPoolBuilderSetDefaults = + (nvnMemoryPoolBuilderSetDefaultsFunction)deviceGetProcAddress( + device, "nvnMemoryPoolBuilderSetDefaults"); + pfnc_nvnMemoryPoolBuilderSetStorage = + (nvnMemoryPoolBuilderSetStorageFunction)deviceGetProcAddress( + device, "nvnMemoryPoolBuilderSetStorage"); + pfnc_nvnMemoryPoolBuilderSetFlags = (nvnMemoryPoolBuilderSetFlagsFunction)deviceGetProcAddress( + device, "nvnMemoryPoolBuilderSetFlags"); + pfnc_nvnMemoryPoolBuilderGetMemory = + (nvnMemoryPoolBuilderGetMemoryFunction)deviceGetProcAddress( + device, "nvnMemoryPoolBuilderGetMemory"); + pfnc_nvnMemoryPoolBuilderGetSize = (nvnMemoryPoolBuilderGetSizeFunction)deviceGetProcAddress( + device, "nvnMemoryPoolBuilderGetSize"); + pfnc_nvnMemoryPoolBuilderGetFlags = (nvnMemoryPoolBuilderGetFlagsFunction)deviceGetProcAddress( + device, "nvnMemoryPoolBuilderGetFlags"); + pfnc_nvnMemoryPoolInitialize = + (nvnMemoryPoolInitializeFunction)deviceGetProcAddress(device, "nvnMemoryPoolInitialize"); + pfnc_nvnMemoryPoolSetDebugLabel = (nvnMemoryPoolSetDebugLabelFunction)deviceGetProcAddress( + device, "nvnMemoryPoolSetDebugLabel"); + pfnc_nvnMemoryPoolFinalize = + (nvnMemoryPoolFinalizeFunction)deviceGetProcAddress(device, "nvnMemoryPoolFinalize"); + pfnc_nvnMemoryPoolMap = + (nvnMemoryPoolMapFunction)deviceGetProcAddress(device, "nvnMemoryPoolMap"); + pfnc_nvnMemoryPoolFlushMappedRange = + (nvnMemoryPoolFlushMappedRangeFunction)deviceGetProcAddress( + device, "nvnMemoryPoolFlushMappedRange"); + pfnc_nvnMemoryPoolInvalidateMappedRange = + (nvnMemoryPoolInvalidateMappedRangeFunction)deviceGetProcAddress( + device, "nvnMemoryPoolInvalidateMappedRange"); + pfnc_nvnMemoryPoolGetBufferAddress = + (nvnMemoryPoolGetBufferAddressFunction)deviceGetProcAddress( + device, "nvnMemoryPoolGetBufferAddress"); + pfnc_nvnMemoryPoolMapVirtual = + (nvnMemoryPoolMapVirtualFunction)deviceGetProcAddress(device, "nvnMemoryPoolMapVirtual"); + pfnc_nvnMemoryPoolGetSize = + (nvnMemoryPoolGetSizeFunction)deviceGetProcAddress(device, "nvnMemoryPoolGetSize"); + pfnc_nvnMemoryPoolGetFlags = + (nvnMemoryPoolGetFlagsFunction)deviceGetProcAddress(device, "nvnMemoryPoolGetFlags"); + pfnc_nvnTexturePoolInitialize = + (nvnTexturePoolInitializeFunction)deviceGetProcAddress(device, "nvnTexturePoolInitialize"); + pfnc_nvnTexturePoolSetDebugLabel = (nvnTexturePoolSetDebugLabelFunction)deviceGetProcAddress( + device, "nvnTexturePoolSetDebugLabel"); + pfnc_nvnTexturePoolFinalize = + (nvnTexturePoolFinalizeFunction)deviceGetProcAddress(device, "nvnTexturePoolFinalize"); + pfnc_nvnTexturePoolRegisterTexture = + (nvnTexturePoolRegisterTextureFunction)deviceGetProcAddress( + device, "nvnTexturePoolRegisterTexture"); + pfnc_nvnTexturePoolRegisterImage = (nvnTexturePoolRegisterImageFunction)deviceGetProcAddress( + device, "nvnTexturePoolRegisterImage"); + pfnc_nvnTexturePoolGetMemoryPool = (nvnTexturePoolGetMemoryPoolFunction)deviceGetProcAddress( + device, "nvnTexturePoolGetMemoryPool"); + pfnc_nvnTexturePoolGetMemoryOffset = + (nvnTexturePoolGetMemoryOffsetFunction)deviceGetProcAddress( + device, "nvnTexturePoolGetMemoryOffset"); + pfnc_nvnTexturePoolGetSize = + (nvnTexturePoolGetSizeFunction)deviceGetProcAddress(device, "nvnTexturePoolGetSize"); + pfnc_nvnSamplerPoolInitialize = + (nvnSamplerPoolInitializeFunction)deviceGetProcAddress(device, "nvnSamplerPoolInitialize"); + pfnc_nvnSamplerPoolSetDebugLabel = (nvnSamplerPoolSetDebugLabelFunction)deviceGetProcAddress( + device, "nvnSamplerPoolSetDebugLabel"); + pfnc_nvnSamplerPoolFinalize = + (nvnSamplerPoolFinalizeFunction)deviceGetProcAddress(device, "nvnSamplerPoolFinalize"); + pfnc_nvnSamplerPoolRegisterSampler = + (nvnSamplerPoolRegisterSamplerFunction)deviceGetProcAddress( + device, "nvnSamplerPoolRegisterSampler"); + pfnc_nvnSamplerPoolRegisterSamplerBuilder = + (nvnSamplerPoolRegisterSamplerBuilderFunction)deviceGetProcAddress( + device, "nvnSamplerPoolRegisterSamplerBuilder"); + pfnc_nvnSamplerPoolGetMemoryPool = (nvnSamplerPoolGetMemoryPoolFunction)deviceGetProcAddress( + device, "nvnSamplerPoolGetMemoryPool"); + pfnc_nvnSamplerPoolGetMemoryOffset = + (nvnSamplerPoolGetMemoryOffsetFunction)deviceGetProcAddress( + device, "nvnSamplerPoolGetMemoryOffset"); + pfnc_nvnSamplerPoolGetSize = + (nvnSamplerPoolGetSizeFunction)deviceGetProcAddress(device, "nvnSamplerPoolGetSize"); + pfnc_nvnBufferBuilderSetDevice = (nvnBufferBuilderSetDeviceFunction)deviceGetProcAddress( + device, "nvnBufferBuilderSetDevice"); + pfnc_nvnBufferBuilderSetDefaults = (nvnBufferBuilderSetDefaultsFunction)deviceGetProcAddress( + device, "nvnBufferBuilderSetDefaults"); + pfnc_nvnBufferBuilderSetStorage = (nvnBufferBuilderSetStorageFunction)deviceGetProcAddress( + device, "nvnBufferBuilderSetStorage"); + pfnc_nvnBufferBuilderGetMemoryPool = + (nvnBufferBuilderGetMemoryPoolFunction)deviceGetProcAddress( + device, "nvnBufferBuilderGetMemoryPool"); + pfnc_nvnBufferBuilderGetMemoryOffset = + (nvnBufferBuilderGetMemoryOffsetFunction)deviceGetProcAddress( + device, "nvnBufferBuilderGetMemoryOffset"); + pfnc_nvnBufferBuilderGetSize = + (nvnBufferBuilderGetSizeFunction)deviceGetProcAddress(device, "nvnBufferBuilderGetSize"); + pfnc_nvnBufferInitialize = + (nvnBufferInitializeFunction)deviceGetProcAddress(device, "nvnBufferInitialize"); + pfnc_nvnBufferSetDebugLabel = + (nvnBufferSetDebugLabelFunction)deviceGetProcAddress(device, "nvnBufferSetDebugLabel"); + pfnc_nvnBufferFinalize = + (nvnBufferFinalizeFunction)deviceGetProcAddress(device, "nvnBufferFinalize"); + pfnc_nvnBufferMap = (nvnBufferMapFunction)deviceGetProcAddress(device, "nvnBufferMap"); + pfnc_nvnBufferGetAddress = + (nvnBufferGetAddressFunction)deviceGetProcAddress(device, "nvnBufferGetAddress"); + pfnc_nvnBufferFlushMappedRange = (nvnBufferFlushMappedRangeFunction)deviceGetProcAddress( + device, "nvnBufferFlushMappedRange"); + pfnc_nvnBufferInvalidateMappedRange = + (nvnBufferInvalidateMappedRangeFunction)deviceGetProcAddress( + device, "nvnBufferInvalidateMappedRange"); + pfnc_nvnBufferGetMemoryPool = + (nvnBufferGetMemoryPoolFunction)deviceGetProcAddress(device, "nvnBufferGetMemoryPool"); + pfnc_nvnBufferGetMemoryOffset = + (nvnBufferGetMemoryOffsetFunction)deviceGetProcAddress(device, "nvnBufferGetMemoryOffset"); + pfnc_nvnBufferGetSize = + (nvnBufferGetSizeFunction)deviceGetProcAddress(device, "nvnBufferGetSize"); + pfnc_nvnBufferGetDebugID = + (nvnBufferGetDebugIDFunction)deviceGetProcAddress(device, "nvnBufferGetDebugID"); + pfnc_nvnTextureBuilderSetDevice = (nvnTextureBuilderSetDeviceFunction)deviceGetProcAddress( + device, "nvnTextureBuilderSetDevice"); + pfnc_nvnTextureBuilderSetDefaults = (nvnTextureBuilderSetDefaultsFunction)deviceGetProcAddress( + device, "nvnTextureBuilderSetDefaults"); + pfnc_nvnTextureBuilderSetFlags = (nvnTextureBuilderSetFlagsFunction)deviceGetProcAddress( + device, "nvnTextureBuilderSetFlags"); + pfnc_nvnTextureBuilderSetTarget = (nvnTextureBuilderSetTargetFunction)deviceGetProcAddress( + device, "nvnTextureBuilderSetTarget"); + pfnc_nvnTextureBuilderSetWidth = (nvnTextureBuilderSetWidthFunction)deviceGetProcAddress( + device, "nvnTextureBuilderSetWidth"); + pfnc_nvnTextureBuilderSetHeight = (nvnTextureBuilderSetHeightFunction)deviceGetProcAddress( + device, "nvnTextureBuilderSetHeight"); + pfnc_nvnTextureBuilderSetDepth = (nvnTextureBuilderSetDepthFunction)deviceGetProcAddress( + device, "nvnTextureBuilderSetDepth"); + pfnc_nvnTextureBuilderSetSize1D = (nvnTextureBuilderSetSize1DFunction)deviceGetProcAddress( + device, "nvnTextureBuilderSetSize1D"); + pfnc_nvnTextureBuilderSetSize2D = (nvnTextureBuilderSetSize2DFunction)deviceGetProcAddress( + device, "nvnTextureBuilderSetSize2D"); + pfnc_nvnTextureBuilderSetSize3D = (nvnTextureBuilderSetSize3DFunction)deviceGetProcAddress( + device, "nvnTextureBuilderSetSize3D"); + pfnc_nvnTextureBuilderSetLevels = (nvnTextureBuilderSetLevelsFunction)deviceGetProcAddress( + device, "nvnTextureBuilderSetLevels"); + pfnc_nvnTextureBuilderSetFormat = (nvnTextureBuilderSetFormatFunction)deviceGetProcAddress( + device, "nvnTextureBuilderSetFormat"); + pfnc_nvnTextureBuilderSetSamples = (nvnTextureBuilderSetSamplesFunction)deviceGetProcAddress( + device, "nvnTextureBuilderSetSamples"); + pfnc_nvnTextureBuilderSetSwizzle = (nvnTextureBuilderSetSwizzleFunction)deviceGetProcAddress( + device, "nvnTextureBuilderSetSwizzle"); + pfnc_nvnTextureBuilderSetDepthStencilMode = + (nvnTextureBuilderSetDepthStencilModeFunction)deviceGetProcAddress( + device, "nvnTextureBuilderSetDepthStencilMode"); + pfnc_nvnTextureBuilderGetStorageSize = + (nvnTextureBuilderGetStorageSizeFunction)deviceGetProcAddress( + device, "nvnTextureBuilderGetStorageSize"); + pfnc_nvnTextureBuilderGetStorageAlignment = + (nvnTextureBuilderGetStorageAlignmentFunction)deviceGetProcAddress( + device, "nvnTextureBuilderGetStorageAlignment"); + pfnc_nvnTextureBuilderSetStorage = (nvnTextureBuilderSetStorageFunction)deviceGetProcAddress( + device, "nvnTextureBuilderSetStorage"); + pfnc_nvnTextureBuilderSetPackagedTextureData = + (nvnTextureBuilderSetPackagedTextureDataFunction)deviceGetProcAddress( + device, "nvnTextureBuilderSetPackagedTextureData"); + pfnc_nvnTextureBuilderSetPackagedTextureLayout = + (nvnTextureBuilderSetPackagedTextureLayoutFunction)deviceGetProcAddress( + device, "nvnTextureBuilderSetPackagedTextureLayout"); + pfnc_nvnTextureBuilderSetStride = (nvnTextureBuilderSetStrideFunction)deviceGetProcAddress( + device, "nvnTextureBuilderSetStride"); + pfnc_nvnTextureBuilderSetGLTextureName = + (nvnTextureBuilderSetGLTextureNameFunction)deviceGetProcAddress( + device, "nvnTextureBuilderSetGLTextureName"); + pfnc_nvnTextureBuilderGetStorageClass = + (nvnTextureBuilderGetStorageClassFunction)deviceGetProcAddress( + device, "nvnTextureBuilderGetStorageClass"); + pfnc_nvnTextureBuilderGetFlags = (nvnTextureBuilderGetFlagsFunction)deviceGetProcAddress( + device, "nvnTextureBuilderGetFlags"); + pfnc_nvnTextureBuilderGetTarget = (nvnTextureBuilderGetTargetFunction)deviceGetProcAddress( + device, "nvnTextureBuilderGetTarget"); + pfnc_nvnTextureBuilderGetWidth = (nvnTextureBuilderGetWidthFunction)deviceGetProcAddress( + device, "nvnTextureBuilderGetWidth"); + pfnc_nvnTextureBuilderGetHeight = (nvnTextureBuilderGetHeightFunction)deviceGetProcAddress( + device, "nvnTextureBuilderGetHeight"); + pfnc_nvnTextureBuilderGetDepth = (nvnTextureBuilderGetDepthFunction)deviceGetProcAddress( + device, "nvnTextureBuilderGetDepth"); + pfnc_nvnTextureBuilderGetLevels = (nvnTextureBuilderGetLevelsFunction)deviceGetProcAddress( + device, "nvnTextureBuilderGetLevels"); + pfnc_nvnTextureBuilderGetFormat = (nvnTextureBuilderGetFormatFunction)deviceGetProcAddress( + device, "nvnTextureBuilderGetFormat"); + pfnc_nvnTextureBuilderGetSamples = (nvnTextureBuilderGetSamplesFunction)deviceGetProcAddress( + device, "nvnTextureBuilderGetSamples"); + pfnc_nvnTextureBuilderGetSwizzle = (nvnTextureBuilderGetSwizzleFunction)deviceGetProcAddress( + device, "nvnTextureBuilderGetSwizzle"); + pfnc_nvnTextureBuilderGetDepthStencilMode = + (nvnTextureBuilderGetDepthStencilModeFunction)deviceGetProcAddress( + device, "nvnTextureBuilderGetDepthStencilMode"); + pfnc_nvnTextureBuilderGetPackagedTextureData = + (nvnTextureBuilderGetPackagedTextureDataFunction)deviceGetProcAddress( + device, "nvnTextureBuilderGetPackagedTextureData"); + pfnc_nvnTextureBuilderGetStride = (nvnTextureBuilderGetStrideFunction)deviceGetProcAddress( + device, "nvnTextureBuilderGetStride"); + pfnc_nvnTextureBuilderGetSparseTileLayout = + (nvnTextureBuilderGetSparseTileLayoutFunction)deviceGetProcAddress( + device, "nvnTextureBuilderGetSparseTileLayout"); + pfnc_nvnTextureBuilderGetGLTextureName = + (nvnTextureBuilderGetGLTextureNameFunction)deviceGetProcAddress( + device, "nvnTextureBuilderGetGLTextureName"); + pfnc_nvnTextureBuilderGetZCullStorageSize = + (nvnTextureBuilderGetZCullStorageSizeFunction)deviceGetProcAddress( + device, "nvnTextureBuilderGetZCullStorageSize"); + pfnc_nvnTextureBuilderGetMemoryPool = + (nvnTextureBuilderGetMemoryPoolFunction)deviceGetProcAddress( + device, "nvnTextureBuilderGetMemoryPool"); + pfnc_nvnTextureBuilderGetMemoryOffset = + (nvnTextureBuilderGetMemoryOffsetFunction)deviceGetProcAddress( + device, "nvnTextureBuilderGetMemoryOffset"); + pfnc_nvnTextureViewSetDefaults = (nvnTextureViewSetDefaultsFunction)deviceGetProcAddress( + device, "nvnTextureViewSetDefaults"); + pfnc_nvnTextureViewSetLevels = + (nvnTextureViewSetLevelsFunction)deviceGetProcAddress(device, "nvnTextureViewSetLevels"); + pfnc_nvnTextureViewSetLayers = + (nvnTextureViewSetLayersFunction)deviceGetProcAddress(device, "nvnTextureViewSetLayers"); + pfnc_nvnTextureViewSetFormat = + (nvnTextureViewSetFormatFunction)deviceGetProcAddress(device, "nvnTextureViewSetFormat"); + pfnc_nvnTextureViewSetSwizzle = + (nvnTextureViewSetSwizzleFunction)deviceGetProcAddress(device, "nvnTextureViewSetSwizzle"); + pfnc_nvnTextureViewSetDepthStencilMode = + (nvnTextureViewSetDepthStencilModeFunction)deviceGetProcAddress( + device, "nvnTextureViewSetDepthStencilMode"); + pfnc_nvnTextureViewSetTarget = + (nvnTextureViewSetTargetFunction)deviceGetProcAddress(device, "nvnTextureViewSetTarget"); + pfnc_nvnTextureViewGetLevels = + (nvnTextureViewGetLevelsFunction)deviceGetProcAddress(device, "nvnTextureViewGetLevels"); + pfnc_nvnTextureViewGetLayers = + (nvnTextureViewGetLayersFunction)deviceGetProcAddress(device, "nvnTextureViewGetLayers"); + pfnc_nvnTextureViewGetFormat = + (nvnTextureViewGetFormatFunction)deviceGetProcAddress(device, "nvnTextureViewGetFormat"); + pfnc_nvnTextureViewGetSwizzle = + (nvnTextureViewGetSwizzleFunction)deviceGetProcAddress(device, "nvnTextureViewGetSwizzle"); + pfnc_nvnTextureViewGetDepthStencilMode = + (nvnTextureViewGetDepthStencilModeFunction)deviceGetProcAddress( + device, "nvnTextureViewGetDepthStencilMode"); + pfnc_nvnTextureViewGetTarget = + (nvnTextureViewGetTargetFunction)deviceGetProcAddress(device, "nvnTextureViewGetTarget"); + pfnc_nvnTextureViewCompare = + (nvnTextureViewCompareFunction)deviceGetProcAddress(device, "nvnTextureViewCompare"); + pfnc_nvnTextureInitialize = + (nvnTextureInitializeFunction)deviceGetProcAddress(device, "nvnTextureInitialize"); + pfnc_nvnTextureGetZCullStorageSize = + (nvnTextureGetZCullStorageSizeFunction)deviceGetProcAddress( + device, "nvnTextureGetZCullStorageSize"); + pfnc_nvnTextureFinalize = + (nvnTextureFinalizeFunction)deviceGetProcAddress(device, "nvnTextureFinalize"); + pfnc_nvnTextureSetDebugLabel = + (nvnTextureSetDebugLabelFunction)deviceGetProcAddress(device, "nvnTextureSetDebugLabel"); + pfnc_nvnTextureGetStorageClass = (nvnTextureGetStorageClassFunction)deviceGetProcAddress( + device, "nvnTextureGetStorageClass"); + pfnc_nvnTextureGetViewOffset = + (nvnTextureGetViewOffsetFunction)deviceGetProcAddress(device, "nvnTextureGetViewOffset"); + pfnc_nvnTextureGetFlags = + (nvnTextureGetFlagsFunction)deviceGetProcAddress(device, "nvnTextureGetFlags"); + pfnc_nvnTextureGetTarget = + (nvnTextureGetTargetFunction)deviceGetProcAddress(device, "nvnTextureGetTarget"); + pfnc_nvnTextureGetWidth = + (nvnTextureGetWidthFunction)deviceGetProcAddress(device, "nvnTextureGetWidth"); + pfnc_nvnTextureGetHeight = + (nvnTextureGetHeightFunction)deviceGetProcAddress(device, "nvnTextureGetHeight"); + pfnc_nvnTextureGetDepth = + (nvnTextureGetDepthFunction)deviceGetProcAddress(device, "nvnTextureGetDepth"); + pfnc_nvnTextureGetLevels = + (nvnTextureGetLevelsFunction)deviceGetProcAddress(device, "nvnTextureGetLevels"); + pfnc_nvnTextureGetFormat = + (nvnTextureGetFormatFunction)deviceGetProcAddress(device, "nvnTextureGetFormat"); + pfnc_nvnTextureGetSamples = + (nvnTextureGetSamplesFunction)deviceGetProcAddress(device, "nvnTextureGetSamples"); + pfnc_nvnTextureGetSwizzle = + (nvnTextureGetSwizzleFunction)deviceGetProcAddress(device, "nvnTextureGetSwizzle"); + pfnc_nvnTextureGetDepthStencilMode = + (nvnTextureGetDepthStencilModeFunction)deviceGetProcAddress( + device, "nvnTextureGetDepthStencilMode"); + pfnc_nvnTextureGetStride = + (nvnTextureGetStrideFunction)deviceGetProcAddress(device, "nvnTextureGetStride"); + pfnc_nvnTextureGetTextureAddress = (nvnTextureGetTextureAddressFunction)deviceGetProcAddress( + device, "nvnTextureGetTextureAddress"); + pfnc_nvnTextureGetSparseTileLayout = + (nvnTextureGetSparseTileLayoutFunction)deviceGetProcAddress( + device, "nvnTextureGetSparseTileLayout"); + pfnc_nvnTextureWriteTexels = + (nvnTextureWriteTexelsFunction)deviceGetProcAddress(device, "nvnTextureWriteTexels"); + pfnc_nvnTextureWriteTexelsStrided = (nvnTextureWriteTexelsStridedFunction)deviceGetProcAddress( + device, "nvnTextureWriteTexelsStrided"); + pfnc_nvnTextureReadTexels = + (nvnTextureReadTexelsFunction)deviceGetProcAddress(device, "nvnTextureReadTexels"); + pfnc_nvnTextureReadTexelsStrided = (nvnTextureReadTexelsStridedFunction)deviceGetProcAddress( + device, "nvnTextureReadTexelsStrided"); + pfnc_nvnTextureFlushTexels = + (nvnTextureFlushTexelsFunction)deviceGetProcAddress(device, "nvnTextureFlushTexels"); + pfnc_nvnTextureInvalidateTexels = (nvnTextureInvalidateTexelsFunction)deviceGetProcAddress( + device, "nvnTextureInvalidateTexels"); + pfnc_nvnTextureGetMemoryPool = + (nvnTextureGetMemoryPoolFunction)deviceGetProcAddress(device, "nvnTextureGetMemoryPool"); + pfnc_nvnTextureGetMemoryOffset = (nvnTextureGetMemoryOffsetFunction)deviceGetProcAddress( + device, "nvnTextureGetMemoryOffset"); + pfnc_nvnTextureGetStorageSize = + (nvnTextureGetStorageSizeFunction)deviceGetProcAddress(device, "nvnTextureGetStorageSize"); + pfnc_nvnTextureCompare = + (nvnTextureCompareFunction)deviceGetProcAddress(device, "nvnTextureCompare"); + pfnc_nvnTextureGetDebugID = + (nvnTextureGetDebugIDFunction)deviceGetProcAddress(device, "nvnTextureGetDebugID"); + pfnc_nvnSamplerBuilderSetDevice = (nvnSamplerBuilderSetDeviceFunction)deviceGetProcAddress( + device, "nvnSamplerBuilderSetDevice"); + pfnc_nvnSamplerBuilderSetDefaults = (nvnSamplerBuilderSetDefaultsFunction)deviceGetProcAddress( + device, "nvnSamplerBuilderSetDefaults"); + pfnc_nvnSamplerBuilderSetMinMagFilter = + (nvnSamplerBuilderSetMinMagFilterFunction)deviceGetProcAddress( + device, "nvnSamplerBuilderSetMinMagFilter"); + pfnc_nvnSamplerBuilderSetWrapMode = (nvnSamplerBuilderSetWrapModeFunction)deviceGetProcAddress( + device, "nvnSamplerBuilderSetWrapMode"); + pfnc_nvnSamplerBuilderSetLodClamp = (nvnSamplerBuilderSetLodClampFunction)deviceGetProcAddress( + device, "nvnSamplerBuilderSetLodClamp"); + pfnc_nvnSamplerBuilderSetLodBias = (nvnSamplerBuilderSetLodBiasFunction)deviceGetProcAddress( + device, "nvnSamplerBuilderSetLodBias"); + pfnc_nvnSamplerBuilderSetCompare = (nvnSamplerBuilderSetCompareFunction)deviceGetProcAddress( + device, "nvnSamplerBuilderSetCompare"); + pfnc_nvnSamplerBuilderSetBorderColor = + (nvnSamplerBuilderSetBorderColorFunction)deviceGetProcAddress( + device, "nvnSamplerBuilderSetBorderColor"); + pfnc_nvnSamplerBuilderSetBorderColori = + (nvnSamplerBuilderSetBorderColoriFunction)deviceGetProcAddress( + device, "nvnSamplerBuilderSetBorderColori"); + pfnc_nvnSamplerBuilderSetBorderColorui = + (nvnSamplerBuilderSetBorderColoruiFunction)deviceGetProcAddress( + device, "nvnSamplerBuilderSetBorderColorui"); + pfnc_nvnSamplerBuilderSetMaxAnisotropy = + (nvnSamplerBuilderSetMaxAnisotropyFunction)deviceGetProcAddress( + device, "nvnSamplerBuilderSetMaxAnisotropy"); + pfnc_nvnSamplerBuilderSetReductionFilter = + (nvnSamplerBuilderSetReductionFilterFunction)deviceGetProcAddress( + device, "nvnSamplerBuilderSetReductionFilter"); + pfnc_nvnSamplerBuilderSetLodSnap = (nvnSamplerBuilderSetLodSnapFunction)deviceGetProcAddress( + device, "nvnSamplerBuilderSetLodSnap"); + pfnc_nvnSamplerBuilderGetMinMagFilter = + (nvnSamplerBuilderGetMinMagFilterFunction)deviceGetProcAddress( + device, "nvnSamplerBuilderGetMinMagFilter"); + pfnc_nvnSamplerBuilderGetWrapMode = (nvnSamplerBuilderGetWrapModeFunction)deviceGetProcAddress( + device, "nvnSamplerBuilderGetWrapMode"); + pfnc_nvnSamplerBuilderGetLodClamp = (nvnSamplerBuilderGetLodClampFunction)deviceGetProcAddress( + device, "nvnSamplerBuilderGetLodClamp"); + pfnc_nvnSamplerBuilderGetLodBias = (nvnSamplerBuilderGetLodBiasFunction)deviceGetProcAddress( + device, "nvnSamplerBuilderGetLodBias"); + pfnc_nvnSamplerBuilderGetCompare = (nvnSamplerBuilderGetCompareFunction)deviceGetProcAddress( + device, "nvnSamplerBuilderGetCompare"); + pfnc_nvnSamplerBuilderGetBorderColor = + (nvnSamplerBuilderGetBorderColorFunction)deviceGetProcAddress( + device, "nvnSamplerBuilderGetBorderColor"); + pfnc_nvnSamplerBuilderGetBorderColori = + (nvnSamplerBuilderGetBorderColoriFunction)deviceGetProcAddress( + device, "nvnSamplerBuilderGetBorderColori"); + pfnc_nvnSamplerBuilderGetBorderColorui = + (nvnSamplerBuilderGetBorderColoruiFunction)deviceGetProcAddress( + device, "nvnSamplerBuilderGetBorderColorui"); + pfnc_nvnSamplerBuilderGetMaxAnisotropy = + (nvnSamplerBuilderGetMaxAnisotropyFunction)deviceGetProcAddress( + device, "nvnSamplerBuilderGetMaxAnisotropy"); + pfnc_nvnSamplerBuilderGetReductionFilter = + (nvnSamplerBuilderGetReductionFilterFunction)deviceGetProcAddress( + device, "nvnSamplerBuilderGetReductionFilter"); + pfnc_nvnSamplerBuilderGetLodSnap = (nvnSamplerBuilderGetLodSnapFunction)deviceGetProcAddress( + device, "nvnSamplerBuilderGetLodSnap"); + pfnc_nvnSamplerInitialize = + (nvnSamplerInitializeFunction)deviceGetProcAddress(device, "nvnSamplerInitialize"); + pfnc_nvnSamplerFinalize = + (nvnSamplerFinalizeFunction)deviceGetProcAddress(device, "nvnSamplerFinalize"); + pfnc_nvnSamplerSetDebugLabel = + (nvnSamplerSetDebugLabelFunction)deviceGetProcAddress(device, "nvnSamplerSetDebugLabel"); + pfnc_nvnSamplerGetMinMagFilter = (nvnSamplerGetMinMagFilterFunction)deviceGetProcAddress( + device, "nvnSamplerGetMinMagFilter"); + pfnc_nvnSamplerGetWrapMode = + (nvnSamplerGetWrapModeFunction)deviceGetProcAddress(device, "nvnSamplerGetWrapMode"); + pfnc_nvnSamplerGetLodClamp = + (nvnSamplerGetLodClampFunction)deviceGetProcAddress(device, "nvnSamplerGetLodClamp"); + pfnc_nvnSamplerGetLodBias = + (nvnSamplerGetLodBiasFunction)deviceGetProcAddress(device, "nvnSamplerGetLodBias"); + pfnc_nvnSamplerGetCompare = + (nvnSamplerGetCompareFunction)deviceGetProcAddress(device, "nvnSamplerGetCompare"); + pfnc_nvnSamplerGetBorderColor = + (nvnSamplerGetBorderColorFunction)deviceGetProcAddress(device, "nvnSamplerGetBorderColor"); + pfnc_nvnSamplerGetBorderColori = (nvnSamplerGetBorderColoriFunction)deviceGetProcAddress( + device, "nvnSamplerGetBorderColori"); + pfnc_nvnSamplerGetBorderColorui = (nvnSamplerGetBorderColoruiFunction)deviceGetProcAddress( + device, "nvnSamplerGetBorderColorui"); + pfnc_nvnSamplerGetMaxAnisotropy = (nvnSamplerGetMaxAnisotropyFunction)deviceGetProcAddress( + device, "nvnSamplerGetMaxAnisotropy"); + pfnc_nvnSamplerGetReductionFilter = (nvnSamplerGetReductionFilterFunction)deviceGetProcAddress( + device, "nvnSamplerGetReductionFilter"); + pfnc_nvnSamplerCompare = + (nvnSamplerCompareFunction)deviceGetProcAddress(device, "nvnSamplerCompare"); + pfnc_nvnSamplerGetDebugID = + (nvnSamplerGetDebugIDFunction)deviceGetProcAddress(device, "nvnSamplerGetDebugID"); + pfnc_nvnBlendStateSetDefaults = + (nvnBlendStateSetDefaultsFunction)deviceGetProcAddress(device, "nvnBlendStateSetDefaults"); + pfnc_nvnBlendStateSetBlendTarget = (nvnBlendStateSetBlendTargetFunction)deviceGetProcAddress( + device, "nvnBlendStateSetBlendTarget"); + pfnc_nvnBlendStateSetBlendFunc = (nvnBlendStateSetBlendFuncFunction)deviceGetProcAddress( + device, "nvnBlendStateSetBlendFunc"); + pfnc_nvnBlendStateSetBlendEquation = + (nvnBlendStateSetBlendEquationFunction)deviceGetProcAddress( + device, "nvnBlendStateSetBlendEquation"); + pfnc_nvnBlendStateSetAdvancedMode = (nvnBlendStateSetAdvancedModeFunction)deviceGetProcAddress( + device, "nvnBlendStateSetAdvancedMode"); + pfnc_nvnBlendStateSetAdvancedOverlap = + (nvnBlendStateSetAdvancedOverlapFunction)deviceGetProcAddress( + device, "nvnBlendStateSetAdvancedOverlap"); + pfnc_nvnBlendStateSetAdvancedPremultipliedSrc = + (nvnBlendStateSetAdvancedPremultipliedSrcFunction)deviceGetProcAddress( + device, "nvnBlendStateSetAdvancedPremultipliedSrc"); + pfnc_nvnBlendStateSetAdvancedNormalizedDst = + (nvnBlendStateSetAdvancedNormalizedDstFunction)deviceGetProcAddress( + device, "nvnBlendStateSetAdvancedNormalizedDst"); + pfnc_nvnBlendStateGetBlendTarget = (nvnBlendStateGetBlendTargetFunction)deviceGetProcAddress( + device, "nvnBlendStateGetBlendTarget"); + pfnc_nvnBlendStateGetBlendFunc = (nvnBlendStateGetBlendFuncFunction)deviceGetProcAddress( + device, "nvnBlendStateGetBlendFunc"); + pfnc_nvnBlendStateGetBlendEquation = + (nvnBlendStateGetBlendEquationFunction)deviceGetProcAddress( + device, "nvnBlendStateGetBlendEquation"); + pfnc_nvnBlendStateGetAdvancedMode = (nvnBlendStateGetAdvancedModeFunction)deviceGetProcAddress( + device, "nvnBlendStateGetAdvancedMode"); + pfnc_nvnBlendStateGetAdvancedOverlap = + (nvnBlendStateGetAdvancedOverlapFunction)deviceGetProcAddress( + device, "nvnBlendStateGetAdvancedOverlap"); + pfnc_nvnBlendStateGetAdvancedPremultipliedSrc = + (nvnBlendStateGetAdvancedPremultipliedSrcFunction)deviceGetProcAddress( + device, "nvnBlendStateGetAdvancedPremultipliedSrc"); + pfnc_nvnBlendStateGetAdvancedNormalizedDst = + (nvnBlendStateGetAdvancedNormalizedDstFunction)deviceGetProcAddress( + device, "nvnBlendStateGetAdvancedNormalizedDst"); + pfnc_nvnColorStateSetDefaults = + (nvnColorStateSetDefaultsFunction)deviceGetProcAddress(device, "nvnColorStateSetDefaults"); + pfnc_nvnColorStateSetBlendEnable = (nvnColorStateSetBlendEnableFunction)deviceGetProcAddress( + device, "nvnColorStateSetBlendEnable"); + pfnc_nvnColorStateSetLogicOp = + (nvnColorStateSetLogicOpFunction)deviceGetProcAddress(device, "nvnColorStateSetLogicOp"); + pfnc_nvnColorStateSetAlphaTest = (nvnColorStateSetAlphaTestFunction)deviceGetProcAddress( + device, "nvnColorStateSetAlphaTest"); + pfnc_nvnColorStateGetBlendEnable = (nvnColorStateGetBlendEnableFunction)deviceGetProcAddress( + device, "nvnColorStateGetBlendEnable"); + pfnc_nvnColorStateGetLogicOp = + (nvnColorStateGetLogicOpFunction)deviceGetProcAddress(device, "nvnColorStateGetLogicOp"); + pfnc_nvnColorStateGetAlphaTest = (nvnColorStateGetAlphaTestFunction)deviceGetProcAddress( + device, "nvnColorStateGetAlphaTest"); + pfnc_nvnChannelMaskStateSetDefaults = + (nvnChannelMaskStateSetDefaultsFunction)deviceGetProcAddress( + device, "nvnChannelMaskStateSetDefaults"); + pfnc_nvnChannelMaskStateSetChannelMask = + (nvnChannelMaskStateSetChannelMaskFunction)deviceGetProcAddress( + device, "nvnChannelMaskStateSetChannelMask"); + pfnc_nvnChannelMaskStateGetChannelMask = + (nvnChannelMaskStateGetChannelMaskFunction)deviceGetProcAddress( + device, "nvnChannelMaskStateGetChannelMask"); + pfnc_nvnMultisampleStateSetDefaults = + (nvnMultisampleStateSetDefaultsFunction)deviceGetProcAddress( + device, "nvnMultisampleStateSetDefaults"); + pfnc_nvnMultisampleStateSetMultisampleEnable = + (nvnMultisampleStateSetMultisampleEnableFunction)deviceGetProcAddress( + device, "nvnMultisampleStateSetMultisampleEnable"); + pfnc_nvnMultisampleStateSetSamples = + (nvnMultisampleStateSetSamplesFunction)deviceGetProcAddress( + device, "nvnMultisampleStateSetSamples"); + pfnc_nvnMultisampleStateSetAlphaToCoverageEnable = + (nvnMultisampleStateSetAlphaToCoverageEnableFunction)deviceGetProcAddress( + device, "nvnMultisampleStateSetAlphaToCoverageEnable"); + pfnc_nvnMultisampleStateSetAlphaToCoverageDither = + (nvnMultisampleStateSetAlphaToCoverageDitherFunction)deviceGetProcAddress( + device, "nvnMultisampleStateSetAlphaToCoverageDither"); + pfnc_nvnMultisampleStateGetMultisampleEnable = + (nvnMultisampleStateGetMultisampleEnableFunction)deviceGetProcAddress( + device, "nvnMultisampleStateGetMultisampleEnable"); + pfnc_nvnMultisampleStateGetSamples = + (nvnMultisampleStateGetSamplesFunction)deviceGetProcAddress( + device, "nvnMultisampleStateGetSamples"); + pfnc_nvnMultisampleStateGetAlphaToCoverageEnable = + (nvnMultisampleStateGetAlphaToCoverageEnableFunction)deviceGetProcAddress( + device, "nvnMultisampleStateGetAlphaToCoverageEnable"); + pfnc_nvnMultisampleStateGetAlphaToCoverageDither = + (nvnMultisampleStateGetAlphaToCoverageDitherFunction)deviceGetProcAddress( + device, "nvnMultisampleStateGetAlphaToCoverageDither"); + pfnc_nvnMultisampleStateSetRasterSamples = + (nvnMultisampleStateSetRasterSamplesFunction)deviceGetProcAddress( + device, "nvnMultisampleStateSetRasterSamples"); + pfnc_nvnMultisampleStateGetRasterSamples = + (nvnMultisampleStateGetRasterSamplesFunction)deviceGetProcAddress( + device, "nvnMultisampleStateGetRasterSamples"); + pfnc_nvnMultisampleStateSetCoverageModulationMode = + (nvnMultisampleStateSetCoverageModulationModeFunction)deviceGetProcAddress( + device, "nvnMultisampleStateSetCoverageModulationMode"); + pfnc_nvnMultisampleStateGetCoverageModulationMode = + (nvnMultisampleStateGetCoverageModulationModeFunction)deviceGetProcAddress( + device, "nvnMultisampleStateGetCoverageModulationMode"); + pfnc_nvnMultisampleStateSetCoverageToColorEnable = + (nvnMultisampleStateSetCoverageToColorEnableFunction)deviceGetProcAddress( + device, "nvnMultisampleStateSetCoverageToColorEnable"); + pfnc_nvnMultisampleStateGetCoverageToColorEnable = + (nvnMultisampleStateGetCoverageToColorEnableFunction)deviceGetProcAddress( + device, "nvnMultisampleStateGetCoverageToColorEnable"); + pfnc_nvnMultisampleStateSetCoverageToColorOutput = + (nvnMultisampleStateSetCoverageToColorOutputFunction)deviceGetProcAddress( + device, "nvnMultisampleStateSetCoverageToColorOutput"); + pfnc_nvnMultisampleStateGetCoverageToColorOutput = + (nvnMultisampleStateGetCoverageToColorOutputFunction)deviceGetProcAddress( + device, "nvnMultisampleStateGetCoverageToColorOutput"); + pfnc_nvnMultisampleStateSetSampleLocationsEnable = + (nvnMultisampleStateSetSampleLocationsEnableFunction)deviceGetProcAddress( + device, "nvnMultisampleStateSetSampleLocationsEnable"); + pfnc_nvnMultisampleStateGetSampleLocationsEnable = + (nvnMultisampleStateGetSampleLocationsEnableFunction)deviceGetProcAddress( + device, "nvnMultisampleStateGetSampleLocationsEnable"); + pfnc_nvnMultisampleStateGetSampleLocationsGrid = + (nvnMultisampleStateGetSampleLocationsGridFunction)deviceGetProcAddress( + device, "nvnMultisampleStateGetSampleLocationsGrid"); + pfnc_nvnMultisampleStateSetSampleLocationsGridEnable = + (nvnMultisampleStateSetSampleLocationsGridEnableFunction)deviceGetProcAddress( + device, "nvnMultisampleStateSetSampleLocationsGridEnable"); + pfnc_nvnMultisampleStateGetSampleLocationsGridEnable = + (nvnMultisampleStateGetSampleLocationsGridEnableFunction)deviceGetProcAddress( + device, "nvnMultisampleStateGetSampleLocationsGridEnable"); + pfnc_nvnMultisampleStateSetSampleLocations = + (nvnMultisampleStateSetSampleLocationsFunction)deviceGetProcAddress( + device, "nvnMultisampleStateSetSampleLocations"); + pfnc_nvnPolygonStateSetDefaults = (nvnPolygonStateSetDefaultsFunction)deviceGetProcAddress( + device, "nvnPolygonStateSetDefaults"); + pfnc_nvnPolygonStateSetCullFace = (nvnPolygonStateSetCullFaceFunction)deviceGetProcAddress( + device, "nvnPolygonStateSetCullFace"); + pfnc_nvnPolygonStateSetFrontFace = (nvnPolygonStateSetFrontFaceFunction)deviceGetProcAddress( + device, "nvnPolygonStateSetFrontFace"); + pfnc_nvnPolygonStateSetPolygonMode = + (nvnPolygonStateSetPolygonModeFunction)deviceGetProcAddress( + device, "nvnPolygonStateSetPolygonMode"); + pfnc_nvnPolygonStateSetPolygonOffsetEnables = + (nvnPolygonStateSetPolygonOffsetEnablesFunction)deviceGetProcAddress( + device, "nvnPolygonStateSetPolygonOffsetEnables"); + pfnc_nvnPolygonStateGetCullFace = (nvnPolygonStateGetCullFaceFunction)deviceGetProcAddress( + device, "nvnPolygonStateGetCullFace"); + pfnc_nvnPolygonStateGetFrontFace = (nvnPolygonStateGetFrontFaceFunction)deviceGetProcAddress( + device, "nvnPolygonStateGetFrontFace"); + pfnc_nvnPolygonStateGetPolygonMode = + (nvnPolygonStateGetPolygonModeFunction)deviceGetProcAddress( + device, "nvnPolygonStateGetPolygonMode"); + pfnc_nvnPolygonStateGetPolygonOffsetEnables = + (nvnPolygonStateGetPolygonOffsetEnablesFunction)deviceGetProcAddress( + device, "nvnPolygonStateGetPolygonOffsetEnables"); + pfnc_nvnDepthStencilStateSetDefaults = + (nvnDepthStencilStateSetDefaultsFunction)deviceGetProcAddress( + device, "nvnDepthStencilStateSetDefaults"); + pfnc_nvnDepthStencilStateSetDepthTestEnable = + (nvnDepthStencilStateSetDepthTestEnableFunction)deviceGetProcAddress( + device, "nvnDepthStencilStateSetDepthTestEnable"); + pfnc_nvnDepthStencilStateSetDepthWriteEnable = + (nvnDepthStencilStateSetDepthWriteEnableFunction)deviceGetProcAddress( + device, "nvnDepthStencilStateSetDepthWriteEnable"); + pfnc_nvnDepthStencilStateSetDepthFunc = + (nvnDepthStencilStateSetDepthFuncFunction)deviceGetProcAddress( + device, "nvnDepthStencilStateSetDepthFunc"); + pfnc_nvnDepthStencilStateSetStencilTestEnable = + (nvnDepthStencilStateSetStencilTestEnableFunction)deviceGetProcAddress( + device, "nvnDepthStencilStateSetStencilTestEnable"); + pfnc_nvnDepthStencilStateSetStencilFunc = + (nvnDepthStencilStateSetStencilFuncFunction)deviceGetProcAddress( + device, "nvnDepthStencilStateSetStencilFunc"); + pfnc_nvnDepthStencilStateSetStencilOp = + (nvnDepthStencilStateSetStencilOpFunction)deviceGetProcAddress( + device, "nvnDepthStencilStateSetStencilOp"); + pfnc_nvnDepthStencilStateGetDepthTestEnable = + (nvnDepthStencilStateGetDepthTestEnableFunction)deviceGetProcAddress( + device, "nvnDepthStencilStateGetDepthTestEnable"); + pfnc_nvnDepthStencilStateGetDepthWriteEnable = + (nvnDepthStencilStateGetDepthWriteEnableFunction)deviceGetProcAddress( + device, "nvnDepthStencilStateGetDepthWriteEnable"); + pfnc_nvnDepthStencilStateGetDepthFunc = + (nvnDepthStencilStateGetDepthFuncFunction)deviceGetProcAddress( + device, "nvnDepthStencilStateGetDepthFunc"); + pfnc_nvnDepthStencilStateGetStencilTestEnable = + (nvnDepthStencilStateGetStencilTestEnableFunction)deviceGetProcAddress( + device, "nvnDepthStencilStateGetStencilTestEnable"); + pfnc_nvnDepthStencilStateGetStencilFunc = + (nvnDepthStencilStateGetStencilFuncFunction)deviceGetProcAddress( + device, "nvnDepthStencilStateGetStencilFunc"); + pfnc_nvnDepthStencilStateGetStencilOp = + (nvnDepthStencilStateGetStencilOpFunction)deviceGetProcAddress( + device, "nvnDepthStencilStateGetStencilOp"); + pfnc_nvnVertexAttribStateSetDefaults = + (nvnVertexAttribStateSetDefaultsFunction)deviceGetProcAddress( + device, "nvnVertexAttribStateSetDefaults"); + pfnc_nvnVertexAttribStateSetFormat = + (nvnVertexAttribStateSetFormatFunction)deviceGetProcAddress( + device, "nvnVertexAttribStateSetFormat"); + pfnc_nvnVertexAttribStateSetStreamIndex = + (nvnVertexAttribStateSetStreamIndexFunction)deviceGetProcAddress( + device, "nvnVertexAttribStateSetStreamIndex"); + pfnc_nvnVertexAttribStateGetFormat = + (nvnVertexAttribStateGetFormatFunction)deviceGetProcAddress( + device, "nvnVertexAttribStateGetFormat"); + pfnc_nvnVertexAttribStateGetStreamIndex = + (nvnVertexAttribStateGetStreamIndexFunction)deviceGetProcAddress( + device, "nvnVertexAttribStateGetStreamIndex"); + pfnc_nvnVertexStreamStateSetDefaults = + (nvnVertexStreamStateSetDefaultsFunction)deviceGetProcAddress( + device, "nvnVertexStreamStateSetDefaults"); + pfnc_nvnVertexStreamStateSetStride = + (nvnVertexStreamStateSetStrideFunction)deviceGetProcAddress( + device, "nvnVertexStreamStateSetStride"); + pfnc_nvnVertexStreamStateSetDivisor = + (nvnVertexStreamStateSetDivisorFunction)deviceGetProcAddress( + device, "nvnVertexStreamStateSetDivisor"); + pfnc_nvnVertexStreamStateGetStride = + (nvnVertexStreamStateGetStrideFunction)deviceGetProcAddress( + device, "nvnVertexStreamStateGetStride"); + pfnc_nvnVertexStreamStateGetDivisor = + (nvnVertexStreamStateGetDivisorFunction)deviceGetProcAddress( + device, "nvnVertexStreamStateGetDivisor"); + pfnc_nvnCommandBufferInitialize = (nvnCommandBufferInitializeFunction)deviceGetProcAddress( + device, "nvnCommandBufferInitialize"); + pfnc_nvnCommandBufferFinalize = + (nvnCommandBufferFinalizeFunction)deviceGetProcAddress(device, "nvnCommandBufferFinalize"); + pfnc_nvnCommandBufferSetDebugLabel = + (nvnCommandBufferSetDebugLabelFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetDebugLabel"); + pfnc_nvnCommandBufferSetMemoryCallback = + (nvnCommandBufferSetMemoryCallbackFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetMemoryCallback"); + pfnc_nvnCommandBufferSetMemoryCallbackData = + (nvnCommandBufferSetMemoryCallbackDataFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetMemoryCallbackData"); + pfnc_nvnCommandBufferAddCommandMemory = + (nvnCommandBufferAddCommandMemoryFunction)deviceGetProcAddress( + device, "nvnCommandBufferAddCommandMemory"); + pfnc_nvnCommandBufferAddControlMemory = + (nvnCommandBufferAddControlMemoryFunction)deviceGetProcAddress( + device, "nvnCommandBufferAddControlMemory"); + pfnc_nvnCommandBufferGetCommandMemorySize = + (nvnCommandBufferGetCommandMemorySizeFunction)deviceGetProcAddress( + device, "nvnCommandBufferGetCommandMemorySize"); + pfnc_nvnCommandBufferGetCommandMemoryUsed = + (nvnCommandBufferGetCommandMemoryUsedFunction)deviceGetProcAddress( + device, "nvnCommandBufferGetCommandMemoryUsed"); + pfnc_nvnCommandBufferGetCommandMemoryFree = + (nvnCommandBufferGetCommandMemoryFreeFunction)deviceGetProcAddress( + device, "nvnCommandBufferGetCommandMemoryFree"); + pfnc_nvnCommandBufferGetControlMemorySize = + (nvnCommandBufferGetControlMemorySizeFunction)deviceGetProcAddress( + device, "nvnCommandBufferGetControlMemorySize"); + pfnc_nvnCommandBufferGetControlMemoryUsed = + (nvnCommandBufferGetControlMemoryUsedFunction)deviceGetProcAddress( + device, "nvnCommandBufferGetControlMemoryUsed"); + pfnc_nvnCommandBufferGetControlMemoryFree = + (nvnCommandBufferGetControlMemoryFreeFunction)deviceGetProcAddress( + device, "nvnCommandBufferGetControlMemoryFree"); + pfnc_nvnCommandBufferBeginRecording = + (nvnCommandBufferBeginRecordingFunction)deviceGetProcAddress( + device, "nvnCommandBufferBeginRecording"); + pfnc_nvnCommandBufferEndRecording = (nvnCommandBufferEndRecordingFunction)deviceGetProcAddress( + device, "nvnCommandBufferEndRecording"); + pfnc_nvnCommandBufferCallCommands = (nvnCommandBufferCallCommandsFunction)deviceGetProcAddress( + device, "nvnCommandBufferCallCommands"); + pfnc_nvnCommandBufferCopyCommands = (nvnCommandBufferCopyCommandsFunction)deviceGetProcAddress( + device, "nvnCommandBufferCopyCommands"); + pfnc_nvnCommandBufferBindBlendState = + (nvnCommandBufferBindBlendStateFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindBlendState"); + pfnc_nvnCommandBufferBindChannelMaskState = + (nvnCommandBufferBindChannelMaskStateFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindChannelMaskState"); + pfnc_nvnCommandBufferBindColorState = + (nvnCommandBufferBindColorStateFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindColorState"); + pfnc_nvnCommandBufferBindMultisampleState = + (nvnCommandBufferBindMultisampleStateFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindMultisampleState"); + pfnc_nvnCommandBufferBindPolygonState = + (nvnCommandBufferBindPolygonStateFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindPolygonState"); + pfnc_nvnCommandBufferBindDepthStencilState = + (nvnCommandBufferBindDepthStencilStateFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindDepthStencilState"); + pfnc_nvnCommandBufferBindVertexAttribState = + (nvnCommandBufferBindVertexAttribStateFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindVertexAttribState"); + pfnc_nvnCommandBufferBindVertexStreamState = + (nvnCommandBufferBindVertexStreamStateFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindVertexStreamState"); + pfnc_nvnCommandBufferBindProgram = (nvnCommandBufferBindProgramFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindProgram"); + pfnc_nvnCommandBufferBindVertexBuffer = + (nvnCommandBufferBindVertexBufferFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindVertexBuffer"); + pfnc_nvnCommandBufferBindVertexBuffers = + (nvnCommandBufferBindVertexBuffersFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindVertexBuffers"); + pfnc_nvnCommandBufferBindUniformBuffer = + (nvnCommandBufferBindUniformBufferFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindUniformBuffer"); + pfnc_nvnCommandBufferBindUniformBuffers = + (nvnCommandBufferBindUniformBuffersFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindUniformBuffers"); + pfnc_nvnCommandBufferBindTransformFeedbackBuffer = + (nvnCommandBufferBindTransformFeedbackBufferFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindTransformFeedbackBuffer"); + pfnc_nvnCommandBufferBindTransformFeedbackBuffers = + (nvnCommandBufferBindTransformFeedbackBuffersFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindTransformFeedbackBuffers"); + pfnc_nvnCommandBufferBindStorageBuffer = + (nvnCommandBufferBindStorageBufferFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindStorageBuffer"); + pfnc_nvnCommandBufferBindStorageBuffers = + (nvnCommandBufferBindStorageBuffersFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindStorageBuffers"); + pfnc_nvnCommandBufferBindTexture = (nvnCommandBufferBindTextureFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindTexture"); + pfnc_nvnCommandBufferBindTextures = (nvnCommandBufferBindTexturesFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindTextures"); + pfnc_nvnCommandBufferBindImage = (nvnCommandBufferBindImageFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindImage"); + pfnc_nvnCommandBufferBindImages = (nvnCommandBufferBindImagesFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindImages"); + pfnc_nvnCommandBufferSetPatchSize = (nvnCommandBufferSetPatchSizeFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetPatchSize"); + pfnc_nvnCommandBufferSetInnerTessellationLevels = + (nvnCommandBufferSetInnerTessellationLevelsFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetInnerTessellationLevels"); + pfnc_nvnCommandBufferSetOuterTessellationLevels = + (nvnCommandBufferSetOuterTessellationLevelsFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetOuterTessellationLevels"); + pfnc_nvnCommandBufferSetPrimitiveRestart = + (nvnCommandBufferSetPrimitiveRestartFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetPrimitiveRestart"); + pfnc_nvnCommandBufferBeginTransformFeedback = + (nvnCommandBufferBeginTransformFeedbackFunction)deviceGetProcAddress( + device, "nvnCommandBufferBeginTransformFeedback"); + pfnc_nvnCommandBufferEndTransformFeedback = + (nvnCommandBufferEndTransformFeedbackFunction)deviceGetProcAddress( + device, "nvnCommandBufferEndTransformFeedback"); + pfnc_nvnCommandBufferPauseTransformFeedback = + (nvnCommandBufferPauseTransformFeedbackFunction)deviceGetProcAddress( + device, "nvnCommandBufferPauseTransformFeedback"); + pfnc_nvnCommandBufferResumeTransformFeedback = + (nvnCommandBufferResumeTransformFeedbackFunction)deviceGetProcAddress( + device, "nvnCommandBufferResumeTransformFeedback"); + pfnc_nvnCommandBufferDrawTransformFeedback = + (nvnCommandBufferDrawTransformFeedbackFunction)deviceGetProcAddress( + device, "nvnCommandBufferDrawTransformFeedback"); + pfnc_nvnCommandBufferDrawArrays = (nvnCommandBufferDrawArraysFunction)deviceGetProcAddress( + device, "nvnCommandBufferDrawArrays"); + pfnc_nvnCommandBufferDrawElements = (nvnCommandBufferDrawElementsFunction)deviceGetProcAddress( + device, "nvnCommandBufferDrawElements"); + pfnc_nvnCommandBufferDrawElementsBaseVertex = + (nvnCommandBufferDrawElementsBaseVertexFunction)deviceGetProcAddress( + device, "nvnCommandBufferDrawElementsBaseVertex"); + pfnc_nvnCommandBufferDrawArraysInstanced = + (nvnCommandBufferDrawArraysInstancedFunction)deviceGetProcAddress( + device, "nvnCommandBufferDrawArraysInstanced"); + pfnc_nvnCommandBufferDrawElementsInstanced = + (nvnCommandBufferDrawElementsInstancedFunction)deviceGetProcAddress( + device, "nvnCommandBufferDrawElementsInstanced"); + pfnc_nvnCommandBufferDrawArraysIndirect = + (nvnCommandBufferDrawArraysIndirectFunction)deviceGetProcAddress( + device, "nvnCommandBufferDrawArraysIndirect"); + pfnc_nvnCommandBufferDrawElementsIndirect = + (nvnCommandBufferDrawElementsIndirectFunction)deviceGetProcAddress( + device, "nvnCommandBufferDrawElementsIndirect"); + pfnc_nvnCommandBufferMultiDrawArraysIndirectCount = + (nvnCommandBufferMultiDrawArraysIndirectCountFunction)deviceGetProcAddress( + device, "nvnCommandBufferMultiDrawArraysIndirectCount"); + pfnc_nvnCommandBufferMultiDrawElementsIndirectCount = + (nvnCommandBufferMultiDrawElementsIndirectCountFunction)deviceGetProcAddress( + device, "nvnCommandBufferMultiDrawElementsIndirectCount"); + pfnc_nvnCommandBufferClearColor = (nvnCommandBufferClearColorFunction)deviceGetProcAddress( + device, "nvnCommandBufferClearColor"); + pfnc_nvnCommandBufferClearColori = (nvnCommandBufferClearColoriFunction)deviceGetProcAddress( + device, "nvnCommandBufferClearColori"); + pfnc_nvnCommandBufferClearColorui = (nvnCommandBufferClearColoruiFunction)deviceGetProcAddress( + device, "nvnCommandBufferClearColorui"); + pfnc_nvnCommandBufferClearDepthStencil = + (nvnCommandBufferClearDepthStencilFunction)deviceGetProcAddress( + device, "nvnCommandBufferClearDepthStencil"); + pfnc_nvnCommandBufferDispatchCompute = + (nvnCommandBufferDispatchComputeFunction)deviceGetProcAddress( + device, "nvnCommandBufferDispatchCompute"); + pfnc_nvnCommandBufferDispatchComputeIndirect = + (nvnCommandBufferDispatchComputeIndirectFunction)deviceGetProcAddress( + device, "nvnCommandBufferDispatchComputeIndirect"); + pfnc_nvnCommandBufferSetViewport = (nvnCommandBufferSetViewportFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetViewport"); + pfnc_nvnCommandBufferSetViewports = (nvnCommandBufferSetViewportsFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetViewports"); + pfnc_nvnCommandBufferSetViewportSwizzles = + (nvnCommandBufferSetViewportSwizzlesFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetViewportSwizzles"); + pfnc_nvnCommandBufferSetScissor = (nvnCommandBufferSetScissorFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetScissor"); + pfnc_nvnCommandBufferSetScissors = (nvnCommandBufferSetScissorsFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetScissors"); + pfnc_nvnCommandBufferSetDepthRange = + (nvnCommandBufferSetDepthRangeFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetDepthRange"); + pfnc_nvnCommandBufferSetDepthBounds = + (nvnCommandBufferSetDepthBoundsFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetDepthBounds"); + pfnc_nvnCommandBufferSetDepthRanges = + (nvnCommandBufferSetDepthRangesFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetDepthRanges"); + pfnc_nvnCommandBufferSetTiledCacheAction = + (nvnCommandBufferSetTiledCacheActionFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetTiledCacheAction"); + pfnc_nvnCommandBufferSetTiledCacheTileSize = + (nvnCommandBufferSetTiledCacheTileSizeFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetTiledCacheTileSize"); + pfnc_nvnCommandBufferBindSeparateTexture = + (nvnCommandBufferBindSeparateTextureFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindSeparateTexture"); + pfnc_nvnCommandBufferBindSeparateSampler = + (nvnCommandBufferBindSeparateSamplerFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindSeparateSampler"); + pfnc_nvnCommandBufferBindSeparateTextures = + (nvnCommandBufferBindSeparateTexturesFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindSeparateTextures"); + pfnc_nvnCommandBufferBindSeparateSamplers = + (nvnCommandBufferBindSeparateSamplersFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindSeparateSamplers"); + pfnc_nvnCommandBufferSetStencilValueMask = + (nvnCommandBufferSetStencilValueMaskFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetStencilValueMask"); + pfnc_nvnCommandBufferSetStencilMask = + (nvnCommandBufferSetStencilMaskFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetStencilMask"); + pfnc_nvnCommandBufferSetStencilRef = + (nvnCommandBufferSetStencilRefFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetStencilRef"); + pfnc_nvnCommandBufferSetBlendColor = + (nvnCommandBufferSetBlendColorFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetBlendColor"); + pfnc_nvnCommandBufferSetPointSize = (nvnCommandBufferSetPointSizeFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetPointSize"); + pfnc_nvnCommandBufferSetLineWidth = (nvnCommandBufferSetLineWidthFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetLineWidth"); + pfnc_nvnCommandBufferSetPolygonOffsetClamp = + (nvnCommandBufferSetPolygonOffsetClampFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetPolygonOffsetClamp"); + pfnc_nvnCommandBufferSetAlphaRef = (nvnCommandBufferSetAlphaRefFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetAlphaRef"); + pfnc_nvnCommandBufferSetSampleMask = + (nvnCommandBufferSetSampleMaskFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetSampleMask"); + pfnc_nvnCommandBufferSetRasterizerDiscard = + (nvnCommandBufferSetRasterizerDiscardFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetRasterizerDiscard"); + pfnc_nvnCommandBufferSetDepthClamp = + (nvnCommandBufferSetDepthClampFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetDepthClamp"); + pfnc_nvnCommandBufferSetConservativeRasterEnable = + (nvnCommandBufferSetConservativeRasterEnableFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetConservativeRasterEnable"); + pfnc_nvnCommandBufferSetConservativeRasterDilate = + (nvnCommandBufferSetConservativeRasterDilateFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetConservativeRasterDilate"); + pfnc_nvnCommandBufferSetSubpixelPrecisionBias = + (nvnCommandBufferSetSubpixelPrecisionBiasFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetSubpixelPrecisionBias"); + pfnc_nvnCommandBufferCopyBufferToTexture = + (nvnCommandBufferCopyBufferToTextureFunction)deviceGetProcAddress( + device, "nvnCommandBufferCopyBufferToTexture"); + pfnc_nvnCommandBufferCopyTextureToBuffer = + (nvnCommandBufferCopyTextureToBufferFunction)deviceGetProcAddress( + device, "nvnCommandBufferCopyTextureToBuffer"); + pfnc_nvnCommandBufferCopyTextureToTexture = + (nvnCommandBufferCopyTextureToTextureFunction)deviceGetProcAddress( + device, "nvnCommandBufferCopyTextureToTexture"); + pfnc_nvnCommandBufferCopyBufferToBuffer = + (nvnCommandBufferCopyBufferToBufferFunction)deviceGetProcAddress( + device, "nvnCommandBufferCopyBufferToBuffer"); + pfnc_nvnCommandBufferClearBuffer = (nvnCommandBufferClearBufferFunction)deviceGetProcAddress( + device, "nvnCommandBufferClearBuffer"); + pfnc_nvnCommandBufferClearTexture = (nvnCommandBufferClearTextureFunction)deviceGetProcAddress( + device, "nvnCommandBufferClearTexture"); + pfnc_nvnCommandBufferClearTexturei = + (nvnCommandBufferClearTextureiFunction)deviceGetProcAddress( + device, "nvnCommandBufferClearTexturei"); + pfnc_nvnCommandBufferClearTextureui = + (nvnCommandBufferClearTextureuiFunction)deviceGetProcAddress( + device, "nvnCommandBufferClearTextureui"); + pfnc_nvnCommandBufferUpdateUniformBuffer = + (nvnCommandBufferUpdateUniformBufferFunction)deviceGetProcAddress( + device, "nvnCommandBufferUpdateUniformBuffer"); + pfnc_nvnCommandBufferReportCounter = + (nvnCommandBufferReportCounterFunction)deviceGetProcAddress( + device, "nvnCommandBufferReportCounter"); + pfnc_nvnCommandBufferResetCounter = (nvnCommandBufferResetCounterFunction)deviceGetProcAddress( + device, "nvnCommandBufferResetCounter"); + pfnc_nvnCommandBufferReportValue = (nvnCommandBufferReportValueFunction)deviceGetProcAddress( + device, "nvnCommandBufferReportValue"); + pfnc_nvnCommandBufferSetRenderEnable = + (nvnCommandBufferSetRenderEnableFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetRenderEnable"); + pfnc_nvnCommandBufferSetRenderEnableConditional = + (nvnCommandBufferSetRenderEnableConditionalFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetRenderEnableConditional"); + pfnc_nvnCommandBufferSetRenderTargets = + (nvnCommandBufferSetRenderTargetsFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetRenderTargets"); + pfnc_nvnCommandBufferDiscardColor = (nvnCommandBufferDiscardColorFunction)deviceGetProcAddress( + device, "nvnCommandBufferDiscardColor"); + pfnc_nvnCommandBufferDiscardDepthStencil = + (nvnCommandBufferDiscardDepthStencilFunction)deviceGetProcAddress( + device, "nvnCommandBufferDiscardDepthStencil"); + pfnc_nvnCommandBufferDownsample = (nvnCommandBufferDownsampleFunction)deviceGetProcAddress( + device, "nvnCommandBufferDownsample"); + pfnc_nvnCommandBufferTiledDownsample = + (nvnCommandBufferTiledDownsampleFunction)deviceGetProcAddress( + device, "nvnCommandBufferTiledDownsample"); + pfnc_nvnCommandBufferDownsampleTextureView = + (nvnCommandBufferDownsampleTextureViewFunction)deviceGetProcAddress( + device, "nvnCommandBufferDownsampleTextureView"); + pfnc_nvnCommandBufferTiledDownsampleTextureView = + (nvnCommandBufferTiledDownsampleTextureViewFunction)deviceGetProcAddress( + device, "nvnCommandBufferTiledDownsampleTextureView"); + pfnc_nvnCommandBufferBarrier = + (nvnCommandBufferBarrierFunction)deviceGetProcAddress(device, "nvnCommandBufferBarrier"); + pfnc_nvnCommandBufferWaitSync = + (nvnCommandBufferWaitSyncFunction)deviceGetProcAddress(device, "nvnCommandBufferWaitSync"); + pfnc_nvnCommandBufferFenceSync = (nvnCommandBufferFenceSyncFunction)deviceGetProcAddress( + device, "nvnCommandBufferFenceSync"); + pfnc_nvnCommandBufferSetTexturePool = + (nvnCommandBufferSetTexturePoolFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetTexturePool"); + pfnc_nvnCommandBufferSetSamplerPool = + (nvnCommandBufferSetSamplerPoolFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetSamplerPool"); + pfnc_nvnCommandBufferSetShaderScratchMemory = + (nvnCommandBufferSetShaderScratchMemoryFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetShaderScratchMemory"); + pfnc_nvnCommandBufferSaveZCullData = + (nvnCommandBufferSaveZCullDataFunction)deviceGetProcAddress( + device, "nvnCommandBufferSaveZCullData"); + pfnc_nvnCommandBufferRestoreZCullData = + (nvnCommandBufferRestoreZCullDataFunction)deviceGetProcAddress( + device, "nvnCommandBufferRestoreZCullData"); + pfnc_nvnCommandBufferSetCopyRowStride = + (nvnCommandBufferSetCopyRowStrideFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetCopyRowStride"); + pfnc_nvnCommandBufferSetCopyImageStride = + (nvnCommandBufferSetCopyImageStrideFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetCopyImageStride"); + pfnc_nvnCommandBufferGetCopyRowStride = + (nvnCommandBufferGetCopyRowStrideFunction)deviceGetProcAddress( + device, "nvnCommandBufferGetCopyRowStride"); + pfnc_nvnCommandBufferGetCopyImageStride = + (nvnCommandBufferGetCopyImageStrideFunction)deviceGetProcAddress( + device, "nvnCommandBufferGetCopyImageStride"); + pfnc_nvnCommandBufferDrawTexture = (nvnCommandBufferDrawTextureFunction)deviceGetProcAddress( + device, "nvnCommandBufferDrawTexture"); + pfnc_nvnProgramSetSubroutineLinkage = + (nvnProgramSetSubroutineLinkageFunction)deviceGetProcAddress( + device, "nvnProgramSetSubroutineLinkage"); + pfnc_nvnCommandBufferSetProgramSubroutines = + (nvnCommandBufferSetProgramSubroutinesFunction)deviceGetProcAddress( + device, "nvnCommandBufferSetProgramSubroutines"); + pfnc_nvnCommandBufferBindCoverageModulationTable = + (nvnCommandBufferBindCoverageModulationTableFunction)deviceGetProcAddress( + device, "nvnCommandBufferBindCoverageModulationTable"); + pfnc_nvnCommandBufferResolveDepthBuffer = + (nvnCommandBufferResolveDepthBufferFunction)deviceGetProcAddress( + device, "nvnCommandBufferResolveDepthBuffer"); + pfnc_nvnCommandBufferPushDebugGroupStatic = + (nvnCommandBufferPushDebugGroupStaticFunction)deviceGetProcAddress( + device, "nvnCommandBufferPushDebugGroupStatic"); + pfnc_nvnCommandBufferPushDebugGroupDynamic = + (nvnCommandBufferPushDebugGroupDynamicFunction)deviceGetProcAddress( + device, "nvnCommandBufferPushDebugGroupDynamic"); + pfnc_nvnCommandBufferPushDebugGroup = + (nvnCommandBufferPushDebugGroupFunction)deviceGetProcAddress( + device, "nvnCommandBufferPushDebugGroup"); + pfnc_nvnCommandBufferPopDebugGroup = + (nvnCommandBufferPopDebugGroupFunction)deviceGetProcAddress( + device, "nvnCommandBufferPopDebugGroup"); + pfnc_nvnCommandBufferPopDebugGroupId = + (nvnCommandBufferPopDebugGroupIdFunction)deviceGetProcAddress( + device, "nvnCommandBufferPopDebugGroupId"); + pfnc_nvnCommandBufferInsertDebugMarkerStatic = + (nvnCommandBufferInsertDebugMarkerStaticFunction)deviceGetProcAddress( + device, "nvnCommandBufferInsertDebugMarkerStatic"); + pfnc_nvnCommandBufferInsertDebugMarkerDynamic = + (nvnCommandBufferInsertDebugMarkerDynamicFunction)deviceGetProcAddress( + device, "nvnCommandBufferInsertDebugMarkerDynamic"); + pfnc_nvnCommandBufferInsertDebugMarker = + (nvnCommandBufferInsertDebugMarkerFunction)deviceGetProcAddress( + device, "nvnCommandBufferInsertDebugMarker"); + pfnc_nvnCommandBufferGetMemoryCallback = + (nvnCommandBufferGetMemoryCallbackFunction)deviceGetProcAddress( + device, "nvnCommandBufferGetMemoryCallback"); + pfnc_nvnCommandBufferGetMemoryCallbackData = + (nvnCommandBufferGetMemoryCallbackDataFunction)deviceGetProcAddress( + device, "nvnCommandBufferGetMemoryCallbackData"); + pfnc_nvnCommandBufferIsRecording = (nvnCommandBufferIsRecordingFunction)deviceGetProcAddress( + device, "nvnCommandBufferIsRecording"); + pfnc_nvnSyncInitialize = + (nvnSyncInitializeFunction)deviceGetProcAddress(device, "nvnSyncInitialize"); + pfnc_nvnSyncFinalize = (nvnSyncFinalizeFunction)deviceGetProcAddress(device, "nvnSyncFinalize"); + pfnc_nvnSyncSetDebugLabel = + (nvnSyncSetDebugLabelFunction)deviceGetProcAddress(device, "nvnSyncSetDebugLabel"); + pfnc_nvnQueueFenceSync = + (nvnQueueFenceSyncFunction)deviceGetProcAddress(device, "nvnQueueFenceSync"); + pfnc_nvnSyncWait = (nvnSyncWaitFunction)deviceGetProcAddress(device, "nvnSyncWait"); + pfnc_nvnQueueWaitSync = + (nvnQueueWaitSyncFunction)deviceGetProcAddress(device, "nvnQueueWaitSync"); + pfnc_nvnEventBuilderSetDefaults = (nvnEventBuilderSetDefaultsFunction)deviceGetProcAddress( + device, "nvnEventBuilderSetDefaults"); + pfnc_nvnEventBuilderSetStorage = (nvnEventBuilderSetStorageFunction)deviceGetProcAddress( + device, "nvnEventBuilderSetStorage"); + pfnc_nvnEventInitialize = + (nvnEventInitializeFunction)deviceGetProcAddress(device, "nvnEventInitialize"); + pfnc_nvnEventFinalize = + (nvnEventFinalizeFunction)deviceGetProcAddress(device, "nvnEventFinalize"); + pfnc_nvnEventGetValue = + (nvnEventGetValueFunction)deviceGetProcAddress(device, "nvnEventGetValue"); + pfnc_nvnEventSignal = (nvnEventSignalFunction)deviceGetProcAddress(device, "nvnEventSignal"); + pfnc_nvnCommandBufferWaitEvent = (nvnCommandBufferWaitEventFunction)deviceGetProcAddress( + device, "nvnCommandBufferWaitEvent"); + pfnc_nvnCommandBufferSignalEvent = (nvnCommandBufferSignalEventFunction)deviceGetProcAddress( + device, "nvnCommandBufferSignalEvent"); +} +} diff --git a/lib/agl b/lib/agl deleted file mode 160000 index 7c063271..00000000 --- a/lib/agl +++ /dev/null @@ -1 +0,0 @@ -Subproject commit 7c063271ba9dd4fb802f0ac2ae2834b5af2e725d diff --git a/lib/agl/.clang-format b/lib/agl/.clang-format new file mode 100644 index 00000000..ef862606 --- /dev/null +++ b/lib/agl/.clang-format @@ -0,0 +1,74 @@ +--- +Language: Cpp +AccessModifierOffset: -4 +AlignAfterOpenBracket: Align +AlignConsecutiveAssignments: false +AlignConsecutiveDeclarations: false +AlignOperands: true +AlignTrailingComments: true +AllowAllParametersOfDeclarationOnNextLine: true +AllowShortBlocksOnASingleLine: Never +AllowShortCaseLabelsOnASingleLine: false +AllowShortFunctionsOnASingleLine: Inline +AllowShortIfStatementsOnASingleLine: Never +AllowShortLoopsOnASingleLine: false +AlwaysBreakAfterDefinitionReturnType: None +AlwaysBreakAfterReturnType: None +AlwaysBreakBeforeMultilineStrings: false +AlwaysBreakTemplateDeclarations: Yes +BinPackArguments: true +BinPackParameters: true +BreakBeforeBinaryOperators: None +BreakBeforeBraces: Attach +BreakBeforeTernaryOperators: false +BreakConstructorInitializersBeforeComma: false +ColumnLimit: 100 +CommentPragmas: '^ (IWYU pragma:|NOLINT)' +ConstructorInitializerAllOnOneLineOrOnePerLine: false +ConstructorInitializerIndentWidth: 4 +ContinuationIndentWidth: 4 +Cpp11BracedListStyle: true +DerivePointerAlignment: false +DisableFormat: false +ForEachMacros: [] +IncludeCategories: + - Regex: '^<[Ww]indows\.h>$' + Priority: 1 + - Regex: '^<' + Priority: 2 + - Regex: '^"' + Priority: 3 +IndentCaseLabels: false +IndentWidth: 4 +IndentWrappedFunctionNames: false +KeepEmptyLinesAtTheStartOfBlocks: false +MacroBlockBegin: '' +MacroBlockEnd: '' +MaxEmptyLinesToKeep: 1 +NamespaceIndentation: None +ObjCBlockIndentWidth: 4 +ObjCSpaceAfterProperty: false +ObjCSpaceBeforeProtocolList: true +PenaltyBreakBeforeFirstCallParameter: 19 +PenaltyBreakComment: 300 +PenaltyBreakFirstLessLess: 120 +PenaltyBreakString: 1000 +PenaltyExcessCharacter: 1000000 +PenaltyReturnTypeOnItsOwnLine: 60 +PointerAlignment: Left +ReflowComments: true +SortIncludes: true +SpaceAfterCStyleCast: false +SpaceBeforeAssignmentOperators: true +SpaceBeforeParens: ControlStatements +SpaceInEmptyParentheses: false +SpacesBeforeTrailingComments: 2 +SpacesInAngles: false +SpacesInContainerLiterals: true +SpacesInCStyleCastParentheses: false +SpacesInParentheses: false +SpacesInSquareBrackets: false +Standard: c++17 +TabWidth: 4 +UseTab: Never +... diff --git a/lib/agl/.gitrepo b/lib/agl/.gitrepo new file mode 100644 index 00000000..1a02bca9 --- /dev/null +++ b/lib/agl/.gitrepo @@ -0,0 +1,12 @@ +; DO NOT EDIT (unless you know what you are doing) +; +; This subdirectory is a git "subrepo", and this file is maintained by the +; git-subrepo command. See https://github.com/git-commands/git-subrepo#readme +; +[subrepo] + remote = https://github.com/open-ead/agl + branch = master + commit = 7c063271ba9dd4fb802f0ac2ae2834b5af2e725d + parent = ffcc7f659ebc9bc9d149e52bec553b906bb47369 + method = merge + cmdver = 0.4.3 diff --git a/lib/agl/CMakeLists.txt b/lib/agl/CMakeLists.txt new file mode 100644 index 00000000..fd9e88a7 --- /dev/null +++ b/lib/agl/CMakeLists.txt @@ -0,0 +1,41 @@ +project(agl CXX ASM) + +add_library(agl OBJECT + include/agl/g3d/aglNW4FToNN.h + include/agl/Utils/aglAtomicPtrArray.h + include/agl/Utils/aglParameter.h + include/agl/Utils/aglParameterCurve.hpp + include/agl/Utils/aglParameterIO.h + include/agl/Utils/aglParameterList.h + include/agl/Utils/aglParameterObj.h + include/agl/Utils/aglParameterStringMgr.h + include/agl/Utils/aglResCommon.h + include/agl/Utils/aglResParameter.h + include/agl/detail/aglGPUMemBlockMgr.h + include/agl/driver/aglGraphicsDriverMgr.h + include/agl/driver/aglNVNMgr.h + include/agl/aglGPUCommon.hpp + include/agl/aglGPUMemBlock.hpp + src/Utils/aglAtomicPtrArray.cpp + src/Utils/aglParameter.cpp + src/Utils/aglParameterIO.cpp + src/Utils/aglParameterList.cpp + src/Utils/aglParameterObj.cpp + src/Utils/aglParameterStringMgr.cpp + src/Utils/aglResCommon.cpp + src/Utils/aglResParameter.cpp + src/detail/aglGPUMemBlockMgr.cpp + src/driver/aglGraphicsDriverMgr.cpp + src/driver/aglNVNMgr.cpp + src/aglGPUMemBlock.cpp +) + +target_compile_options(agl PRIVATE -fno-exceptions) +target_compile_options(agl PRIVATE -fno-strict-aliasing) +target_compile_options(agl PRIVATE -Wno-invalid-offsetof) +target_include_directories(agl PUBLIC include/) + +if(NOT TARGET sead) + add_subdirectory(../sead) +endif() +target_link_libraries(agl PUBLIC sead) diff --git a/lib/agl/README.md b/lib/agl/README.md new file mode 100644 index 00000000..fff97715 --- /dev/null +++ b/lib/agl/README.md @@ -0,0 +1,5 @@ +# agl + +This is a decompilation of agl, a C++ library for first-party Nintendo games that is used for graphics, lighting and parameter utils (AAMP). + +See [sead](https://github.com/open-ead/sead) for more information about the goal of this project, guidelines for contributing and build information. diff --git a/lib/agl/include/agl/Utils/aglAtomicPtrArray.h b/lib/agl/include/agl/Utils/aglAtomicPtrArray.h new file mode 100644 index 00000000..d20e60be --- /dev/null +++ b/lib/agl/include/agl/Utils/aglAtomicPtrArray.h @@ -0,0 +1,239 @@ +#pragma once + +#include +#include +#include +#include + +namespace sead { +class Heap; +} + +namespace agl { + +namespace detail { + +class AtomicPtrArrayImpl { +public: + AtomicPtrArrayImpl() = default; + AtomicPtrArrayImpl(s32 ptrNumMax, void* buf) { setBuffer(ptrNumMax, buf); } + + void setBuffer(s32 ptrNumMax, void* buf); + void allocBuffer(s32 ptrNumMax, sead::Heap* heap, s32 alignment = sizeof(void*)); + void freeBuffer(); + bool isBufferReady() const { return mPtrs != nullptr; } + + bool isEmpty() const { return mPtrNum == 0; } + bool isFull() const { return mPtrNum == mPtrNumMax; } + + s32 size() const { return mPtrNum; } + s32 capacity() const { return mPtrNumMax; } + + void erase(s32 position) { erase(position, 1); } + void erase(s32 position, s32 count); + void clear() { mPtrNum.exchange(0); } + + void swap(s32 pos1, s32 pos2) { + auto* ptr = mPtrs[pos1]; + mPtrs[pos1] = mPtrs[pos2]; + mPtrs[pos2] = ptr; + } + void shuffle() { + sead::Random random; + shuffle(&random); + } + void shuffle(sead::Random* random); + +protected: + using CompareCallbackImpl = int (*)(const void* a, const void* b); + + void* at(s32 idx) const { + if (u32(mPtrNum) <= u32(idx)) { + SEAD_ASSERT_MSG(false, "index exceeded [%d/%d]", idx, mPtrNum.load()); + return nullptr; + } + return mPtrs[idx]; + } + + void* unsafeAt(s32 idx) const { return mPtrs[idx]; } + + // XXX: should this use at()? + void* front() const { return mPtrs[0]; } + void* back() const { return mPtrs[mPtrNum - 1]; } + + void pushBack(void* ptr) { + const s32 idx = mPtrNum++; + SEAD_ASSERT_MSG(idx < mPtrNumMax, "index = %d, mPtrNumMax = %d", idx, mPtrNumMax.load()); + mPtrs[idx] = ptr; + } + + void* popBack() { return isEmpty() ? nullptr : mPtrs[--mPtrNum]; } + + void* popFront() { + if (isEmpty()) + return nullptr; + + void* result = mPtrs[0]; + erase(0); + return result; + } + + void* find(const void* ptr, CompareCallbackImpl cmp) const { + for (s32 i = 0; i < mPtrNum; ++i) { + if (cmp(ptr, mPtrs[i]) == 0) + return mPtrs[i]; + } + return nullptr; + } + + s32 search(const void* ptr, CompareCallbackImpl cmp) const { + for (s32 i = 0; i < mPtrNum; ++i) { + if (cmp(ptr, mPtrs[i]) == 0) + return i; + } + return -1; + } + + bool equal(const AtomicPtrArrayImpl& other, CompareCallbackImpl cmp) const { + if (mPtrNum != other.mPtrNum) + return false; + + for (s32 i = 0; i < mPtrNum; ++i) { + if (cmp(mPtrs[i], other.mPtrs[i]) != 0) + return false; + } + return true; + } + + s32 indexOf(const void* ptr) const { + for (s32 i = 0; i < mPtrNum; ++i) { + if (mPtrs[i] == ptr) + return i; + } + return -1; + } + + void sort(CompareCallbackImpl cmp); + void heapSort(CompareCallbackImpl cmp); + + sead::Atomic mPtrNum = 0; + sead::Atomic mPtrNumMax = 0; + void** mPtrs = nullptr; +}; + +} // namespace detail + +namespace utl { + +template +class AtomicPtrArray : public detail::AtomicPtrArrayImpl { +public: + AtomicPtrArray() = default; + AtomicPtrArray(s32 ptrNumMax, T** buf) : AtomicPtrArrayImpl(ptrNumMax, buf) {} + + T* at(s32 pos) const { return static_cast(AtomicPtrArrayImpl::at(pos)); } + T* unsafeAt(s32 pos) const { return static_cast(AtomicPtrArrayImpl::unsafeAt(pos)); } + T* operator[](s32 pos) const { return at(pos); } + + // XXX: Does this use at()? + T* front() const { return at(0); } + T* back() const { return at(mPtrNum - 1); } + + void pushBack(T* ptr) { AtomicPtrArrayImpl::pushBack(ptr); } + + T* popBack() { return static_cast(AtomicPtrArrayImpl::popBack()); } + T* popFront() { return static_cast(AtomicPtrArrayImpl::popFront()); } + + s32 indexOf(const T* ptr) const { return AtomicPtrArrayImpl::indexOf(ptr); } + + using CompareCallback = s32 (*)(const T*, const T*); + + void sort() { AtomicPtrArrayImpl::sort(compareT); } + void sort(CompareCallback cmp) { AtomicPtrArrayImpl::sort(cmp); } + void heapSort() { AtomicPtrArrayImpl::heapSort(compareT); } + void heapSort(CompareCallback cmp) { AtomicPtrArrayImpl::heapSort(cmp); } + + bool equal(const AtomicPtrArray& other, CompareCallback cmp) const { + return AtomicPtrArrayImpl::equal(other, cmp); + } + + T* find(const T* ptr) const { return AtomicPtrArrayImpl::find(ptr, compareT); } + T* find(const T* ptr, CompareCallback cmp) const { return AtomicPtrArrayImpl::find(ptr, cmp); } + s32 search(const T* ptr) const { return AtomicPtrArrayImpl::search(ptr, compareT); } + s32 search(const T* ptr, CompareCallback cmp) const { + return AtomicPtrArrayImpl::search(ptr, cmp); + } + + bool operator==(const AtomicPtrArray& other) const { return equal(other, compareT); } + bool operator!=(const AtomicPtrArray& other) const { return !(*this == other); } + + class iterator { + public: + iterator(T* const* pptr) : mPPtr{pptr} {} + bool operator==(const iterator& other) const { return mPPtr == other.mPPtr; } + bool operator!=(const iterator& other) const { return !(*this == other); } + iterator& operator++() { + ++mPPtr; + return *this; + } + T& operator*() const { return **mPPtr; } + T* operator->() const { return *mPPtr; } + + private: + T* const* mPPtr; + }; + + iterator begin() const { return iterator(data()); } + iterator end() const { return iterator(data() + mPtrNum); } + + class constIterator { + public: + constIterator(const T* const* pptr) : mPPtr{pptr} {} + bool operator==(const constIterator& other) const { return mPPtr == other.mPPtr; } + bool operator!=(const constIterator& other) const { return !(*this == other); } + constIterator& operator++() { + ++mPPtr; + return *this; + } + const T& operator*() const { return **mPPtr; } + const T* operator->() const { return *mPPtr; } + + private: + const T* const* mPPtr; + }; + + constIterator constBegin() const { return constIterator(data()); } + constIterator constEnd() const { return constIterator(data() + mPtrNum); } + + T** data() const { return reinterpret_cast(mPtrs); } + +protected: + static int compareT(const T* a, const T* b) { + if (*a < *b) + return -1; + if (*a > *b) + return 1; + return 0; + } +}; + +template +class FixedPtrArray : public AtomicPtrArray { +public: + FixedPtrArray() { AtomicPtrArray::setBuffer(N, mWork); } + + // These do not make sense for a *fixed* array. + void setBuffer(s32 ptrNumMax, void* buf) = delete; + void allocBuffer(s32 ptrNumMax, sead::Heap* heap, s32 alignment = sizeof(void*)) = delete; + bool tryAllocBuffer(s32 ptrNumMax, sead::Heap* heap, s32 alignment = sizeof(void*)) = delete; + void freeBuffer() = delete; + +private: + // Nintendo uses an untyped u8[N*sizeof(void*)] buffer. That is undefined behavior, + // so we will not do that. + T* mWork[N]; +}; + +} // namespace utl + +} // namespace agl diff --git a/lib/agl/include/agl/Utils/aglParameter.h b/lib/agl/include/agl/Utils/aglParameter.h new file mode 100644 index 00000000..9ab66a6d --- /dev/null +++ b/lib/agl/include/agl/Utils/aglParameter.h @@ -0,0 +1,439 @@ +#pragma once + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include "agl/Utils/aglResParameter.h" + +namespace sead { +class Heap; +class XmlElement; +} // namespace sead + +namespace agl::utl { + +class IParameterObj; + +class ParameterBase { +public: + enum class ParameterType { + Bool = 0, + F32 = 1, + Int = 2, + Vec2 = 3, + Vec3 = 4, + Vec4 = 5, + Color = 6, + String32 = 7, + String64 = 8, + Curve1 = 9, + Curve2 = 10, + Curve3 = 11, + Curve4 = 12, + BufferInt = 13, + BufferF32 = 14, + String256 = 15, + Quat = 16, + U32 = 17, + BufferU32 = 18, + BufferBinary = 19, + StringRef = 20, + Special = 21, + }; + + ParameterBase(); + ParameterBase(const sead::SafeString& name, const sead::SafeString& label, + IParameterObj* param_obj); + ParameterBase(const sead::SafeString& name, const sead::SafeString& label, + const sead::SafeString& meta, IParameterObj* param_obj); + virtual ~ParameterBase() { ; } + + void initializeListNode(const sead::SafeString& name, const sead::SafeString& label, + const sead::SafeString& meta, IParameterObj* param_obj); + + u32 getNameHash() const { return mNameHash; } + sead::SafeString getParameterName() const; + sead::SafeString getName() const { return getParameterName(); } + sead::SafeString getLabel() const; + sead::SafeString getMeta() const; + + ParameterBase* getNext() const { return mNext; } + + static const char* getTagName(); + static const char* getAttributeNameString(); + static const char* getAttributeTypeString(); + static const char* getAttributeValueString(); + static const char* getParameterTypeName(ParameterType type); + + bool isSafeType(ParameterType type) const; + bool verifyType(ParameterType type) const; + + virtual bool copy(const ParameterBase& other); + virtual void copyUnsafe(const ParameterBase& other); + virtual bool copyLerp(const ParameterBase& param1, const ParameterBase& param2, f32 t); + +#ifdef SEAD_DEBUG + virtual void genMessageParameter(sead::hostio::Context* context); + void genMessageParameter(sead::hostio::Context* context, const sead::SafeString&); + virtual void listenPropertyEventParameter(sead::hostio::Reflexible* reflexible, + const sead::hostio::PropertyEvent* event); +#endif + + virtual void writeToXML(sead::XmlElement* element, sead::Heap* heap); + virtual bool readFromXML(const sead::XmlElement& element, bool x); + + virtual ParameterType getParameterType() const = 0; + virtual const void* ptr() const = 0; + virtual void* ptr() = 0; + virtual const void* typePtr() const = 0; + virtual void* typePtr() = 0; + virtual u32 size() const = 0; + virtual u32 calcBinarizeSize() const { return size(); } + virtual ParameterBase* clone(sead::Heap* heap, IParameterObj* obj) const = 0; + + void applyResource(ResParameter res); + void applyResource(ResParameter res, f32 t); + void applyString(const sead::SafeString& string, bool x); + virtual void postApplyResource_(const void*, size_t) {} + void createByTypeName(const sead::SafeString& a, const sead::SafeString& b); + + virtual bool isBinary() const { return false; } + virtual bool isBinaryInternalBuffer() const { return true; } + bool isInterpolatable() const; + size_t binarize(void* binary) const; + bool makeZero(); + + static u32 calcHash(const sead::SafeString& key); + + template + T* ptrT() { + return static_cast(ptr()); + } + + template + const T* ptrT() const { + return static_cast(ptr()); + } + +protected: + friend class IParameterObj; + + template + void copyLerp_(const ParameterBase& param1, const ParameterBase& param2, f32 t); + + u32 mNameHash; + ParameterBase* mNext; + +#ifdef SEAD_DEBUG + const char* mName; + const char* mLabel; + const char* mMeta; +#endif +}; + +using ParameterType = ParameterBase::ParameterType; + +template +class Parameter : public ParameterBase { +public: + Parameter() = default; + + explicit Parameter(const T& value) : mValue(value) {} + + Parameter(const T& value, const sead::SafeString& name, IParameterObj* obj) { + initializeParameter(value, name, name, obj); + } + + Parameter(const T& value, const sead::SafeString& name, const sead::SafeString& label, + IParameterObj* obj) { + initializeParameter(value, name, label, obj); + } + + Parameter(const T& value, const sead::SafeString& name, const sead::SafeString& label, + const sead::SafeString& meta, IParameterObj* obj) { + initializeParameter(value, name, label, meta, obj); + } + + ~Parameter() override { ; } + + ParameterType getParameterType() const override { + if constexpr (std::is_pointer()) + return ParameterType::Special; + else if constexpr (std::is_same()) + return ParameterType::Bool; + else if constexpr (std::is_same()) + return ParameterType::F32; + else if constexpr (std::is_same()) + return ParameterType::Int; + else if constexpr (std::is_same()) + return ParameterType::Vec2; + else if constexpr (std::is_same()) + return ParameterType::Vec3; + else if constexpr (std::is_same()) + return ParameterType::Vec4; + else if constexpr (std::is_same()) + return ParameterType::Color; + else if constexpr (std::is_same>()) + return ParameterType::String32; + else if constexpr (std::is_same>()) + return ParameterType::String64; + // TODO: curve1-4 + else if constexpr (std::is_same>()) + return ParameterType::String256; + else if constexpr (std::is_same()) + return ParameterType::Quat; + else if constexpr (std::is_same()) + return ParameterType::U32; + else if constexpr (std::is_same()) + return ParameterType::StringRef; + else + static_assert(!std::is_same(), "Unknown type"); + } + + const void* ptr() const override { + if constexpr (std::is_base_of()) { + return mValue.cstr(); + } else { + return &mValue; + } + } + + void* ptr() override { + if constexpr (std::is_same()) { + SEAD_ASSERT_MSG(false, "Can't access."); + return nullptr; + } else if constexpr (std::is_base_of()) { + return mValue.getBuffer(); + } else { + return &mValue; + } + } + + const void* typePtr() const override { return &mValue; } + void* typePtr() override { return &mValue; } + + u32 size() const override { + if constexpr (std::is_same()) + return 8; + else if constexpr (std::is_same>()) + return 32; + else if constexpr (std::is_same>()) + return 64; + else if constexpr (std::is_same>()) + return 256; + else + return sizeof(T); + } + + u32 calcBinarizeSize() const override { + if constexpr (std::is_base_of()) { + return mValue.calcLength() + 1; + } else { + return size(); + } + } + + ParameterBase* clone(sead::Heap* heap, IParameterObj* obj) const override { + return new (heap) Parameter(mValue, getName(), getLabel(), getMeta(), obj); + } + + void initializeParameter(const T& value, const sead::SafeString& name, + const sead::SafeString& label, IParameterObj* obj) { + initializeListNode(name, label, "", obj); + mValue = value; + + if constexpr (std::is_same()) { + SEAD_ASSERT_MSG(!sead::MemUtil::isStack(value.cstr()), "%p is in stack", value.cstr()); + } + } + + void initializeParameter(const T& value, const sead::SafeString& name, + const sead::SafeString& label, const sead::SafeString& meta, + IParameterObj* obj) { + initializeListNode(name, label, meta, obj); + mValue = value; + + if constexpr (std::is_same()) { + SEAD_ASSERT_MSG(!sead::MemUtil::isStack(value.cstr()), "%p is in stack", value.cstr()); + } + } + + /// Alias of initializeParameter. + void init(const T& value, const sead::SafeString& name, IParameterObj* obj) { + initializeParameter(value, name, name, obj); + } + + /// Alias of initializeParameter. + void init(const T& value, const sead::SafeString& name, const sead::SafeString& label, + IParameterObj* obj) { + initializeParameter(value, name, label, obj); + } + + /// Alias of initializeParameter. + void init(const T& value, const sead::SafeString& name, const sead::SafeString& label, + const sead::SafeString& meta, IParameterObj* obj) { + initializeParameter(value, name, label, meta, obj); + } + + T& ref() { return mValue; } + const T& ref() const { return mValue; } + + T& operator*() { return mValue; } + const T& operator*() const { return mValue; } + T* operator->() { return &mValue; } + const T* operator->() const { return &mValue; } + + Parameter& operator=(const T& value) { + mValue = value; + return *this; + } + +protected: + T mValue; +}; + +template +class ParameterBuffer : public Parameter { +public: + ParameterBuffer(sead::Heap* heap, s32 num) { + SEAD_ASSERT(!isBinaryInternalBuffer()); + this->mValue = new (heap) T[num]; + mBufferSize = num; + mBufferAllocated = true; + + for (s32 i = 0; i < num; ++i) + this->mValue[i] = {}; + } + + ~ParameterBuffer() override { freeBuffer(); } + + void freeBuffer() { + if (!mBufferAllocated) + return; + + if (this->mValue) + delete[] this->mValue; + mBufferAllocated = false; + } + + ParameterType getParameterType() const override { + if constexpr (std::is_same()) + return ParameterType::BufferInt; + else if constexpr (std::is_same()) + return ParameterType::BufferF32; + else if constexpr (std::is_same()) + return ParameterType::BufferU32; + else if constexpr (std::is_same()) + return ParameterType::BufferBinary; + else + static_assert(!std::is_same(), "Unknown type"); + } + + const void* ptr() const override { return this->mValue; } + void* ptr() override { return this->mValue; } + u32 size() const override { return sizeof(T) * mBufferSize; } + + void postApplyResource_(const void* data, size_t size) override { + if (isBinaryInternalBuffer()) + return; + this->mValue = data; + mBufferSize = size / sizeof(T); + } + + bool isBinary() const override { return true; } + bool isBinaryInternalBuffer() const override { return mBufferAllocated; } + +protected: + s32 mBufferSize; + bool mBufferAllocated; +}; + +class ParameterDirection3f : public Parameter { +public: + ~ParameterDirection3f() override = default; + +#ifdef SEAD_DEBUG + void genMessageParameter(sead::hostio::Context* context) override; + void listenPropertyEventParameter(sead::hostio::Reflexible* reflexible, + const sead::hostio::PropertyEvent* event) override; +#endif +}; + +template +class ParameterCurve : public ParameterBase { +public: + ParameterCurve(const sead::SafeString& name, const sead::SafeString& label, + IParameterObj* param_obj); + + void reset(); + + bool copy(const ParameterBase& other) override; + void copyUnsafe(const ParameterBase& other) override; + + void writeToXML(sead::XmlElement* element, sead::Heap* heap) override; + bool readFromXML(const sead::XmlElement& element, bool x) override; + + ParameterType getParameterType() const override; + + const void* ptr() const override { return mCurveData.data(); } + void* ptr() override { return mCurveData.data(); } + const void* typePtr() const override { return mCurveData.data(); } + void* typePtr() override { return mCurveData.data(); } + u32 size() const override { return sizeof(mCurveData); } + + ParameterBase* clone(sead::Heap* heap, IParameterObj* obj) const override; + + void postApplyResource_(const void*, size_t size) override; + +#ifdef SEAD_DEBUG + void genMessageParameter(sead::hostio::Context* context) override; + virtual void genMessageParameterUnit(sead::hostio::Context* context, s32, + const sead::SafeString&, const sead::SafeString&); +#endif + + static constexpr u32 cUnitCurveParamNum = 30; + +protected: + std::array, N> mCurves; + std::array mCurveData; +}; + +inline ResParameter getResParameter(const agl::utl::ResParameterObj& obj, + const sead::SafeString& name) { + const s32 idx = obj.searchIndex(ParameterBase::calcHash(name)); + if (idx == -1) + return {}; + + return obj.getResParameter(idx); +} + +inline ResParameterObj getResParameterObj(const agl::utl::ResParameterList& list, + const sead::SafeString& name) { + const s32 idx = list.searchObjIndex(ParameterBase::calcHash(name)); + if (idx == -1) + return {}; + + return list.getResParameterObj(idx); +} + +inline ResParameterList getResParameterList(const agl::utl::ResParameterList& list, + const sead::SafeString& name) { + const s32 idx = list.searchListIndex(ParameterBase::calcHash(name)); + if (idx == -1) + return {}; + + return list.getResParameterList(idx); +} + +} // namespace agl::utl + +#define AGL_UTILS_PARAMETER_H_ +#include "agl/Utils/aglParameterCurve.hpp" +#undef AGL_UTILS_PARAMETER_H_ diff --git a/lib/agl/include/agl/Utils/aglParameterCurve.hpp b/lib/agl/include/agl/Utils/aglParameterCurve.hpp new file mode 100644 index 00000000..5802ed80 --- /dev/null +++ b/lib/agl/include/agl/Utils/aglParameterCurve.hpp @@ -0,0 +1,94 @@ +#pragma once + +#ifndef AGL_UTILS_PARAMETER_H_ +#include "agl/Utils/aglParameter.h" +#endif + +namespace agl::utl { + +template +inline ParameterCurve::ParameterCurve(const sead::SafeString& name, + const sead::SafeString& label, IParameterObj* param_obj) + : ParameterBase(name, label, param_obj) { + reset(); +} + +template +inline void ParameterCurve::reset() { + static f32 s_initialize[9] = {0.0, 0.0, 0.5, 0.5, 0.5, 0.5, 1.0, 1.0, 0.5}; + for (s32 i = 0; i < N; ++i) { + sead::MemUtil::copy(mCurveData[i].f, s_initialize, sizeof(s_initialize)); + for (s32 j = 9; j < cUnitCurveParamNum; ++j) + mCurveData[i].f[j] = 1.0; + mCurves[i].setData(&mCurveData[i], sead::hostio::CurveType::Hermit2D, cUnitCurveParamNum, + 9); + } +} + +template +inline bool ParameterCurve::copy(const ParameterBase& other) { + if (getParameterType() != other.getParameterType()) + return false; + + if (getName() != other.getName()) + return false; + + copyUnsafe(other); + return true; +} + +template +inline void ParameterCurve::copyUnsafe(const ParameterBase& other) { + if (getParameterType() != other.getParameterType()) { + SEAD_ASSERT_MSG(false, "getParameterType() == src.getParameterType()"); + return; + } + + sead::MemUtil::copy(ptr(), other.ptr(), size()); + for (s32 i = 0; i < N; ++i) { + auto& curve = mCurves[i]; + auto& curve_other = static_cast&>(other).mCurves[i]; + curve.setCurveType(curve_other.getCurveType()); + curve.mInfo.numUse = curve_other.mInfo.numUse; + } +} + +template +inline ParameterType ParameterCurve::getParameterType() const { + if constexpr (N == 1) + return ParameterType::Curve1; + else if constexpr (N == 2) + return ParameterType::Curve2; + else if constexpr (N == 3) + return ParameterType::Curve3; + else if constexpr (N == 4) + return ParameterType::Curve4; + else + static_assert(N == 1, "Invalid number of curves"); +} + +template +inline ParameterBase* ParameterCurve::clone(sead::Heap* heap, IParameterObj* obj) const { + auto* instance = new (heap) ParameterCurve(getParameterName(), getLabel(), obj); + sead::MemUtil::copy(instance->mCurveData.data(), mCurveData.data(), sizeof(mCurveData)); + return instance; +} + +template +inline void ParameterCurve::postApplyResource_(const void*, size_t size) { + if (this->size() == size) { + for (s32 i = 0; i < N; ++i) { + mCurves[i].setCurveType(sead::hostio::CurveType(mCurveData[i].curveType)); + mCurves[i].mFloats = mCurveData[i].f; + mCurves[i].mInfo.numFloats = cUnitCurveParamNum; + mCurves[i].setNumUse(mCurveData[i].numUse); + } + } else { + for (s32 i = 0; i < N; ++i) { + mCurves[i].mInfo.numFloats = cUnitCurveParamNum; + mCurves[i].mFloats = mCurveData[i].f; + } + } +} + +} // namespace agl::utl diff --git a/lib/agl/include/agl/Utils/aglParameterIO.h b/lib/agl/include/agl/Utils/aglParameterIO.h new file mode 100644 index 00000000..e4354f17 --- /dev/null +++ b/lib/agl/include/agl/Utils/aglParameterIO.h @@ -0,0 +1,47 @@ +#pragma once + +#include "agl/Utils/aglParameterList.h" + +namespace sead { +class XmlDocument; +} + +namespace agl::utl { + +class IParameterIO : public IParameterList { +public: + IParameterIO(); + IParameterIO(const sead::SafeString& name, u32 version); + ~IParameterIO() override { ; } + + virtual bool save(const sead::SafeString& path, u32) const; + virtual void applyResParameterArchive(ResParameterArchive arc); + virtual void applyResParameterArchiveLerp(ResParameterArchive arc_a, ResParameterArchive arc_b, + f32 t); + + void load(const sead::SafeString& path, bool); + void loadText(const void* data, u32 size, bool); + + bool isCompleteArchive(ResParameterArchive archive, bool) const; + + void genMessageIO(sead::hostio::Context* context, u32); + void listenPropertyEventIO(sead::hostio::Reflexible* reflexible, + sead::hostio::PropertyEvent* event); + +protected: + virtual void callbackInvalidVersion_(ResParameterArchive) {} + +#ifdef SEAD_DEBUG + virtual void writeHeader_(sead::XmlElement* element, sead::Heap* heap) const; +#endif + void save_(const sead::SafeString& path, const sead::XmlDocument* document) const; + + sead::FixedSafeString<64> mType; + u32 mVersion; + void* _a8 = nullptr; + sead::FixedSafeString<256> _b0 = sead::SafeString::cEmptyString; + u32 mResFileSize = 0; + u32 _1cc; +}; + +} // namespace agl::utl diff --git a/lib/agl/include/agl/Utils/aglParameterList.h b/lib/agl/include/agl/Utils/aglParameterList.h new file mode 100644 index 00000000..3f06650e --- /dev/null +++ b/lib/agl/include/agl/Utils/aglParameterList.h @@ -0,0 +1,100 @@ +#pragma once + +#include +#include +#include "agl/Utils/aglResParameter.h" + +namespace sead { +class XmlElement; +} + +namespace agl::utl { + +class IParameterObj; +class ParameterBase; + +class IParameterList { +public: + IParameterList(); + virtual ~IParameterList() { ; } + + void addList(IParameterList* child, const sead::SafeString& name); + void addObj(IParameterObj* child, const sead::SafeString& name); + void clearList(); + void clearObj(); + void removeList(IParameterList* child); + void removeObj(IParameterObj* child); + + IParameterObj* getChildObjHead() const { return mpChildObjHead; } + IParameterObj* getChildObjTail() const { return mpChildObjTail; } + IParameterList* getChildListHead() const { return mpChildListHead; } + IParameterList* getChildListTail() const { return mpChildListTail; } + IParameterList* getNext() const { return mNext; } + IParameterList* getParent() const { return mParent; } + + sead::SafeString getName() const; + u32 getNameHash() const { return mNameHash; } + + void applyResParameterList(ResParameterList list); + void applyResParameterList(ResParameterList list1, ResParameterList list2, f32 t); + + bool isComplete(ResParameterList res, bool) const; + + const char* getTagName(); + void createAttribute(sead::XmlElement* element, sead::Heap* heap) const; + void writeToXML(sead::XmlElement* element, sead::Heap* heap); + bool readFromXML(const sead::XmlElement& element, bool x); + + bool verify() const; + bool verifyList() const; + bool verifyObj() const; + bool verifyList(IParameterList* p_check, IParameterList* other) const; + bool verifyObj(IParameterObj* obj1, IParameterObj* obj2) const; + + void sortByHash(); + +#ifdef SEAD_DEBUG + void genMessageParameter(sead::hostio::Context* context); + void listenPropertyEventParameter(sead::hostio::Reflexible* reflexible, + const sead::hostio::PropertyEvent* event); +#endif + +protected: + virtual bool preWrite_() const { return true; } + virtual void postWrite_() const {} + virtual bool preRead_() { return true; } + virtual void postRead_() {} + virtual bool isApply_(ResParameterList list) const { + return list.getParameterListNameHash() == mNameHash; + } + virtual void callbackNotAppliable_(IParameterObj*, ParameterBase*, ResParameterObj) {} + virtual void callbackNotInterpolatable_(IParameterObj*, ParameterBase*, ResParameterObj, + ResParameterObj, ResParameter, ResParameter, f32) {} + + void setParameterListName_(const sead::SafeString& name); + void applyResParameterList_(bool interpolate, ResParameterList l1, ResParameterList l2, f32 t); + ResParameterObj searchResParameterObj_(ResParameterList res, const IParameterObj& obj) const; + IParameterObj* searchChildParameterObj_(ResParameterObj res, IParameterObj* obj) const; + void applyResParameterObjB_(bool interpolate, ResParameterList res, f32 t); + ResParameterList searchResParameterList_(ResParameterList res, + const IParameterList& list) const; + IParameterList* searchChildParameterList_(ResParameterList res) const; + void applyResParameterListB_(bool interpolate, ResParameterList res, f32 t); + + IParameterObj* mpChildObjHead = nullptr; + IParameterObj* mpChildObjTail = nullptr; + IParameterList* mpChildListHead = nullptr; + IParameterList* mpChildListTail = nullptr; + u32 mNameHash; + IParameterList* mNext = nullptr; + IParameterList* mParent = nullptr; + const char* mName; +}; + +class ParameterList : public IParameterList { +public: + using IParameterList::IParameterList; + ~ParameterList() override { ; } +}; + +} // namespace agl::utl diff --git a/lib/agl/include/agl/Utils/aglParameterObj.h b/lib/agl/include/agl/Utils/aglParameterObj.h new file mode 100644 index 00000000..ce3fe6ba --- /dev/null +++ b/lib/agl/include/agl/Utils/aglParameterObj.h @@ -0,0 +1,100 @@ +#pragma once + +#include +#include +#include "agl/Utils/aglResParameter.h" + +namespace sead { +class XmlElement; +} + +namespace agl::utl { + +class IParameterList; +class ParameterBase; + +class IParameterObj { +public: + IParameterObj(); + virtual ~IParameterObj() { ; } + + void pushBackListNode(ParameterBase* p_node); + void sortByHash(); + + sead::SafeString getName() const; + u32 getNameHash() const { return mNameHash; } + + ParameterBase* getParamListHead() const { return mParamListHead; } + ParameterBase* getParamListTail() const { return mParamListTail; } + u32 getParamListSize() const { return mParamListSize; } + IParameterObj* getNext() const { return mNext; } + + void writeToXML(sead::XmlElement* element, sead::Heap* heap); + bool readFromXML(const sead::XmlElement& element, bool x); + void createAttribute(sead::XmlElement* element, sead::Heap* heap) const; + static const char* getTagName(); + + void applyResParameterObj(ResParameterObj obj1, ResParameterObj obj2, f32 t, + IParameterList* list); + + void applyResParameterObj(ResParameterObj obj, IParameterList* list = nullptr) { + applyResParameterObj_(false, obj, {}, 0.0, list); + } + + bool isComplete(ResParameterObj obj, bool) const; + bool verify() const; + bool verify(ParameterBase* p_check, ParameterBase* other) const; + + void copy(ParameterBase* first, ParameterBase* last, const ParameterBase* src_first, + const ParameterBase* src_last); + void copy(const IParameterObj& obj); + void copyLerp(ParameterBase* first, ParameterBase* last, const ParameterBase* src1_first, + const ParameterBase* src1_last, const ParameterBase* src2_first, + const ParameterBase* src2_last, f32 t); + void copyLerp(const IParameterObj& obj1, const IParameterObj& obj2, f32 t); + +#ifdef SEAD_DEBUG + void genMessageParameter(sead::hostio::Context* context); + void listenPropertyEventParameter(sead::hostio::Reflexible* reflexible, + const sead::hostio::PropertyEvent* event); +#endif + +protected: + friend class IParameterList; + + virtual bool preWrite_() const { return true; } + virtual void postWrite_() const {} + virtual bool preRead_() { return true; } + virtual void postRead_() {} + virtual bool preCopy_() { return true; } + virtual void postCopy_() {} + virtual bool isApply_(ResParameterObj obj) const { + return obj.getParameterObjNameHash() == mNameHash; + } + + void applyResParameterObj_(bool interpolate, ResParameterObj obj1, ResParameterObj obj2, f32 t, + IParameterList* list); + ParameterBase* searchParameter_(u32 hash); + ParameterBase* searchParameter_(u32 hash) const; + + void copy_(ParameterBase* first, ParameterBase* last, const ParameterBase* src_first, + const ParameterBase* src_last); + void copyLerp_(ParameterBase* first, ParameterBase* last, const ParameterBase* src1_first, + const ParameterBase* src1_last, const ParameterBase* src2_first, + const ParameterBase* src2_last, f32 t); + + ParameterBase* mParamListHead = nullptr; + ParameterBase* mParamListTail = nullptr; + u32 mParamListSize = 0; + u32 mNameHash = 0; + IParameterObj* mNext = nullptr; + const char* mName = nullptr; +}; + +class ParameterObj : public IParameterObj { +public: + using IParameterObj::IParameterObj; + ~ParameterObj() override { ; } +}; + +} // namespace agl::utl diff --git a/lib/agl/include/agl/Utils/aglParameterStringMgr.h b/lib/agl/include/agl/Utils/aglParameterStringMgr.h new file mode 100644 index 00000000..fe49d043 --- /dev/null +++ b/lib/agl/include/agl/Utils/aglParameterStringMgr.h @@ -0,0 +1,31 @@ +#pragma once + +#include +#include +#include +#include +#include + +namespace agl::utl { + +class ParameterStringMgr : public sead::hostio::Node { + SEAD_SINGLETON_DISPOSER(ParameterStringMgr) + ParameterStringMgr(); + virtual ~ParameterStringMgr(); + +public: + void initialize(sead::Heap* heap); + const char* appendString(const sead::SafeString& string); + +#ifdef SEAD_DEBUG + void listenPropertyEvent(const sead::hostio::PropertyEvent* event) override; + void genMessage(sead::hostio::Context* context) override; +#endif + +private: + sead::Heap* mHeap = nullptr; + sead::PtrArray mStrings; + sead::CriticalSection mCS; +}; + +} // namespace agl::utl diff --git a/lib/agl/include/agl/Utils/aglResCommon.h b/lib/agl/include/agl/Utils/aglResCommon.h new file mode 100644 index 00000000..4c8be7f2 --- /dev/null +++ b/lib/agl/include/agl/Utils/aglResCommon.h @@ -0,0 +1,43 @@ +#pragma once + +#include +#include + +namespace agl { + +template +struct ResCommon { + bool isValid() const { return mPtr != nullptr; } + + ResDataType* ptr() const { + assertValid(); + return mPtr; + } + + u8* ptrBytes() const { return reinterpret_cast(mPtr); } + + bool isValidMagic() const { + return sead::BitUtil::bitCastPtr(ptr(), 0) == ResDataType::getSignature(); + } + + bool isValidVersion() const { + return sead::BitUtil::bitCastPtr(ptr(), 4) == ResDataType::getVersion(); + } + + void assertValid() const { SEAD_ASSERT(isValid()); } + + // NON_MATCHING: weird control flow + void verify() const { + char* b = reinterpret_cast(mPtr); + assertValid(); + SEAD_ASSERT_MSG(isValidMagic(), "Wrong binary. [%c%c%c%c].", b[0], b[1], b[2], b[3]); + SEAD_ASSERT_MSG(isValidVersion(), "Version error.current:%d binary:%d", + ResDataType::getVersion(), sead::BitUtil::bitCastPtr(ptr(), 4)); + } + + ResDataType* mPtr; +}; + +void ModifyEndianU32(bool big_endian, void* p_data, size_t size); + +} // namespace agl diff --git a/lib/agl/include/agl/Utils/aglResParameter.h b/lib/agl/include/agl/Utils/aglResParameter.h new file mode 100644 index 00000000..e9ffa754 --- /dev/null +++ b/lib/agl/include/agl/Utils/aglResParameter.h @@ -0,0 +1,266 @@ +#pragma once + +#include +#include +#include +#include +#include "agl/Utils/aglResCommon.h" + +namespace sead { +template +class TreeMap; +} + +namespace agl::utl { + +struct ResParameterData { + constexpr u32 getParameterNameHash() const { return name_hash; } + constexpr u32 getOffset() const { return 4 * (offset_and_type & 0xFFFFFF); } + constexpr u32 getType() const { return offset_and_type >> 24; } + + u32 name_hash; + u32 offset_and_type; +}; +static_assert(sizeof(ResParameterData) == 0x8); + +struct ResParameter { + ResParameterData* ptr() const { return mPtr; } + u8* ptrBytes() const { return reinterpret_cast(mPtr); } + + u32 getParameterNameHash() const { return ptr()->getParameterNameHash(); } + + template + T* getData() const { + return reinterpret_cast(ptrBytes() + ptr()->getOffset()); + } + + /// Get the data size in bytes. + size_t getDataSize() const; + + template + bool copyData(T* out) const; + + /// Get the number of elements in the buffer. + /// @warning Only valid for buffer types. + size_t getBufferSize() const { + return *reinterpret_cast(ptrBytes() + ptr()->getOffset() - 4); + } + + ResParameterData* mPtr; +}; + +struct ResParameterObjData { + constexpr u32 getParameterObjNameHash() const { return name_hash; } + constexpr u32 getParametersOffset() const { return 4 * u16(param_offset_and_num); } + constexpr u16 getNumParameters() const { return param_offset_and_num >> 16; } + constexpr bool hasParameters() const { return getNumParameters() != 0; } + + u32 name_hash; + u32 param_offset_and_num; +}; +static_assert(sizeof(ResParameterObjData) == 8); + +struct ResParameterObj { + class Iterator { + public: + Iterator(ResParameterData* ptr, s32 idx) : mIdx(idx), mPtr(ptr) {} + bool operator==(const Iterator& rhs) const { return getIndex() == rhs.getIndex(); } + bool operator!=(const Iterator& rhs) const { return !operator==(rhs); } + s32 getIndex() const { return mIdx; } + ResParameter getParam() const { return {mPtr}; } + ResParameter operator*() const { return getParam(); } + Iterator& operator++() { + ++mIdx; + ++mPtr; + return *this; + } + + private: + s32 mIdx; + ResParameterData* mPtr; + }; + + Iterator begin() const { + if (!ptr()->hasParameters()) + return {nullptr, 0}; + return {reinterpret_cast(ptrBytes() + ptr()->getParametersOffset()), 0}; + } + Iterator end() const { return {nullptr, s32(ptr()->getNumParameters())}; } + + explicit operator bool() const { return ptr() != nullptr; } + ResParameterObjData* ptr() const { return mPtr; } + u8* ptrBytes() const { return reinterpret_cast(mPtr); } + + u32 getParameterObjNameHash() const { return ptr()->getParameterObjNameHash(); } + s32 getNum() const { return ptr()->getNumParameters(); } + + /// Get a parameter by index. The index must be valid. + ResParameter getResParameter(s32 index) const { + SEAD_ASSERT(0 <= index && index < getNum()); + return getResParameter(index, ptr()->getParametersOffset()); + } + + ResParameter getResParameter(s32 index, u32 offset) const { + return {reinterpret_cast(ptrBytes() + offset + + sizeof(ResParameterData) * index)}; + } + + template + T* getParameterData(s32 index) const { + return getResParameter(index).getData(); + } + + /// @returns the index of the specified parameter, or -1 if not found. + s32 searchIndex(u32 param_hash) const; + + ResParameterObjData* mPtr; +}; + +struct ResParameterListData { + constexpr u32 getParameterListNameHash() const { return name_hash; } + constexpr u32 getListsOffset() const { return 4 * u16(list_offset_and_num); } + constexpr u32 getObjectsOffset() const { return 4 * u16(obj_offset_and_num); } + constexpr u32 getNumLists() const { return list_offset_and_num >> 16; } + constexpr s32 getNumObjects() const { return obj_offset_and_num >> 16; } + constexpr bool hasLists() const { return getNumLists() != 0; } + constexpr bool hasObjects() const { return getNumObjects() != 0; } + + u32 name_hash; + u32 list_offset_and_num; + u32 obj_offset_and_num; +}; +static_assert(sizeof(ResParameterListData) == 0xc); + +struct ResParameterList { + class ListIterator { + public: + ListIterator(ResParameterListData* ptr, s32 idx) : mIdx(idx), mPtr(ptr) {} + bool operator==(const ListIterator& rhs) const { return getIndex() == rhs.getIndex(); } + bool operator!=(const ListIterator& rhs) const { return !operator==(rhs); } + s32 getIndex() const { return mIdx; } + ResParameterList getList() const { return {mPtr}; } + ResParameterList operator*() const { return getList(); } + ListIterator& operator++() { + ++mIdx; + ++mPtr; + return *this; + } + + private: + s32 mIdx; + ResParameterListData* mPtr; + }; + + ListIterator listBegin() const { + if (!ptr()->hasLists()) + return {nullptr, 0}; + return {reinterpret_cast(ptrBytes() + ptr()->getListsOffset()), 0}; + } + ListIterator listEnd() const { return {nullptr, s32(ptr()->getNumLists())}; } + + class ObjIterator { + public: + ObjIterator(ResParameterObjData* ptr, s32 idx) : mIdx(idx), mPtr(ptr) {} + bool operator==(const ObjIterator& rhs) const { return getIndex() == rhs.getIndex(); } + bool operator!=(const ObjIterator& rhs) const { return !operator==(rhs); } + s32 getIndex() const { return mIdx; } + ResParameterObj getObj() const { return {mPtr}; } + ResParameterObj operator*() const { return getObj(); } + ObjIterator& operator++() { + ++mIdx; + ++mPtr; + return *this; + } + + private: + s32 mIdx; + ResParameterObjData* mPtr; + }; + + ObjIterator objBegin() const { + if (!ptr()->hasObjects()) + return {nullptr, 0}; + return {reinterpret_cast(ptrBytes() + ptr()->getObjectsOffset()), 0}; + } + ObjIterator objEnd() const { return {nullptr, s32(ptr()->getNumObjects())}; } + + explicit operator bool() const { return ptr() != nullptr; } + ResParameterListData* ptr() const { return mPtr; } + u8* ptrBytes() const { return reinterpret_cast(mPtr); } + + u32 getParameterListNameHash() const { return ptr()->getParameterListNameHash(); } + s32 getResParameterListNum() const { return ptr()->getNumLists(); } + s32 getResParameterObjNum() const { return ptr()->getNumObjects(); } + + /// Get a parameter list by index. The index must be valid. + ResParameterList getResParameterList(s32 index) const { + SEAD_ASSERT(0 <= index && index < getResParameterListNum()); + return getResParameterList(index, ptr()->getListsOffset()); + } + + ResParameterList getResParameterList(s32 index, u32 offset) const { + return {reinterpret_cast(ptrBytes() + offset + + sizeof(ResParameterListData) * index)}; + } + + /// Get a parameter object by index. The index must be valid. + ResParameterObj getResParameterObj(s32 index) const { + SEAD_ASSERT(0 <= index && index < getResParameterObjNum()); + return getResParameterObj(index, ptr()->getObjectsOffset()); + } + + ResParameterObj getResParameterObj(s32 index, u32 offset) const { + return {reinterpret_cast(ptrBytes() + offset + + sizeof(ResParameterObjData) * index)}; + } + + /// @returns the index of the specified list, or -1 if not found. + s32 searchListIndex(u32 list_hash) const; + + /// @returns the index of the specified object, or -1 if not found. + s32 searchObjIndex(u32 obj_hash) const; + + void dump(s32, const sead::TreeMap* name_table) const; + + ResParameterListData* mPtr; +}; + +constexpr std::array HeaderMagic = {{'A', 'A', 'M', 'P'}}; + +enum class ResParameterArchiveFlag : u32 { + LittleEndian = 1 << 0, + Utf8 = 1 << 1, +}; + +struct ResParameterArchiveData { + static u32 getVersion() { return 2; } + static u32 getSignature() { return 'AAMP'; } + + std::array magic; + u32 version; + sead::TypedBitFlag flags; + u32 file_size; + u32 pio_version; + /// Offset to parameter IO (relative to 0x30) + u32 offset_to_pio; + /// Number of lists (including parameter IO) + u32 num_lists; + u32 num_objects; + u32 num_parameters; + u32 data_section_size; + u32 string_section_size; + u32 unk_section_size; +}; +static_assert(sizeof(ResParameterArchiveData) == 0x30); + +struct ResParameterArchive : ResCommon { + ResParameterArchive() = default; + explicit ResParameterArchive(const void* p_data); + + ResParameterList getRootList() const { + return {reinterpret_cast( + ptrBytes() + sizeof(ResParameterArchiveData) + mPtr->offset_to_pio)}; + } +}; + +} // namespace agl::utl diff --git a/lib/agl/include/agl/aglGPUCommon.hpp b/lib/agl/include/agl/aglGPUCommon.hpp new file mode 100644 index 00000000..d0cbe5a4 --- /dev/null +++ b/lib/agl/include/agl/aglGPUCommon.hpp @@ -0,0 +1,29 @@ +#pragma once + +#include + +namespace agl { +enum class MemoryAttribute : u32 { + Default = 0, + _00 = 1 << 0, + _01 = 1 << 1, + CompressibleMemory = 1 << 2, + CpuCached = 1 << 3, + _04 = 1 << 4, + // PHYSICAL, no CPU and GPU access. + MemoryReserved = 1 << 7, + GpuCached = 1 << 8, + + // TODO: More? +}; + +struct GPUMemVoidAddr { + // FIXME: what are thoses? + u64 _0; + u64 _8; + u64 mAddress; + + u64 getGPUMemBlock() const { return mAddress; } +}; + +} // namespace agl \ No newline at end of file diff --git a/lib/agl/include/agl/aglGPUMemBlock.hpp b/lib/agl/include/agl/aglGPUMemBlock.hpp new file mode 100644 index 00000000..1d938858 --- /dev/null +++ b/lib/agl/include/agl/aglGPUMemBlock.hpp @@ -0,0 +1,49 @@ +#pragma once + +#include +#include +#include +#include +#include +#include +#include "aglGPUCommon.hpp" + +namespace agl { + +namespace detail { +class MemoryPool; +class MemoryPoolHeap; +} // namespace detail + +class GPUMemBlockBase { +public: + explicit GPUMemBlockBase(sead::Heap* p_heap); + virtual ~GPUMemBlockBase(); + + void clear(); + void freeBuffer(); + void free(); + void allocBuffer_(u64, sead::Heap*, s32, MemoryAttribute); + bool tryAllocBuffer_(u64, sead::Heap*, s32, MemoryAttribute); + void setBuffer_(u64, void*, void*, MemoryAttribute); + void setVirtual_(u64, sead::Heap*, MemoryAttribute, GPUMemVoidAddr, s32); + void addList(GPUMemBlockBase*); + void setMemoryPool(void*, u64, detail::MemoryPool*); + void setMemoryPoolHeap(void*, u64, detail::MemoryPoolHeap*); + u64 getByteOffset() const; + u64 getMemoryPoolType() const; + + // TODO: the rest of the methods... + +private: + void* mMemoryBuffer; + u64 mMemoryBufferSize; + detail::MemoryPool* mpMemoryPool; + detail::MemoryPoolHeap* mMemoryPoolHeap; + uint8_t mFlags; + GPUMemBlockBase* mpTail; +}; + +static_assert(sizeof(GPUMemBlockBase) == 0x38); + +} // namespace agl diff --git a/lib/agl/include/agl/detail/aglGPUMemBlockMgr.h b/lib/agl/include/agl/detail/aglGPUMemBlockMgr.h new file mode 100644 index 00000000..af0e5148 --- /dev/null +++ b/lib/agl/include/agl/detail/aglGPUMemBlockMgr.h @@ -0,0 +1,98 @@ +#pragma once + +#include +#include +#include +#include +#include +#include +#include +#include +#include + +namespace agl::detail { + +typedef sead::BitFlag32 MemoryPoolDriverBitFlag; + +constexpr s32 VALID_POOL_TYPE_VALUE = -1; +constexpr s32 cGPUAccessMask = 0xF0000000; +constexpr u64 cGPUPhysicalMemorySizeAlignment = 0x1000; + +class MemoryPoolType : MemoryPoolDriverBitFlag { +public: + MemoryPoolType() : MemoryPoolDriverBitFlag() {} + MemoryPoolType(s32 p_value) : MemoryPoolDriverBitFlag(p_value) {} + + MemoryPoolType convert(MemoryAttribute attribute); + + bool IsValid() const { return (*this & cValidPoolType) == cValidPoolType; } + + void MarkValid() { *this = *this | cValidPoolType; } + +private: + static const MemoryPoolType cInvalidPoolType; + static const MemoryPoolType cValidPoolType; +}; + +class MemoryPool { +public: + MemoryPool(); + +private: + NVNmemoryPool mDriverPool; + MemoryPoolType mMemoryType; + uint32_t idk; +}; + +static_assert(sizeof(MemoryPool) == 0x108); + +class GPUMemBlockMgrHeapEx : public sead::hostio::Node, public sead::IDisposer { +public: + GPUMemBlockMgrHeapEx(sead::Heap* p_heap); + ~GPUMemBlockMgrHeapEx() override; + + void finalize(); + +private: + s32 mAllowSharing; + void* m08; + void* m10; + sead::CriticalSection mCS; +}; + +static_assert(sizeof(GPUMemBlockMgrHeapEx) == 0x80); + +enum class GPUMemBlockMgrFlags : u8 { + MemoryPoolRelated = 1 << 0, + EnablePoolSharing = 1 << 1, + Debug = 1 << 2 +}; + +class GPUMemBlockMgr : public sead::hostio::Node { + SEAD_SINGLETON_DISPOSER(GPUMemBlockMgr) +public: + GPUMemBlockMgr(); + virtual ~GPUMemBlockMgr(); + + void initialize(sead::Heap* heap1, sead::Heap* heap2); + void enableSharedMemoryPool(bool enabled); + static u64 calcGPUMemorySize(u64 userSize); + static s32 calcGPUMemoryAlignment(s32 userAlignment); + +#ifdef SEAD_DEBUG + void listenPropertyEvent(const sead::hostio::PropertyEvent* event) override; + void genMessage(sead::hostio::Context* context) override; +#endif + +private: + GPUMemBlockMgrHeapEx* findGPUMemBlockMgrHeapEx_(sead::Heap* p_heap, int* p_outIndex); + + sead::CriticalSection mCS; + sead::PtrArray mMngrHeaps; + size_t mMinBlockSize; + sead::TypedBitFlag mFlags; +}; + +static_assert(sizeof(GPUMemBlockMgr) == 0x88); + +} // namespace agl::detail diff --git a/lib/agl/include/agl/driver/aglGraphicsDriverMgr.h b/lib/agl/include/agl/driver/aglGraphicsDriverMgr.h new file mode 100644 index 00000000..11780475 --- /dev/null +++ b/lib/agl/include/agl/driver/aglGraphicsDriverMgr.h @@ -0,0 +1,42 @@ +#pragma once + +#include +#include + +namespace agl { +class DrawContext; +class DisplayList; +} // namespace agl + +namespace agl::driver { + +class GraphicsDriverMgr : public sead::hostio::Node { + SEAD_SINGLETON_DISPOSER(GraphicsDriverMgr) +public: + GraphicsDriverMgr(); + virtual ~GraphicsDriverMgr(); + + void waitDrawDone() const; + void dumpInfo() const; + void setPointLimits(agl::DrawContext* draw_context, float min, float max) const; + void setPointSize(agl::DrawContext* draw_context, float point_size) const; + void setLineWidth(agl::DrawContext* draw_context, float line_width) const; + + agl::DisplayList* getDefaultCommandBuffer(); + +#ifdef SEAD_DEBUG + void listenPropertyEvent(const sead::hostio::PropertyEvent* event) override; + void genMessage(sead::hostio::Context* context) override; +#endif + +protected: + void initialize_(sead::Heap p_heap); + +private: + agl::DisplayList* mDefaultCommandBuffer; + void* _30; +}; + +static_assert(sizeof(GraphicsDriverMgr) == 0x38); + +} // namespace agl::driver diff --git a/lib/agl/include/agl/driver/aglNVNMgr.h b/lib/agl/include/agl/driver/aglNVNMgr.h new file mode 100644 index 00000000..dbd4b2e4 --- /dev/null +++ b/lib/agl/include/agl/driver/aglNVNMgr.h @@ -0,0 +1,22 @@ +#pragma once + +#include +#include +#include "agl/driver/aglGraphicsDriverMgr.h" + +namespace agl::driver { + +class NVNMgr : public GraphicsDriverMgr { + // TODO: This is wrong and should actually touch the GraphicsDriverMgr implementation + SEAD_SINGLETON_DISPOSER(NVNMgr) +public: + NVNMgr(); + ~NVNMgr() override; + +private: +}; + +// TODO: need sead::Graphics reversing... +// static_assert(sizeof(NVNMgr) == 0x548); + +}; // namespace agl::driver \ No newline at end of file diff --git a/lib/agl/include/agl/g3d/aglNW4FToNN.h b/lib/agl/include/agl/g3d/aglNW4FToNN.h new file mode 100644 index 00000000..79e39fbd --- /dev/null +++ b/lib/agl/include/agl/g3d/aglNW4FToNN.h @@ -0,0 +1,15 @@ +#pragma once + +namespace nn::g3d { +class ResFile; +} + +namespace agl::g3d { + +class ResFile { +public: + static void BindTexture(nn::g3d::ResFile*, nn::g3d::ResFile*); + static void Cleanup(nn::g3d::ResFile*); +}; + +} // namespace agl::g3d diff --git a/lib/agl/src/Utils/aglAtomicPtrArray.cpp b/lib/agl/src/Utils/aglAtomicPtrArray.cpp new file mode 100644 index 00000000..48b2449b --- /dev/null +++ b/lib/agl/src/Utils/aglAtomicPtrArray.cpp @@ -0,0 +1,84 @@ +#include "agl/Utils/aglAtomicPtrArray.h" +#include +#include + +namespace agl::detail { + +void AtomicPtrArrayImpl::setBuffer(s32 ptrNumMax, void* buf) { + if (ptrNumMax >= 1) { + if (!buf) { + SEAD_ASSERT_MSG(false, "buf is null"); + return; + } + + mPtrs = static_cast(buf); + mPtrNum = 0; + mPtrNumMax = ptrNumMax; + } else { + SEAD_ASSERT_MSG(false, "ptrNumMax[%d] must be larger than zero", ptrNumMax); + } +} + +void AtomicPtrArrayImpl::allocBuffer(s32 ptrNumMax, sead::Heap* heap, s32 alignment) { + SEAD_ASSERT(mPtrs == nullptr); + + if (ptrNumMax >= 1) + setBuffer(ptrNumMax, new (heap, alignment) u8[s32(sizeof(void*)) * ptrNumMax]); + else + SEAD_ASSERT_MSG(false, "ptrNumMax[%d] must be larger than zero", ptrNumMax); +} + +void AtomicPtrArrayImpl::freeBuffer() { + if (isBufferReady()) { + delete[] mPtrs; + mPtrs = nullptr; + mPtrNum = 0; + mPtrNumMax = 0; + } +} + +void AtomicPtrArrayImpl::erase(s32 pos, s32 count) { + if (pos < 0) { + SEAD_ASSERT_MSG(false, "illegal position[%d]", pos); + return; + } + + if (count < 0) { + SEAD_ASSERT_MSG(false, "illegal number[%d]", count); + return; + } + + const s32 end_pos = pos + count; + const s32 ptr_num = mPtrNum; + + if (pos + count > ptr_num) { + SEAD_ASSERT_MSG(false, "pos[%d] + num[%d] exceed size[%d]", pos, count, ptr_num); + return; + } + + if (ptr_num > end_pos) + sead::MemUtil::copyOverlap(mPtrs + pos, mPtrs + end_pos, + sizeof(void*) * (ptr_num - end_pos)); + + mPtrNum = ptr_num - count; +} + +// NON_MATCHING: semantically equivalent (Fisher–Yates) +void AtomicPtrArrayImpl::shuffle(sead::Random* random) { + SEAD_ASSERT(random); + for (s32 i = mPtrNum - 1; i > 0; --i) + swap(i, random->getS32Range(0, i + 1)); +} + +// NON_MATCHING: Nintendo implemented a sorting algorithm manually +void AtomicPtrArrayImpl::sort(CompareCallbackImpl cmp) { + std::sort(mPtrs, mPtrs + mPtrNum, [cmp](void* a, void* b) { return cmp(a, b) < 0; }); +} + +// NON_MATCHING: Nintendo implemented heap sort manually +void AtomicPtrArrayImpl::heapSort(CompareCallbackImpl cmp) { + std::make_heap(mPtrs, mPtrs + mPtrNum); + std::sort_heap(mPtrs, mPtrs + mPtrNum, [cmp](void* a, void* b) { return cmp(a, b) < 0; }); +} + +} // namespace agl::detail diff --git a/lib/agl/src/Utils/aglParameter.cpp b/lib/agl/src/Utils/aglParameter.cpp new file mode 100644 index 00000000..252b3305 --- /dev/null +++ b/lib/agl/src/Utils/aglParameter.cpp @@ -0,0 +1,436 @@ +#include "agl/Utils/aglParameter.h" +#include +#include +#include +#include +#include +#include +#include "agl/Utils/aglParameterObj.h" +#include "agl/Utils/aglParameterStringMgr.h" + +namespace agl::utl { + +static constexpr const char* sParameterTypeNames[] = { + "bool", "f32", "int", "vec2", "vec3", "vec4", "color", + "string32", "string64", "curve1", "curve2", "curve3", "curve4", "buffer_int", + "buffer_f32", "string256", "quat", "u32", "buffer_u32", "buffer_binary", "stringRef", +}; + +u32 ParameterBase::calcHash(const sead::SafeString& key) { + return sead::HashCRC32::calcStringHash(key); +} + +ParameterBase::ParameterBase() { + initializeListNode("default", "parameter", "", nullptr); +} + +ParameterBase::ParameterBase(const sead::SafeString& name, const sead::SafeString& label, + IParameterObj* param_obj) { + initializeListNode(name, label, "", param_obj); +} + +ParameterBase::ParameterBase(const sead::SafeString& name, const sead::SafeString& label, + const sead::SafeString& meta, IParameterObj* param_obj) { + initializeListNode(name, label, meta, param_obj); +} + +void ParameterBase::initializeListNode(const sead::SafeString& name, const sead::SafeString& label, + const sead::SafeString& meta, IParameterObj* param_obj) { + mNext = nullptr; + +#ifdef SEAD_DEBUG + if (ParameterStringMgr::instance()) { + mName = ParameterStringMgr::instance()->appendString(name); + mLabel = ParameterStringMgr::instance()->appendString(label); + mMeta = ParameterStringMgr::instance()->appendString(meta); + } else { + mName = nullptr; + mLabel = nullptr; + mMeta = nullptr; + } +#endif + + mNameHash = calcHash(name); + + if (param_obj) + param_obj->pushBackListNode(this); +} + +sead::SafeString ParameterBase::getParameterName() const { +#ifdef SEAD_DEBUG + return mName; +#else + return sead::SafeString::cEmptyString; +#endif +} + +sead::SafeString ParameterBase::getLabel() const { +#ifdef SEAD_DEBUG + return mLabel; +#else + return sead::SafeString::cEmptyString; +#endif +} + +sead::SafeString ParameterBase::getMeta() const { +#ifdef SEAD_DEBUG + return mMeta; +#else + return sead::SafeString::cEmptyString; +#endif +} + +const char* ParameterBase::getTagName() { + return "param"; +} + +const char* ParameterBase::getAttributeNameString() { + return "name"; +} + +const char* ParameterBase::getAttributeTypeString() { + return "type"; +} + +const char* ParameterBase::getAttributeValueString() { + return "value"; +} + +const char* ParameterBase::getParameterTypeName(ParameterType type) { + return sParameterTypeNames[u32(type)]; +} + +// NON_MATCHING: Clang emits a switch... +bool ParameterBase::isSafeType(ParameterType type) const { + if (getParameterType() == type) + return true; + + constexpr std::pair pairs[] = { + {ParameterType::String64, ParameterType::String32}, + {ParameterType::String32, ParameterType::String64}, + {ParameterType::String256, ParameterType::String32}, + {ParameterType::String256, ParameterType::String64}, + {ParameterType::String32, ParameterType::String256}, + {ParameterType::String64, ParameterType::String256}, + }; + + for (const auto pair : pairs) { + if (type == pair.first && getParameterType() == pair.second) + return true; + } + + if (getParameterType() == ParameterType::StringRef && + (type == ParameterType::String32 || type == ParameterType::String64 || + type == ParameterType::String256)) { + return true; + } + + return false; +} + +bool ParameterBase::verifyType(ParameterType type) const { + if (isSafeType(type)) + return true; + + sead::BufferingPrintFormatter ss; + ss << "!!! AGL ERROR !!! Instance ParameterType = %s Resource ParameterType = %s\n" + << sParameterTypeNames[u32(getParameterType())] << sParameterTypeNames[u32(type)] + << sead::flush; + return false; +} + +bool ParameterBase::copy(const ParameterBase& other) { + if (getParameterType() != other.getParameterType() || mNameHash != other.mNameHash) + return false; + + copyUnsafe(other); + return true; +} + +void ParameterBase::copyUnsafe(const ParameterBase& other) { + if (other.getParameterType() == ParameterType::StringRef) { + auto* source = static_cast(other.typePtr()); + auto* dest = static_cast(typePtr()); + *dest = *source; + return; + } + + auto* dest = ptrT(); + auto* src = other.ptrT(); + const s32 n = size(); + for (s32 i = 0; i < n; ++i) + *dest++ = *src++; +} + +template <> +void ParameterBase::copyLerp_(const ParameterBase& param1, const ParameterBase& param2, + f32 t) { + *ptrT() = sead::lerp(*param1.ptrT(), *param2.ptrT(), t); +} + +template <> +void ParameterBase::copyLerp_(const ParameterBase& param1, const ParameterBase& param2, + f32 t) { + sead::QuatCalcCommon::slerpTo(*ptrT(), *param1.ptrT(), + *param2.ptrT(), t); +} + +template +static void lerpVec_(T& v_dest, const T& v1, const T& v2, f32 t) { + for (size_t i = 0; i < v_dest.e.size(); ++i) + v_dest.e[i] = sead::lerp(v1.e[i], v2.e[i], t); +} + +template +static void copyLerpVec_(ParameterBase& dest, const ParameterBase& param1, + const ParameterBase& param2, f32 t) { + lerpVec_(*dest.ptrT(), *param1.ptrT(), *param2.ptrT(), t); +} + +bool ParameterBase::copyLerp(const ParameterBase& param1, const ParameterBase& param2, f32 t) { + if (getParameterType() != param1.getParameterType() || mNameHash != param1.mNameHash) + return false; + + if (getParameterType() != param2.getParameterType() || mNameHash != param2.mNameHash) + return false; + + switch (getParameterType()) { + case ParameterType::Bool: + case ParameterType::Int: + case ParameterType::String32: + case ParameterType::String64: + case ParameterType::String256: + case ParameterType::U32: + copyUnsafe(param1); + return true; + case ParameterType::F32: + copyLerp_(param1, param2, t); + return true; + case ParameterType::Vec2: + copyLerpVec_(*this, param1, param2, t); + return true; + case ParameterType::Vec3: + copyLerpVec_(*this, param1, param2, t); + return true; + case ParameterType::Vec4: + copyLerpVec_(*this, param1, param2, t); + return true; + case ParameterType::Color: { + auto& color = *ptrT(); + color.setLerp(*param1.ptrT(), *param2.ptrT(), t); + return true; + } + case ParameterType::Curve1: + case ParameterType::Curve2: + case ParameterType::Curve3: + case ParameterType::Curve4: + case ParameterType::BufferInt: + case ParameterType::BufferF32: + case ParameterType::BufferU32: + case ParameterType::BufferBinary: + case ParameterType::StringRef: + case ParameterType::Special: + return true; + case ParameterType::Quat: + copyLerp_(param1, param2, t); + return true; + default: + SEAD_ASSERT_MSG(false, "%d", int(getParameterType())); + return true; + } +} + +static void applyResourceSimple_(ParameterBase& param, const ResParameter& res) { + void* dest = param.ptr(); + const void* src = res.getData(); + + const size_t data_size = param.size(); + const size_t res_data_size = res.getDataSize(); + const auto copy_size = data_size < res_data_size ? data_size : res_data_size; + + sead::MemUtil::copy(dest, src, copy_size); +} + +void ParameterBase::applyResource(ResParameter res) { +#ifdef SEAD_DEBUG + if (!verifyType(ParameterType(res.ptr()->getType()))) + return; +#endif + + if (getParameterType() == ParameterType::Bool) { + const bool value = *res.getData() != 0; + *ptrT() = value; + } else if (isBinaryInternalBuffer()) { + if (getParameterType() == ParameterType::StringRef) + *static_cast(typePtr()) = res.getData(); + else + applyResourceSimple_(*this, res); + } + + postApplyResource_(res.getData(), res.getDataSize()); +} + +void ParameterBase::applyResource(ResParameter res, f32 t) { +#ifdef SEAD_DEBUG + if (!verifyType(ParameterType(res.ptr()->getType()))) + return; +#endif + + switch (getParameterType()) { + case ParameterType::Bool: + *ptrT() = *res.getData() != 0; + break; + case ParameterType::F32: { + f32 x; + sead::MemUtil::copy(&x, res.getData(), size()); + *ptrT() += x * t; + break; + } + case ParameterType::Int: + case ParameterType::String32: + case ParameterType::String64: + case ParameterType::String256: + case ParameterType::U32: + applyResourceSimple_(*this, res); + break; + case ParameterType::Vec2: { + sead::Vector2f vec; + sead::MemUtil::copy(&vec, res.getData(), size()); + *ptrT() += vec * t; + break; + } + case ParameterType::Vec3: { + sead::Vector3f vec; + sead::MemUtil::copy(&vec, res.getData(), size()); + *ptrT() += vec * t; + break; + } + case ParameterType::Vec4: { + sead::Vector4f vec; + sead::MemUtil::copy(&vec, res.getData(), size()); + *ptrT() += vec * t; + break; + } + case ParameterType::Color: { + sead::Color4f color; + sead::MemUtil::copy(&color, res.getData(), size()); + *ptrT() += color * sead::Color4f{t, t, t, t}; + break; + } + case ParameterType::Curve1: + case ParameterType::Curve2: + case ParameterType::Curve3: + case ParameterType::Curve4: + case ParameterType::Special: + break; + case ParameterType::BufferInt: + case ParameterType::BufferF32: + case ParameterType::BufferU32: + case ParameterType::BufferBinary: + if (isBinaryInternalBuffer()) + applyResourceSimple_(*this, res); + break; + case ParameterType::Quat: { + sead::Quatf quat; + sead::MemUtil::copy(&quat, res.getData(), size()); + auto* target = ptrT(); + sead::QuatCalcCommon::slerpTo(*target, *target, quat, t); + break; + } + case ParameterType::StringRef: + *static_cast(typePtr()) = res.getData(); + break; + default: + SEAD_ASSERT_MSG(false, "%d", int(getParameterType())); + break; + } + + postApplyResource_(res.getData(), res.getDataSize()); +} + +bool ParameterBase::isInterpolatable() const { + const auto type = getParameterType(); + return type == ParameterType::F32 || type == ParameterType::Vec2 || + type == ParameterType::Vec3 || type == ParameterType::Vec4 || + type == ParameterType::Color || type == ParameterType::Quat; +} + +size_t ParameterBase::binarize(void* binary) const { + SEAD_ASSERT(binary != nullptr); + + size_t binary_size; + if (getParameterType() != ParameterType::Bool) { + binary_size = calcBinarizeSize(); + sead::MemUtil::copy(binary, ptr(), binary_size); + } else { + binary_size = sizeof(u32); + *static_cast(binary) = *ptrT(); + } + return binary_size; +} + +bool ParameterBase::makeZero() { + switch (getParameterType()) { + case ParameterType::F32: + *ptrT() = 0; + return true; + case ParameterType::Vec2: + *ptrT() = {0, 0}; + return true; + case ParameterType::Vec3: + *ptrT() = {0, 0, 0}; + return true; + case ParameterType::Vec4: + *ptrT() = {0, 0, 0, 0}; + return true; + case ParameterType::Color: + *ptrT() = {0, 0, 0, 0}; + return true; + case ParameterType::Quat: { + auto* quat = ptrT(); + quat->z = 0; + quat->w = 1; + quat->x = quat->y = 0; + return true; + } + case ParameterType::Bool: + case ParameterType::Int: + case ParameterType::String32: + case ParameterType::String64: + case ParameterType::Curve1: + case ParameterType::Curve2: + case ParameterType::Curve3: + case ParameterType::Curve4: + case ParameterType::BufferInt: + case ParameterType::BufferF32: + case ParameterType::String256: + case ParameterType::U32: + case ParameterType::BufferU32: + case ParameterType::BufferBinary: + case ParameterType::StringRef: + case ParameterType::Special: + return false; + } + return false; +} + +// TODO: Remove these explicit instantiations once ParameterBase::createByTypeName is implemented. +template class Parameter; +template class Parameter; +template class Parameter; +template class Parameter; +template class Parameter; +template class Parameter; +template class Parameter; +template class Parameter>; +template class Parameter>; +template class Parameter>; +template class Parameter; +template class Parameter; +template class Parameter; +template class ParameterCurve<1>; +template class ParameterCurve<2>; +template class ParameterCurve<3>; +template class ParameterCurve<4>; + +} // namespace agl::utl diff --git a/lib/agl/src/Utils/aglParameterIO.cpp b/lib/agl/src/Utils/aglParameterIO.cpp new file mode 100644 index 00000000..e73dd47b --- /dev/null +++ b/lib/agl/src/Utils/aglParameterIO.cpp @@ -0,0 +1,48 @@ +#include "agl/Utils/aglParameterIO.h" +#include + +namespace agl::utl { + +IParameterIO::IParameterIO() { + _1cc = 1; + mType = "xml"; + mVersion = 0; + setParameterListName_("param_root"); +} + +IParameterIO::IParameterIO(const sead::SafeString& name, u32 version) { + _1cc = 0; + mType = name; + mVersion = version; + setParameterListName_("param_root"); +} + +void IParameterIO::applyResParameterArchive(ResParameterArchive arc) { + SEAD_ASSERT(arc.isValid()); + mResFileSize = arc.mPtr->file_size; + + if (mVersion != arc.mPtr->pio_version) + callbackInvalidVersion_(arc); + + applyResParameterList(arc.getRootList()); +} + +void IParameterIO::applyResParameterArchiveLerp(ResParameterArchive arc_a, + ResParameterArchive arc_b, f32 t) { + SEAD_ASSERT(arc_a.isValid()); + SEAD_ASSERT(arc_b.isValid()); + + if (mVersion != arc_a.mPtr->pio_version) + callbackInvalidVersion_(arc_a); + + if (mVersion != arc_b.mPtr->pio_version) + callbackInvalidVersion_(arc_b); + + applyResParameterList(arc_a.getRootList(), arc_b.getRootList(), t); +} + +bool IParameterIO::isCompleteArchive(ResParameterArchive archive, bool x) const { + return isComplete(archive.getRootList(), x); +} + +} // namespace agl::utl diff --git a/lib/agl/src/Utils/aglParameterList.cpp b/lib/agl/src/Utils/aglParameterList.cpp new file mode 100644 index 00000000..d86421ff --- /dev/null +++ b/lib/agl/src/Utils/aglParameterList.cpp @@ -0,0 +1,339 @@ +#include "agl/Utils/aglParameterList.h" +#include +#include +#include +#include "agl/Utils/aglParameter.h" +#include "agl/Utils/aglParameterObj.h" +#include "agl/Utils/aglParameterStringMgr.h" + +namespace agl::utl { + +IParameterList::IParameterList() { + setParameterListName_(sead::SafeString::cEmptyString); +} + +void IParameterList::setParameterListName_(const sead::SafeString& name) { +#ifdef SEAD_DEBUG + if (ParameterStringMgr::instance()) + mName = ParameterStringMgr::instance()->appendString(name); + else + mName = nullptr; +#endif + + mNameHash = ParameterBase::calcHash(name); +} + +void IParameterList::addList(IParameterList* child, const sead::SafeString& name) { + SEAD_ASSERT(child != nullptr); + child->setParameterListName_(name); + + (!mpChildListTail ? mpChildListHead : mpChildListTail->mNext) = child; + mpChildListTail = child; + child->mParent = this; +} + +void IParameterList::addObj(IParameterObj* child, const sead::SafeString& name) { + SEAD_ASSERT(child != nullptr); + +#ifdef SEAD_DEBUG + if (ParameterStringMgr::instance()) + child->mName = ParameterStringMgr::instance()->appendString(name); +#endif + child->mNameHash = ParameterBase::calcHash(name); + + (!mpChildObjTail ? mpChildObjHead : mpChildObjTail->mNext) = child; + mpChildObjTail = child; +} + +void IParameterList::clearList() { + for (auto* i = mpChildListHead; i;) { + auto* next = i->mNext; + i->mNext = nullptr; + i = next; + } + mpChildListHead = nullptr; + mpChildListTail = nullptr; +} + +void IParameterList::clearObj() { + for (auto* i = mpChildObjHead; i;) { + auto* next = i->mNext; + i->mNext = nullptr; + i = next; + } + mpChildObjHead = nullptr; + mpChildObjTail = nullptr; +} + +void IParameterList::removeList(IParameterList* child) { + SEAD_ASSERT(child != nullptr); + auto* i = mpChildListHead; + if (!i) + return; + + IParameterList* prev = nullptr; + while (true) { + if (i == child) + break; + prev = i; + i = i->mNext; + if (!i) + return; + } + + (prev ? prev->mNext : mpChildListHead) = child->mNext; + if (!child->mNext) { + SEAD_ASSERT(mpChildListTail == child); + mpChildListTail = prev; + } + child->mNext = nullptr; +} + +void IParameterList::removeObj(IParameterObj* child) { + SEAD_ASSERT(child != nullptr); + auto* i = mpChildObjHead; + if (!i) + return; + + IParameterObj* prev = nullptr; + while (true) { + if (i == child) + break; + prev = i; + i = i->mNext; + if (!i) + return; + } + + (prev ? prev->mNext : mpChildObjHead) = child->mNext; + if (!child->mNext) { + SEAD_ASSERT(mpChildObjTail == child); + mpChildObjTail = prev; + } + child->mNext = nullptr; +} + +void IParameterList::applyResParameterList(ResParameterList list) { + return applyResParameterList_(false, list, {}, 0.0); +} + +void IParameterList::applyResParameterList(ResParameterList list1, ResParameterList list2, f32 t) { + if (list1.ptr() && t <= 0.0) + return applyResParameterList_(false, list1, {}, 0.0); + if (list2.ptr() && t >= 1.0) + return applyResParameterList_(false, list2, {}, 0.0); + return applyResParameterList_(true, list1, list2, t); +} + +bool IParameterList::isComplete(ResParameterList res, bool) const { + if (!res.ptr()) + return false; + + s32 obj_count = 0; + for (auto* i = mpChildObjHead; i; i = i->mNext) { + if (res.searchObjIndex(i->mNameHash) == -1) + return false; + ++obj_count; + } + + s32 list_count = 0; + for (auto* i = mpChildListHead; i; i = i->mNext) { + if (res.searchListIndex(i->mNameHash) == -1) + return false; + ++list_count; + } + + return obj_count == res.getResParameterObjNum() && list_count == res.getResParameterListNum(); +} + +sead::SafeString IParameterList::getName() const { +#ifdef SEAD_DEBUG + return mName; +#else + return sead::SafeString::cEmptyString; +#endif +} + +const char* IParameterList::getTagName() { + return "param_list"; +} + +bool IParameterList::verify() const { + bool ok = true; + ok &= verifyList(); + ok &= verifyObj(); + for (auto* i = mpChildListHead; i; i = i->mNext) + ok &= i->verify(); + for (auto* i = mpChildObjHead; i; i = i->mNext) + ok &= i->verify(); + return ok; +} + +bool IParameterList::verifyList() const { + bool ret = true; + for (auto* i = mpChildListHead; i; i = i->mNext) + ret &= verifyList(i, i->mNext); + return ret; +} + +bool IParameterList::verifyObj() const { + bool ret = true; + for (auto* i = mpChildObjHead; i; i = i->mNext) + ret &= verifyObj(i, i->mNext); + return ret; +} + +bool IParameterList::verifyList(IParameterList* p_check, IParameterList* other) const { + SEAD_ASSERT(p_check != nullptr); + auto* list = other; + bool ok = true; + while (list) { + if (p_check->getNameHash() == list->getNameHash()) { + sead::BufferingPrintFormatter ss; + ss << "Same hash code at [%s] and [%s]. Please change.\n" + << p_check->getName().cstr() << list->getName().cstr() << sead::flush; + ok = false; + } + list = list->mNext; + } + return ok; +} + +bool IParameterList::verifyObj(IParameterObj* p_check, IParameterObj* other) const { + SEAD_ASSERT(p_check != nullptr); + auto* list = other; + bool ok = true; + while (list) { + if (p_check->getNameHash() == list->getNameHash()) { + sead::BufferingPrintFormatter ss; + ss << "Same hash code at [%s] and [%s]. Please change.\n" + << p_check->getName().cstr() << list->getName().cstr() << sead::flush; + ok = false; + } + list = list->mNext; + } + return ok; +} + +ResParameterObj IParameterList::searchResParameterObj_(ResParameterList res, + const IParameterObj& obj) const { + if (!res.ptr()) + return {}; + for (auto it = res.objBegin(), end = res.objEnd(); it != end; ++it) { + if (obj.isApply_(*it)) + return *it; + } + return {}; +} + +IParameterObj* IParameterList::searchChildParameterObj_(ResParameterObj res, + IParameterObj* obj) const { + if (!res.ptr() || !mpChildObjHead) + return nullptr; + + auto* start = obj ? obj : mpChildObjHead; + auto* child = start; + while (!child->isApply_(res)) { + child = child->mNext; + if (!child) + child = mpChildObjHead; + + if (child == start) + return nullptr; + } + return child; +} + +ResParameterList IParameterList::searchResParameterList_(ResParameterList res, + const IParameterList& list) const { + if (!res.ptr()) + return {}; + for (auto it = res.listBegin(), end = res.listEnd(); it != end; ++it) { + if (list.isApply_(it.getList())) + return it.getList(); + } + return {}; +} + +IParameterList* IParameterList::searchChildParameterList_(ResParameterList res) const { + if (!res.ptr()) + return nullptr; + + for (auto* child = mpChildListHead; child; child = child->mNext) { + if (child->isApply_(res)) + return child; + } + return nullptr; +} + +void IParameterList::applyResParameterObjB_(bool interpolate, ResParameterList res, f32 t) { + if (!res.ptr()) + return; + IParameterObj* obj = nullptr; + for (auto it = res.objBegin(), end = res.objEnd(); it != end; ++it) { + auto* result = searchChildParameterObj_(*it, obj); + if (result) { + result->applyResParameterObj_(interpolate, {}, *it, t, this); + obj = result; + } + } +} + +void IParameterList::applyResParameterListB_(bool interpolate, ResParameterList res, f32 t) { + if (!res.ptr()) + return; + for (auto it = res.listBegin(), end = res.listEnd(); it != end; ++it) { + auto* list = searchChildParameterList_(*it); + if (list) + list->applyResParameterList_(interpolate, {}, *it, t); + } +} + +void IParameterList::applyResParameterList_(bool interpolate, ResParameterList l1, + ResParameterList l2, f32 t) { + if (!preRead_()) + return; + + // Recursively apply all parameter objects. + if (l1.ptr()) { + IParameterObj* obj = nullptr; + for (auto it = l1.objBegin(), end = l1.objEnd(); it != end; ++it) { + auto* child = searchChildParameterObj_(*it, obj); + if (child) { + const auto obj2 = searchResParameterObj_(l2, *child); + child->applyResParameterObj_(interpolate, *it, obj2, t, this); + obj = child; + } else { + applyResParameterObjB_(interpolate, l2, t); + } + } + } else { + applyResParameterObjB_(interpolate, l2, t); + } + + // Now recursively apply all parameter lists. + if (l1.ptr()) { + for (auto it = l1.listBegin(), end = l1.listEnd(); it != end; ++it) { + auto* child = searchChildParameterList_(*it); + if (l2.ptr()) { + if (child) { + const auto other_list = searchResParameterList_(l2, *child); + child->applyResParameterList_(interpolate, *it, other_list, t); + } else { + applyResParameterListB_(interpolate, l2, t); + } + } else { + if (child) + child->applyResParameterList_(interpolate, *it, {}, t); + else + applyResParameterListB_(interpolate, {}, t); + } + } + } else { + applyResParameterListB_(interpolate, l2, t); + } + + postRead_(); +} + +} // namespace agl::utl diff --git a/lib/agl/src/Utils/aglParameterObj.cpp b/lib/agl/src/Utils/aglParameterObj.cpp new file mode 100644 index 00000000..4b391403 --- /dev/null +++ b/lib/agl/src/Utils/aglParameterObj.cpp @@ -0,0 +1,233 @@ +#include "agl/Utils/aglParameterObj.h" +#include +#include +#include "agl/Utils/aglParameter.h" + +namespace agl::utl { + +IParameterObj::IParameterObj() = default; + +void IParameterObj::pushBackListNode(ParameterBase* p_node) { + SEAD_ASSERT(p_node != nullptr); + + ParameterBase** ptr; + if (mParamListTail) { + ptr = &mParamListTail->mNext; + } else { + ptr = &mParamListHead; + mParamListTail = p_node; + } + + *ptr = p_node; + mParamListTail = p_node; + ++mParamListSize; +} + +const char* IParameterObj::getTagName() { + return "param_array"; +} + +sead::SafeString IParameterObj::getName() const { +#ifdef SEAD_DEBUG + return mName; +#else + return sead::SafeString::cEmptyString; +#endif +} + +void IParameterObj::applyResParameterObj(ResParameterObj obj1, ResParameterObj obj2, f32 t, + IParameterList* list) { + if (obj1.ptr() && t <= 0.0f) { + applyResParameterObj_(false, obj1, {}, 0.0f, list); + return; + } + + if (obj2.ptr() && t >= 1.0f) { + applyResParameterObj_(false, obj2, {}, 0.0f, list); + return; + } + + applyResParameterObj_(true, obj1, obj2, t, list); +} + +bool IParameterObj::isComplete(ResParameterObj obj, bool check_values) const { + if (!obj.ptr() || obj.getNum() != mParamListSize) + return false; + + ParameterBase* param = mParamListHead; + + while (param) { + const auto idx = obj.searchIndex(param->getNameHash()); + if (idx == -1) + return false; + + if (check_values) { + const auto res = obj.getResParameter(idx); + + // As usual, booleans are a special case. + if (ParameterType(res.ptr()->getType()) == ParameterType::Bool) { + const bool value = *res.getData() != 0; + if (value != *param->ptrT()) + return false; + } else { + if (sead::MemUtil::compare(param->ptr(), res.getData(), res.getDataSize())) + return false; + } + } + + param = param->mNext; + } + return true; +} + +bool IParameterObj::verify() const { + bool ret = true; + for (auto* param = mParamListHead; param; param = param->mNext) + ret &= verify(param, param->mNext); + return ret; +} + +bool IParameterObj::verify(ParameterBase* p_check, ParameterBase* other) const { + SEAD_ASSERT(p_check != nullptr); + auto* param = other; + bool ok = true; + while (param) { + if (p_check->getNameHash() == param->getNameHash()) { + sead::BufferingPrintFormatter ss; + ss << "Same hash code at [%s] and [%s]. Please change.\n" + << p_check->getName().cstr() << param->getName().cstr() + << sead::flush; + ok = false; + } + param = param->mNext; + } + return ok; +} + +ParameterBase* IParameterObj::searchParameter_(u32 hash) { + for (auto* param = mParamListHead; param; param = param->mNext) { + if (param->getNameHash() == hash) + return param; + } + return nullptr; +} + +ParameterBase* IParameterObj::searchParameter_(u32 hash) const { + for (auto* param = mParamListHead; param; param = param->mNext) { + if (param->getNameHash() == hash) + return param; + } + return nullptr; +} + +void IParameterObj::copy(ParameterBase* first, ParameterBase* last, const ParameterBase* src_first, + const ParameterBase* src_last) { + if (!preCopy_()) + return; + + copy_(first, last, src_first, src_last); + + postCopy_(); +} + +void IParameterObj::copy_(ParameterBase* first, ParameterBase* last, const ParameterBase* src_first, + const ParameterBase* src_last) { + auto target = first; + auto source = src_first; + while (target != last && source != src_last) { + const bool result = target->copy(*source); + SEAD_ASSERT(result); + target = target->mNext; + source = source->mNext; + } +} + +void IParameterObj::copy(const IParameterObj& obj) { + if (!preCopy_()) + return; + + auto* mpHead = mParamListHead; + SEAD_ASSERT(mpHead != nullptr); + + auto* src = obj.mParamListHead; + while (src && src->getNameHash() != mpHead->getNameHash()) + src = src->mNext; + + while (src && mpHead) { + const bool result = mpHead->copy(*src); + SEAD_ASSERT(result); + mpHead = mpHead->mNext; + if (!mpHead) + break; + src = src->mNext; + } + + postCopy_(); +} + +void IParameterObj::copyLerp(ParameterBase* first, ParameterBase* last, + const ParameterBase* src1_first, const ParameterBase* src1_last, + const ParameterBase* src2_first, const ParameterBase* src2_last, + f32 t) { + if (!preCopy_()) + return; + + if (t <= 0.0) + copy_(first, last, src1_first, src1_last); + else if (t >= 1.0) + copy_(first, last, src2_first, src2_last); + else + copyLerp_(first, last, src1_first, src1_last, src2_first, src2_last, t); + + postCopy_(); +} + +void IParameterObj::copyLerp(const IParameterObj& obj1, const IParameterObj& obj2, f32 t) { + if (!preCopy_()) + return; + + auto mpHead = mParamListHead; + SEAD_ASSERT(mpHead); + + const u32 hash = mpHead->getNameHash(); + + auto* it1 = obj1.mParamListHead; + while (it1 && it1->getNameHash() != hash) + it1 = it1->mNext; + + auto* it2 = obj2.mParamListHead; + while (it2 && it2->getNameHash() != hash) + it2 = it2->mNext; + + while (it1 && it2 && mpHead) { + const bool result = mpHead->copyLerp(*it1, *it2, t); + SEAD_ASSERT(result); + it2 = it2->mNext; + if (!it2) + break; + mpHead = mpHead->mNext; + if (!mpHead) + break; + it1 = it1->mNext; + } + + postCopy_(); +} + +void IParameterObj::copyLerp_(ParameterBase* first, ParameterBase* last, + const ParameterBase* src1_first, const ParameterBase* src1_last, + const ParameterBase* src2_first, const ParameterBase* src2_last, + f32 t) { + auto* it = first; + auto* src1 = src1_first; + auto* src2 = src2_first; + while (it != last && src1 != src1_last && src2 != src2_last) { + const bool result = it->copyLerp(*src1, *src2, t); + SEAD_ASSERT(result); + it = it->mNext; + src1 = src1->mNext; + src2 = src2->mNext; + } +} + +} // namespace agl::utl diff --git a/lib/agl/src/Utils/aglParameterStringMgr.cpp b/lib/agl/src/Utils/aglParameterStringMgr.cpp new file mode 100644 index 00000000..a9948ee7 --- /dev/null +++ b/lib/agl/src/Utils/aglParameterStringMgr.cpp @@ -0,0 +1,26 @@ +#include "agl/Utils/aglParameterStringMgr.h" + +namespace agl::utl { + +SEAD_SINGLETON_DISPOSER_IMPL(ParameterStringMgr) + +ParameterStringMgr::ParameterStringMgr() { +#ifdef SEAD_DEBUG + setNodeName("utl::ParameterStringMgr"); + setNodeMeta("Icon=NOTE"); +#endif +} + +ParameterStringMgr::~ParameterStringMgr() { + mStrings.freeBuffer(); +} + +void ParameterStringMgr::initialize(sead::Heap* heap) { + mHeap = heap; + if (heap) { + mStrings.allocBuffer(0x20000, heap); + mStrings.clear(); + } +} + +} // namespace agl::utl diff --git a/lib/agl/src/Utils/aglResCommon.cpp b/lib/agl/src/Utils/aglResCommon.cpp new file mode 100644 index 00000000..cb81a3f2 --- /dev/null +++ b/lib/agl/src/Utils/aglResCommon.cpp @@ -0,0 +1,18 @@ +#include "agl/Utils/aglResCommon.h" +#include +#include + +namespace agl { + +void ModifyEndianU32(bool big_endian, void* p_data, size_t size) { + SEAD_ASSERT(p_data != nullptr); + SEAD_ASSERT(size % 4 == 0); + + u32* data = reinterpret_cast(p_data); + for (s32 i = 0; i < s32(size / 4); ++i) { + data[i] = sead::Endian::toHostU32( + big_endian ? sead::Endian::Types::cLittle : sead::Endian::Types::cBig, data[i]); + } +} + +} // namespace agl diff --git a/lib/agl/src/Utils/aglResParameter.cpp b/lib/agl/src/Utils/aglResParameter.cpp new file mode 100644 index 00000000..066f9379 --- /dev/null +++ b/lib/agl/src/Utils/aglResParameter.cpp @@ -0,0 +1,95 @@ +#include "agl/Utils/aglResParameter.h" +#include +#include +#include +#include "agl/Utils/aglParameter.h" + +namespace agl::utl { + +size_t ResParameter::getDataSize() const { + switch (ParameterType(ptr()->getType())) { + case ParameterType::Bool: + case ParameterType::F32: + case ParameterType::Int: + case ParameterType::U32: + return 4; + case ParameterType::Vec2: + return sizeof(sead::Vector2f); + case ParameterType::Vec3: + return sizeof(sead::Vector3f); + case ParameterType::Vec4: + case ParameterType::Color: + case ParameterType::Quat: + return sizeof(sead::Vector4f); + case ParameterType::String32: + case ParameterType::String64: + case ParameterType::String256: + case ParameterType::StringRef: + return sead::SafeString(getData()).calcLength() + 1; + case ParameterType::Curve1: + return 1 * 0x80; + case ParameterType::Curve2: + return 2 * 0x80; + case ParameterType::Curve3: + return 3 * 0x80; + case ParameterType::Curve4: + return 4 * 0x80; + case ParameterType::BufferInt: + case ParameterType::BufferF32: + case ParameterType::BufferU32: + return 4 * getBufferSize(); + case ParameterType::BufferBinary: + return getBufferSize(); + default: + SEAD_ASSERT_MSG(false, "illigal type:%d", ptr()->getType()); + return 0; + } +} + +s32 ResParameterObj::searchIndex(u32 param_hash) const { + for (s32 i = 0; i < getNum(); ++i) { + if (getResParameter(i).getParameterNameHash() == param_hash) + return i; + } + return -1; +} + +s32 ResParameterList::searchListIndex(u32 list_hash) const { + for (s32 i = 0; i < getResParameterListNum(); ++i) { + if (getResParameterList(i).getParameterListNameHash() == list_hash) + return i; + } + return -1; +} + +s32 ResParameterList::searchObjIndex(u32 obj_hash) const { + for (s32 i = 0; i < getResParameterObjNum(); ++i) { + if (getResParameterObj(i).getParameterObjNameHash() == obj_hash) + return i; + } + return -1; +} + +// NON_MATCHING: partial implementation (unused conversion code is unimplemented) +ResParameterArchive::ResParameterArchive(const void* p_data) { + mPtr = static_cast(const_cast(p_data)); + if (!p_data) + return; + + SEAD_ASSERT(sead::PtrUtil::isAlignedN(p_data, 4)); + if (mPtr->flags.isOff(ResParameterArchiveFlag::LittleEndian)) + ModifyEndianU32(false, mPtr, sizeof(ResParameterArchiveData)); + + verify(); + + if (mPtr->flags.isOn(ResParameterArchiveFlag::LittleEndian) && + mPtr->flags.isOn(ResParameterArchiveFlag::Utf8)) { + // Nothing else to do. + return; + } + + // FIXME: implement endianness and string encoding conversion (requires PrivateResource) + SEAD_ASSERT_MSG(false, "endianness and string conversion is unimplemented"); +} + +} // namespace agl::utl diff --git a/lib/agl/src/aglGPUMemBlock.cpp b/lib/agl/src/aglGPUMemBlock.cpp new file mode 100644 index 00000000..7deae321 --- /dev/null +++ b/lib/agl/src/aglGPUMemBlock.cpp @@ -0,0 +1 @@ +#include "agl/aglGPUMemBlock.hpp" \ No newline at end of file diff --git a/lib/agl/src/detail/aglGPUMemBlockMgr.cpp b/lib/agl/src/detail/aglGPUMemBlockMgr.cpp new file mode 100644 index 00000000..d54af663 --- /dev/null +++ b/lib/agl/src/detail/aglGPUMemBlockMgr.cpp @@ -0,0 +1,55 @@ +#include "agl/detail/aglGPUMemBlockMgr.h" + +namespace agl::detail { +const MemoryPoolType MemoryPoolType::cInvalidPoolType(0); +const MemoryPoolType MemoryPoolType::cValidPoolType(VALID_POOL_TYPE_VALUE); + +SEAD_SINGLETON_DISPOSER_IMPL(GPUMemBlockMgr) + +GPUMemBlockMgr::GPUMemBlockMgr() { + mMinBlockSize = cGPUPhysicalMemorySizeAlignment; + mFlags = GPUMemBlockMgrFlags::EnablePoolSharing; +} + +GPUMemBlockMgr::~GPUMemBlockMgr() { + mMngrHeaps.freeBuffer(); +} + +void GPUMemBlockMgr::initialize(sead::Heap* heap1, sead::Heap* heap2) { + mMngrHeaps.allocBuffer(0x1000, heap1); + mMngrHeaps.clear(); +} + +void GPUMemBlockMgr::enableSharedMemoryPool(bool enabled) { + mFlags.change(GPUMemBlockMgrFlags::EnablePoolSharing, enabled); +} + +u64 GPUMemBlockMgr::calcGPUMemorySize(u64 userSize) { + return sead::MathSizeT::roundUp(userSize, cGPUPhysicalMemorySizeAlignment); +} + +s32 GPUMemBlockMgr::calcGPUMemoryAlignment(s32 userAlignment) { + return sead::Mathi::roundUpPow2(sead::Mathi::abs(userAlignment), + cGPUPhysicalMemorySizeAlignment) * + sead::Mathi::sign(userAlignment); +} + +GPUMemBlockMgrHeapEx* GPUMemBlockMgr::findGPUMemBlockMgrHeapEx_(sead::Heap* p_heap, + int* p_outIndex) { + SEAD_ASSERT(p_heap != nullptr); + + if (mMngrHeaps.isEmpty()) { + return nullptr; + } + + // TODO + return nullptr; +} + +GPUMemBlockMgrHeapEx::GPUMemBlockMgrHeapEx(sead::Heap* p_heap) { + mAllowSharing = 1; + m08 = nullptr; + m10 = nullptr; +} + +} // namespace agl::detail \ No newline at end of file diff --git a/lib/agl/src/driver/aglGraphicsDriverMgr.cpp b/lib/agl/src/driver/aglGraphicsDriverMgr.cpp new file mode 100644 index 00000000..c70910a8 --- /dev/null +++ b/lib/agl/src/driver/aglGraphicsDriverMgr.cpp @@ -0,0 +1,12 @@ +#include "agl/driver/aglGraphicsDriverMgr.h" + +namespace agl::driver { +SEAD_SINGLETON_DISPOSER_IMPL(GraphicsDriverMgr) + +GraphicsDriverMgr::GraphicsDriverMgr() { + mDefaultCommandBuffer = nullptr; + _30 = nullptr; +} + +GraphicsDriverMgr::~GraphicsDriverMgr() = default; +} // namespace agl::driver \ No newline at end of file diff --git a/lib/agl/src/driver/aglNVNMgr.cpp b/lib/agl/src/driver/aglNVNMgr.cpp new file mode 100644 index 00000000..903373d7 --- /dev/null +++ b/lib/agl/src/driver/aglNVNMgr.cpp @@ -0,0 +1,6 @@ +#include "agl/driver/aglNVNMgr.h" + +namespace agl::driver { +// TODO: This is wrong and should actually touch the GraphicsDriverMgr implementation +SEAD_SINGLETON_DISPOSER_IMPL(NVNMgr) +} // namespace agl::driver \ No newline at end of file diff --git a/lib/sead b/lib/sead deleted file mode 160000 index 1b66e825..00000000 --- a/lib/sead +++ /dev/null @@ -1 +0,0 @@ -Subproject commit 1b66e825d1927254c191028523645541b13c7eab diff --git a/lib/sead/.clang-format b/lib/sead/.clang-format new file mode 100644 index 00000000..11036a74 --- /dev/null +++ b/lib/sead/.clang-format @@ -0,0 +1,90 @@ +--- +Language: Cpp +AccessModifierOffset: -4 +AlignAfterOpenBracket: Align +AlignConsecutiveAssignments: false +AlignConsecutiveDeclarations: false +AlignOperands: true +AlignTrailingComments: true +AllowAllParametersOfDeclarationOnNextLine: true +AllowShortBlocksOnASingleLine: Empty +AllowShortCaseLabelsOnASingleLine: false +AllowShortFunctionsOnASingleLine: Inline +AllowShortIfStatementsOnASingleLine: Never +AllowShortLoopsOnASingleLine: false +AlwaysBreakAfterDefinitionReturnType: None +AlwaysBreakAfterReturnType: None +AlwaysBreakBeforeMultilineStrings: false +AlwaysBreakTemplateDeclarations: Yes +BinPackArguments: true +BinPackParameters: true +BreakBeforeBinaryOperators: None +BreakBeforeBraces: Custom +BraceWrapping: + AfterCaseLabel: true + AfterClass: true + AfterControlStatement: Always + AfterEnum: true + AfterFunction: true + AfterNamespace: true + AfterStruct: true + AfterUnion: true + AfterExternBlock: true + BeforeCatch: true + BeforeElse: true + BeforeLambdaBody: false + BeforeWhile: false + IndentBraces: false +BreakBeforeTernaryOperators: false +BreakConstructorInitializersBeforeComma: false +ColumnLimit: 100 +CommentPragmas: '^ (IWYU pragma:|NOLINT)' +ConstructorInitializerAllOnOneLineOrOnePerLine: false +ConstructorInitializerIndentWidth: 4 +ContinuationIndentWidth: 4 +Cpp11BracedListStyle: true +DerivePointerAlignment: false +DisableFormat: false +ForEachMacros: [] +IncludeCategories: + - Regex: '^<[Ww]indows\.h>$' + Priority: 1 + - Regex: '^<' + Priority: 2 + - Regex: '^"' + Priority: 3 +IndentCaseLabels: false +IndentWidth: 4 +IndentWrappedFunctionNames: false +KeepEmptyLinesAtTheStartOfBlocks: false +MacroBlockBegin: '' +MacroBlockEnd: '' +MaxEmptyLinesToKeep: 1 +NamespaceIndentation: None +ObjCBlockIndentWidth: 4 +ObjCSpaceAfterProperty: false +ObjCSpaceBeforeProtocolList: true +PenaltyBreakBeforeFirstCallParameter: 19 +PenaltyBreakComment: 300 +PenaltyBreakFirstLessLess: 120 +PenaltyBreakString: 1000 +PenaltyExcessCharacter: 1000000 +PenaltyReturnTypeOnItsOwnLine: 60 +PointerAlignment: Left +ReflowComments: true +SortIncludes: true +SpaceAfterCStyleCast: false +SpaceBeforeAssignmentOperators: true +SpaceBeforeParens: ControlStatements +SpaceInEmptyParentheses: false +SpacesBeforeTrailingComments: 2 +SpacesInAngles: false +SpacesInContainerLiterals: true +SpacesInCStyleCastParentheses: false +SpacesInParentheses: false +SpacesInSquareBrackets: false +Standard: Latest +TabWidth: 4 +UseTab: Never +WhitespaceSensitiveMacros: ["SEAD_ENUM", "SEAD_ENUM_EX", "SEAD_ENUM_EX_VALUES"] +... diff --git a/lib/sead/.gitattributes b/lib/sead/.gitattributes new file mode 100644 index 00000000..dfe07704 --- /dev/null +++ b/lib/sead/.gitattributes @@ -0,0 +1,2 @@ +# Auto detect text files and perform LF normalization +* text=auto diff --git a/lib/sead/.github/workflows/lint_pr.yml b/lib/sead/.github/workflows/lint_pr.yml new file mode 100644 index 00000000..5c59be72 --- /dev/null +++ b/lib/sead/.github/workflows/lint_pr.yml @@ -0,0 +1,11 @@ +name: lint_pr +on: [push, pull_request] +jobs: + clang-format: + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v2 + - uses: DoozyX/clang-format-lint-action@v0.12 + with: + source: 'include modules' + clangFormatVersion: 12 diff --git a/lib/sead/.gitignore b/lib/sead/.gitignore new file mode 100644 index 00000000..bd86fa1b --- /dev/null +++ b/lib/sead/.gitignore @@ -0,0 +1,44 @@ +# Prerequisites +*.d + +# Compiled Object files +*.slo +*.lo +*.o +*.obj + +# Precompiled Headers +*.gch +*.pch + +# Compiled Dynamic libraries +*.so +*.dylib +*.dll + +# Fortran module files +*.mod +*.smod + +# Compiled Static libraries +*.lai +*.la +*.a +*.lib + +# Executables +*.exe +*.out +*.app +*.elf + +# GreenHills files +*.dep +*.dla +*.dnm +*.gpj +*.ii +*.map +*.opt +*.ti +tgt/* diff --git a/lib/sead/.gitrepo b/lib/sead/.gitrepo new file mode 100644 index 00000000..3846b4c1 --- /dev/null +++ b/lib/sead/.gitrepo @@ -0,0 +1,12 @@ +; DO NOT EDIT (unless you know what you are doing) +; +; This subdirectory is a git "subrepo", and this file is maintained by the +; git-subrepo command. See https://github.com/git-commands/git-subrepo#readme +; +[subrepo] + remote = https://github.com/open-ead/sead + branch = master + commit = 1b66e825d1927254c191028523645541b13c7eab + parent = ffcc7f659ebc9bc9d149e52bec553b906bb47369 + method = merge + cmdver = 0.4.3 diff --git a/lib/sead/CMakeLists.txt b/lib/sead/CMakeLists.txt new file mode 100644 index 00000000..697a6fa3 --- /dev/null +++ b/lib/sead/CMakeLists.txt @@ -0,0 +1,279 @@ +project(sead CXX ASM) + +option(SEAD_DEBUG "Enable debug assertions and warnings" OFF) +set(SEAD_PLATFORM "nin" CACHE STRING "Target platform (default: nin)") +set_property( + CACHE SEAD_PLATFORM + PROPERTY STRINGS "nin" +) + +add_library(sead OBJECT + include/basis/seadNew.h + include/basis/seadRawPrint.h + include/basis/seadTypes.h + modules/src/basis/seadNew.cpp + + include/codec/seadBase64.h + include/codec/seadHashCRC16.h + include/codec/seadHashCRC32.h + modules/src/codec/seadHashCRC16.cpp + modules/src/codec/seadHashCRC32.cpp + + include/container/seadBuffer.h + include/container/seadFreeList.h + include/container/seadListImpl.h + include/container/seadObjArray.h + include/container/seadObjList.h + include/container/seadOffsetList.h + include/container/seadOrderedSet.h + include/container/seadPtrArray.h + include/container/seadRingBuffer.h + include/container/seadSafeArray.h + include/container/seadStrTreeMap.h + include/container/seadTList.h + include/container/seadTreeMap.h + include/container/seadTreeNode.h + modules/src/container/seadListImpl.cpp + modules/src/container/seadPtrArray.cpp + modules/src/container/seadTreeNode.cpp + + include/devenv/seadAssertConfig.h + include/devenv/seadEnvUtil.h + include/devenv/seadGameConfig.h + include/devenv/seadStackTrace.h + modules/src/devenv/seadAssertConfig.cpp + modules/src/devenv/seadGameConfig.cpp + modules/src/devenv/seadStackTrace.cpp + + include/filedevice/seadArchiveFileDevice.h + include/filedevice/seadFileDevice.h + include/filedevice/seadFileDeviceMgr.h + include/filedevice/seadMainFileDevice.h + include/filedevice/seadPath.h + modules/src/filedevice/seadArchiveFileDevice.cpp + modules/src/filedevice/seadFileDevice.cpp + modules/src/filedevice/seadFileDeviceMgr.cpp + modules/src/filedevice/seadMainFileDevice.cpp + modules/src/filedevice/seadPath.cpp + + include/framework/seadCalculateTask.h + include/framework/seadFramework.h + include/framework/seadHeapPolicies.h + include/framework/seadInfLoopChecker.h + include/framework/seadMethodTree.h + include/framework/seadMethodTreeMgr.h + include/framework/seadProcessMeter.h + include/framework/seadProcessMeterBar.h + include/framework/seadTaskBase.h + include/framework/seadTaskID.h + include/framework/seadTaskMgr.h + include/framework/seadTaskParameter.h + modules/src/framework/seadCalculateTask.cpp + modules/src/framework/seadMethodTree.cpp + modules/src/framework/seadProcessMeterBar.cpp + + include/gfx/seadCamera.h + include/gfx/seadColor.h + include/gfx/seadDrawContext.h + include/gfx/seadFrameBuffer.h + include/gfx/seadPrimitiveRenderer.h + include/gfx/seadPrimitiveRendererUtil.h + include/gfx/seadProjection.h + include/gfx/seadTexture.h + modules/src/gfx/seadCamera.cpp + modules/src/gfx/seadColor.cpp + # modules/src/gfx/seadPrimitiveRenderer.cpp + # modules/src/gfx/seadPrimitiveRendererUtil.cpp + modules/src/gfx/seadProjection.cpp + + include/heap/seadArena.h + include/heap/seadDisposer.h + include/heap/seadExpHeap.h + include/heap/seadFrameHeap.h + include/heap/seadHeap.h + include/heap/seadHeapMgr.h + include/heap/seadMemBlock.h + modules/src/heap/seadDisposer.cpp + modules/src/heap/seadExpHeap.cpp + modules/src/heap/seadHeap.cpp + modules/src/heap/seadHeapMgr.cpp + + include/math/seadBoundBox.h + include/math/seadBoundBox.hpp + include/math/seadMathBase.h + include/math/seadMathCalcCommon.h + include/math/seadMathCalcCommon.hpp + include/math/seadMathNumbers.h + include/math/seadMathPolicies.h + include/math/seadMatrix.h + include/math/seadMatrix.hpp + include/math/seadMatrixCalcCommon.h + include/math/seadMatrixCalcCommon.hpp + include/math/seadQuat.h + include/math/seadQuat.hpp + include/math/seadQuatCalcCommon.h + include/math/seadQuatCalcCommon.hpp + include/math/seadVector.h + include/math/seadVector.hpp + include/math/seadVectorCalcCommon.h + include/math/seadVectorCalcCommon.hpp + modules/src/math/seadBoundBox.cpp + modules/src/math/seadMathCalcCommon.cpp + modules/src/math/seadMatrix.cpp + modules/src/math/seadQuat.cpp + modules/src/math/seadVector.cpp + + include/mc/seadCoreInfo.h + include/mc/seadJob.h + include/mc/seadJobQueue.h + include/mc/seadWorker.h + include/mc/seadWorkerMgr.h + modules/src/mc/seadCoreInfo.cpp + modules/src/mc/seadJob.cpp + modules/src/mc/seadJobQueue.cpp + modules/src/mc/seadWorker.cpp + modules/src/mc/seadWorkerMgr.cpp + + include/prim/seadBitFlag.h + include/prim/seadBitUtil.h + include/prim/seadContainerIterator.h + include/prim/seadDelegate.h + include/prim/seadDelegateEventSlot.h + include/prim/seadEndian.h + include/prim/seadEnum.h + include/prim/seadFormatPrint.h + include/prim/seadLongBitFlag.h + include/prim/seadMemUtil.h + include/prim/seadNamable.h + include/prim/seadPtrUtil.h + include/prim/seadRuntimeTypeInfo.h + include/prim/seadSafeString.h + include/prim/seadSafeString.hpp + include/prim/seadScopedLock.h + include/prim/seadScopeGuard.h + include/prim/seadSizedEnum.h + include/prim/seadStorageFor.h + include/prim/seadStringBuilder.h + include/prim/seadStringUtil.h + include/prim/seadTypedBitFlag.h + include/prim/seadTypedLongBitFlag.h + modules/src/prim/seadBitFlag.cpp + modules/src/prim/seadEndian.cpp + modules/src/prim/seadEnum.cpp + modules/src/prim/seadMemUtil.cpp + modules/src/prim/seadSafeString.cpp + modules/src/prim/seadStringBuilder.cpp + modules/src/prim/seadStringUtil.cpp + + include/random/seadGlobalRandom.h + include/random/seadRandom.h + modules/src/random/seadGlobalRandom.cpp + modules/src/random/seadRandom.cpp + + include/resource/seadArchiveRes.h + include/resource/seadDecompressor.h + include/resource/seadResource.h + include/resource/seadResourceMgr.h + include/resource/seadSharcArchiveRes.h + include/resource/seadSZSDecompressor.h + modules/src/resource/seadArchiveRes.cpp + modules/src/resource/seadResource.cpp + modules/src/resource/seadResourceMgr.cpp + modules/src/resource/seadSharcArchiveRes.cpp + modules/src/resource/seadSZSDecompressor.cpp + + include/stream/seadBufferStream.h + include/stream/seadStream.h + include/stream/seadStreamFormat.h + include/stream/seadStreamSrc.h + + include/thread/seadAtomic.h + include/thread/seadCriticalSection.h + include/thread/seadDelegateThread.h + include/thread/seadEvent.h + include/thread/seadMessageQueue.h + include/thread/seadMutex.h + include/thread/seadReadWriteLock.h + include/thread/seadSemaphore.h + include/thread/seadSpinLock.h + include/thread/seadThread.h + include/thread/seadThreadLocalStorage.h + include/thread/seadThreadUtil.h + modules/src/thread/seadDelegateThread.cpp + modules/src/thread/seadReadWriteLock.cpp + modules/src/thread/seadSpinLock.cpp + modules/src/thread/seadThread.cpp + modules/src/thread/seadThreadUtil.cpp + + include/time/seadCalendarSpan.h + include/time/seadCalendarTime.h + include/time/seadDateSpan.h + include/time/seadDateTime.h + include/time/seadDateUtil.h + include/time/seadTickSpan.h + include/time/seadTickTime.h + modules/src/time/seadCalendarTime.cpp + modules/src/time/seadDateSpan.cpp + modules/src/time/seadDateTime.cpp + modules/src/time/seadDateTimeUtc.cpp + modules/src/time/seadDateUtil.cpp + modules/src/time/seadTickSpan.cpp +) + +target_sources(sead PRIVATE + include/hostio/seadHostIOCurve.h + modules/src/hostio/seadHostIOCurve.cpp +) +if(SEAD_DEBUG) + target_sources(sead PRIVATE + include/hostio/seadHostIOEventListener.h + include/hostio/seadHostIOMgr.h + include/hostio/seadHostIONode.h + include/hostio/seadHostIOReflexible.h + include/hostio/seadHostIOThreadLock.h + modules/src/hostio/seadHostIOEventListener.cpp + modules/src/hostio/seadHostIONode.cpp + modules/src/hostio/seadHostIOReflexible.cpp + modules/src/hostio/seadHostIOThreadLock.cpp + ) +endif() + +if(SEAD_PLATFORM STREQUAL "nin") + if(NOT TARGET NintendoSDK) + add_subdirectory(../NintendoSDK) + endif() + target_link_libraries(sead PUBLIC NintendoSDK) + + target_sources(sead PRIVATE + include/filedevice/nin/seadNinAocFileDeviceNin.h + include/filedevice/nin/seadNinContentFileDeviceNin.h + include/filedevice/nin/seadNinFileDeviceBaseNin.h + include/filedevice/nin/seadNinHostIOFileDevice.h + include/filedevice/nin/seadNinSaveFileDeviceNin.h + include/filedevice/nin/seadNinSDFileDeviceNin.h + modules/src/filedevice/nin/seadNinAocFileDeviceNin.cpp + modules/src/filedevice/nin/seadNinContentFileDeviceNin.cpp + modules/src/filedevice/nin/seadNinFileDeviceBaseNin.cpp + modules/src/filedevice/nin/seadNinHostIOFileDevice.cpp + modules/src/filedevice/nin/seadNinSaveFileDeviceNin.cpp + modules/src/filedevice/nin/seadNinSDFileDeviceNin.cpp + + include/thread/nin/seadThreadLocalStorageNin.hpp + modules/src/thread/nin/seadCriticalSectionNin.cpp + modules/src/thread/nin/seadEventNin.cpp + modules/src/thread/nin/seadMessageQueueNin.cpp + modules/src/thread/nin/seadMutexNin.cpp + modules/src/thread/nin/seadSemaphoreNin.cpp + modules/src/thread/nin/seadThreadNin.cpp + ) +endif() + +target_compile_options(sead PRIVATE -fno-exceptions) +target_compile_options(sead PRIVATE -fno-strict-aliasing) +target_compile_options(sead PRIVATE -Wall -Wextra -Wdeprecated) +target_compile_options(sead PRIVATE -Wno-invalid-offsetof) +target_include_directories(sead PUBLIC include/) + +if(SEAD_DEBUG) + target_compile_definitions(sead PUBLIC SEAD_DEBUG=1) +endif() diff --git a/lib/sead/README.md b/lib/sead/README.md new file mode 100644 index 00000000..6c9d8749 --- /dev/null +++ b/lib/sead/README.md @@ -0,0 +1,98 @@ +# sead + +This is a decompilation of sead, the standard C++ library for first-party Nintendo games. + +Unlike the original [sead decompilation project](https://github.com/aboood40091/sead), which this repo derives from, this project targets more recent versions of sead. + +The objective is to recreate the standard library as accurately as possible, so that interoperability can eventually be achieved by adding support for other platforms and by making it easier to create projects that interact with sead games. + +Because sead is statically linked in games (and only in games), acquiring the original sead requires legally owning at least one recent first-party Nintendo game. Picking a game that ships with debugging symbols is strongly recommended: + +* Super Mario Odyssey (version 1.0.0) ([buy it here](https://www.nintendo.com/games/detail/super-mario-odyssey-switch/)) +* Splatoon 2 (version <= 3.1.0) ([buy it here](https://www.nintendo.com/games/detail/splatoon-2-switch/)) +* [Nintendo Labo](https://labo.nintendo.com/) (the pilot build has symbols, file names and assertions) +* Any other title that has symbols and uses sead + +File names, function names and the file organization come from debugging symbols, assertions and information in all of the aforementioned titles. +Nobody except Nintendo has the source code of sead, not even third-party developers. + +Note that many names (especially for inlined, templated functions) are just plain guesses. + +## Modules + +For progress, refer to [the GitHub project page](https://github.com/zeldamods/sead/projects/1). Several modules currently fail to build for Switch. + +* **audio** - Audio +* **basis** - Types, asserts, allocation operators +* **codec** - Base64, CRC16, CRC32 +* **container** - Templated container classes +* **controller** - Controller +* **devenv** - Development environment (debug utilities) +* **filedevice** - File IO +* **framework** - Framework (game framework, tasks, etc.) +* **geom** - Geometry +* **gfx** - Graphics +* **heap** - Heap (arenas, disposers, different types of heaps) +* **hostio** - Host IO (communication with PCs) +* **math** - Maths utilities (vector, matrix, etc.) +* **message** - libms wrapper +* **mc** - Multi-core support +* **prim** - Primitives (strings, enums, RTTI, etc.) +* **random** - Random number generator +* **resource** - Resource (loading, decompressing, etc.) +* **stream** - Stream IO +* **thread** - Thread utilities (threads, critical sections, message queues, etc.) +* **time** - Time utilities + +### Platform specific source + +Platform-specific files are usually placed into a subdirectory that is called: + +* **cafe** for Wii U +* **ctr** for 3DS +* **nin** for nnSdk (Switch) + +## Building + +Building this project requires: + +- A C++17 capable compiler (or >= Clang 4.0). While older parts of sead are written in C++03, the newer modules in sead target C++11 (or newer) and recent C++ language or library features make writing C++ more convenient. +- CMake 3.10+ + +### Configuration + +sead can be configured with several compile-time defines: + +* `SEAD_DEBUG`: enables assertions and HostIO code. + +#### Platforms +* `cafe`: Wii U +* `NNSDK`: nnSdk (Switch and any platform that is supported by modern nnSdk) + +Other platforms (generic Unix, iOS, Android, CTR) are not supported. + +#### Matching hacks + +This project sometimes uses small hacks to force particular code to be generated by the compiler. Those have no semantic effects but can help with matching assembly code especially when the hacks are used for functions that are inlined. + +* `MATCHING_HACK_NX_CLANG`: Hacks for Switch sead, when compiling with Clang. + +## Contributing + +### Non-inlined functions +When **implementing non-inlined functions**, please compare the assembly output against the original function and make it match the original code. At this scale, that is pretty much the only reliable way to ensure accuracy and functional equivalency. + +However, given the large number of functions, certain kinds of small differences can be ignored when a function would otherwise be equivalent: + +* Regalloc differences. + +* Instruction reorderings when it is obvious the function is still semantically equivalent (e.g. two add/mov instructions that operate on entirely different registers being reordered) + +When ignoring minor differences, add a `// NOT_MATCHING: explanation` comment and explain what does not match. + +### Header utilities or inlined functions +For **header-only utilities** (like container classes), use pilot/debug builds, assertion messages and common sense to try to undo function inlining. For example, if you see the same assertion appear in many functions and the file name is a header file, or if you see identical snippets of code in many different places, chances are that you are dealing with an inlined function. In that case, you should refactor the inlined code into its own function. + +Also note that introducing inlined functions is sometimes necessary to get the desired codegen. + +If a function is inlined, you should try as hard as possible to make it match perfectly. For inlined functions, it is better to use weird code or small hacks to force a match as differences would otherwise appear in every single function that inlines the non-matching code, which drastically complicates matching other functions. If a hack is used, wrap it inside a `#ifdef MATCHING_HACK_{PLATFORM}` (see above for a list of defines). diff --git a/lib/sead/include/basis/seadNew.h b/lib/sead/include/basis/seadNew.h new file mode 100644 index 00000000..c5b66a02 --- /dev/null +++ b/lib/sead/include/basis/seadNew.h @@ -0,0 +1,70 @@ +#ifndef SEAD_NEW_H_ +#define SEAD_NEW_H_ + +#include +#include + +#include + +namespace sead +{ +class Heap; + +void AllocFailAssert(Heap* heap, size_t size, u32 alignment); + +#ifndef SEAD_DEBUG +inline void AllocFailAssert(Heap*, size_t, u32) {} +#endif +} // namespace sead + +void* operator new(size_t size); +void* operator new[](size_t size); +void* operator new(size_t size, const std::nothrow_t&) noexcept; +void* operator new[](size_t size, const std::nothrow_t&) noexcept; + +void* operator new(size_t size, s32 alignment); +void* operator new[](size_t size, s32 alignment); +void* operator new(size_t size, s32 alignment, const std::nothrow_t&) noexcept; +void* operator new[](size_t size, s32 alignment, const std::nothrow_t&) noexcept; + +void* operator new(size_t size, sead::Heap* heap, const std::nothrow_t&) noexcept; +void* operator new[](size_t size, sead::Heap* heap, const std::nothrow_t&) noexcept; + +void* operator new(size_t size, sead::Heap* heap, s32 alignment = sizeof(void*)); +void* operator new[](size_t size, sead::Heap* heap, s32 alignment = sizeof(void*)); +void* operator new(size_t size, sead::Heap* heap, s32 alignment, const std::nothrow_t&) noexcept; +void* operator new[](size_t size, sead::Heap* heap, s32 alignment, const std::nothrow_t&) noexcept; + +void operator delete(void* ptr) noexcept; +void operator delete[](void* ptr) noexcept; +void operator delete(void* ptr, const std::nothrow_t&) noexcept; +void operator delete[](void* ptr, const std::nothrow_t&) noexcept; + +void operator delete(void* ptr, s32); +void operator delete[](void* ptr, s32); +void operator delete(void* ptr, s32, const std::nothrow_t&) noexcept; +void operator delete[](void* ptr, s32, const std::nothrow_t&) noexcept; + +void operator delete(void* ptr, sead::Heap*, const std::nothrow_t&) noexcept; +void operator delete[](void* ptr, sead::Heap*, const std::nothrow_t&) noexcept; + +void operator delete(void* ptr, sead::Heap*, s32); +void operator delete[](void* ptr, sead::Heap*, s32); +void operator delete(void* ptr, sead::Heap*, s32, const std::nothrow_t&) noexcept; +void operator delete[](void* ptr, sead::Heap*, s32, const std::nothrow_t&) noexcept; + +namespace sead +{ +inline u8* AllocBuffer(size_t size, Heap* heap, s32 alignment) +{ + u8* buffer = new (heap, alignment, std::nothrow) u8[size]; + if (buffer) + return buffer; + +#ifdef SEAD_DEBUG + sead::AllocFailAssert(heap, size, alignment); +#endif + return nullptr; +} +} // namespace sead +#endif // SEAD_NEW_H_ diff --git a/lib/sead/include/basis/seadRawPrint.h b/lib/sead/include/basis/seadRawPrint.h new file mode 100644 index 00000000..979f9695 --- /dev/null +++ b/lib/sead/include/basis/seadRawPrint.h @@ -0,0 +1,95 @@ +#pragma once + +#include + +#include + +#ifdef SEAD_DEBUG +#define SEAD_ASSERT_MSG(condition, message, ...) \ + do \ + { \ + if (!(condition)) \ + sead::system::HaltWithDetail(__FILE__, __LINE__, message, ##__VA_ARGS__); \ + } while (0) +#define SEAD_ASSERT(condition) \ + do \ + { \ + if (!(condition)) \ + sead::system::HaltWithDetailNoFormat(__FILE__, __LINE__, #condition); \ + } while (0) +#define SEAD_WARN(message, ...) \ + do \ + sead::system::Warning(__FILE__, __LINE__, message, ##__VA_ARGS__); \ + while (0) +#define SEAD_DEBUG_PRINT(format, ...) \ + do \ + sead::system::Print(format, ##__VA_ARGS__); \ + while (0) +#else +#define SEAD_ASSERT_MSG(condition, message, ...) \ + do \ + { \ + if (false) \ + { \ + static_cast(condition); \ + sead::system::detail::CheckFormat(message, ##__VA_ARGS__); \ + } \ + } while (0) +#define SEAD_ASSERT(condition) \ + do \ + { \ + if (false) \ + static_cast(condition); \ + } while (0) +#define SEAD_WARN(message, ...) \ + do \ + { \ + if (false) \ + sead::system::detail::CheckFormat(message, ##__VA_ARGS__); \ + } while (0) +#define SEAD_DEBUG_PRINT(format, ...) \ + do \ + { \ + if (false) \ + sead::system::detail::CheckFormat(format, ##__VA_ARGS__); \ + } while (0) +#endif + +namespace sead +{ +namespace system +{ +namespace detail +{ +// Dummy function whose only purpose is to trigger a format string check. +#ifdef __GNUC__ +[[maybe_unused]] [[gnu::format(printf, 1, 2)]] +#endif +inline void +CheckFormat(const char*, ...) +{ +} +} // namespace detail + +void Halt(); +#ifdef __GNUC__ +[[gnu::format(printf, 3, 4)]] +#endif +void HaltWithDetail(const char* file, int line, const char* msg, ...); +void HaltWithDetailNoFormat(const char* file, int line, const char* msg); +void DebugBreak(); + +#ifdef __GNUC__ +[[gnu::format(printf, 1, 2)]] +#endif +void Print(const char* format, ...); +void PrintV(const char* format, std::va_list); +void PrintString(const char* format, s32); + +#ifdef __GNUC__ +[[gnu::format(printf, 3, 4)]] +#endif +void Warning(const char* file, int line, const char* msg, ...); +void SetWarningEnable(bool enable); +} // namespace system +} // namespace sead diff --git a/lib/sead/include/basis/seadTypes.h b/lib/sead/include/basis/seadTypes.h new file mode 100644 index 00000000..f007d62a --- /dev/null +++ b/lib/sead/include/basis/seadTypes.h @@ -0,0 +1,27 @@ +#ifndef SEAD_TYPES_H_ +#define SEAD_TYPES_H_ + +#ifdef cafe +#include +#else +#include +#include + +using u8 = std::uint8_t; +using u16 = std::uint16_t; +using u32 = std::uint32_t; +using u64 = std::uint64_t; + +using s8 = std::int8_t; +using s16 = std::int16_t; +using s32 = std::int32_t; +using s64 = std::int64_t; + +using f32 = float; +using f64 = double; + +using char16 = char16_t; +using size_t = std::size_t; +#endif + +#endif // SEAD_NEW_H_ diff --git a/lib/sead/include/codec/seadBase64.h b/lib/sead/include/codec/seadBase64.h new file mode 100644 index 00000000..83acda5f --- /dev/null +++ b/lib/sead/include/codec/seadBase64.h @@ -0,0 +1,14 @@ +#pragma once + +#include + +namespace sead +{ +class Base64 +{ +public: + static void encode(char* dst, const void* src, size_t length, bool url_safe); + static bool decode(void* dst, size_t dst_size, const char* src, size_t src_size, + size_t* decoded_size); +}; +} // namespace sead diff --git a/lib/sead/include/codec/seadHashCRC16.h b/lib/sead/include/codec/seadHashCRC16.h new file mode 100644 index 00000000..cc1b006c --- /dev/null +++ b/lib/sead/include/codec/seadHashCRC16.h @@ -0,0 +1,33 @@ +#pragma once + +#include +#include + +namespace sead +{ +class HashCRC16 +{ +public: + struct Context + { + u32 hash = 0; + }; + + static u32 calcHash(const void* ptr, u32 size); + static u32 calcHashWithContext(Context* context, const void* ptr, u32 size); + + static u32 calcStringHash(const char* str); + static u32 calcStringHash(const SafeString& str) { return calcStringHash(str.cstr()); } + static u32 calcStringHashWithContext(Context* context, const char* str); + static u32 calcStringHashWithContext(Context* context, const SafeString& str) + { + return calcStringHashWithContext(context, str.cstr()); + } + + static void initialize(); + +private: + static u16 sTable[256]; + static bool sInitialized; +}; +} // namespace sead diff --git a/lib/sead/include/codec/seadHashCRC32.h b/lib/sead/include/codec/seadHashCRC32.h new file mode 100644 index 00000000..1f2675b7 --- /dev/null +++ b/lib/sead/include/codec/seadHashCRC32.h @@ -0,0 +1,33 @@ +#pragma once + +#include +#include + +namespace sead +{ +class HashCRC32 +{ +public: + struct Context + { + u32 hash = -1; + }; + + static u32 calcHash(const void* ptr, u32 size); + static u32 calcHashWithContext(Context* context, const void* ptr, u32 size); + + static u32 calcStringHash(const char* str); + static u32 calcStringHash(const SafeString& str) { return calcStringHash(str.cstr()); } + static u32 calcStringHashWithContext(Context* context, const char* str); + static u32 calcStringHashWithContext(Context* context, const SafeString& str) + { + return calcStringHashWithContext(context, str.cstr()); + } + + static void initialize(); + +private: + static u32 sTable[256]; + static bool sInitialized; +}; +} // namespace sead diff --git a/lib/sead/include/container/seadBuffer.h b/lib/sead/include/container/seadBuffer.h new file mode 100644 index 00000000..eb058e64 --- /dev/null +++ b/lib/sead/include/container/seadBuffer.h @@ -0,0 +1,442 @@ +#ifndef SEAD_BUFFER_H_ +#define SEAD_BUFFER_H_ + +#include +#include + +#include +#include +#include +#include +#include + +namespace sead +{ +class Heap; + +template +class Buffer +{ +public: + Buffer() : mSize(0), mBuffer(NULL) {} + Buffer(s32 size, T* buffer) : mSize(size), mBuffer(buffer) {} + template + Buffer(T (&array)[N]) : Buffer(N, array) + { + } + + Buffer(const Buffer& other) { *this = other; } + + Buffer& operator=(const Buffer& other) + { + mSize = other.mSize; + mBuffer = other.mBuffer; + return *this; + } + + class iterator + { + public: + explicit iterator(T* buffer, s32 index = 0) : mIndex(index), mBuffer(buffer) {} + bool operator==(const iterator& rhs) const + { + return mIndex == rhs.mIndex && mBuffer == rhs.mBuffer; + } + bool operator!=(const iterator& rhs) const { return !operator==(rhs); } + iterator& operator++() + { + ++mIndex; + return *this; + } + T& operator*() const { return mBuffer[mIndex]; } + T* operator->() const { return &mBuffer[mIndex]; } + s32 getIndex() const { return mIndex; } + + private: + s32 mIndex; + T* mBuffer; + }; + + class constIterator + { + public: + explicit constIterator(const T* buffer, s32 index = 0) : mIndex(index), mBuffer(buffer) {} + bool operator==(const constIterator& rhs) const + { + return mIndex == rhs.mIndex && mBuffer == rhs.mBuffer; + } + bool operator!=(const constIterator& rhs) const { return !operator==(rhs); } + constIterator& operator++() + { + ++mIndex; + return *this; + } + const T& operator*() const { return mBuffer[mIndex]; } + const T* operator->() const { return &mBuffer[mIndex]; } + s32 getIndex() const { return mIndex; } + + private: + s32 mIndex; + const T* mBuffer; + }; + + iterator begin() { return iterator(mBuffer); } + iterator begin(s32 idx) + { + if (u32(size()) < u32(idx)) + { + SEAD_ASSERT_MSG(false, "range over [0,%d] : %d", size(), idx); + return end(); + } + return iterator(mBuffer, idx); + } + + constIterator begin() const { return constIterator(mBuffer); } + constIterator begin(s32 idx) const + { + if (u32(size()) < u32(idx)) + { + SEAD_ASSERT_MSG(false, "range over [0,%d] : %d", size(), idx); + return end(); + } + return constIterator(mBuffer, idx); + } + + iterator end() { return iterator(mBuffer, mSize); } + constIterator end() const { return constIterator(mBuffer, mSize); } + + class reverseIterator + { + public: + explicit reverseIterator(T* buffer, s32 index = 0) : mIndex(index), mBuffer(buffer) {} + bool operator==(const reverseIterator& rhs) const { return mIndex == rhs.mIndex; } + bool operator!=(const reverseIterator& rhs) const { return !operator==(rhs); } + reverseIterator& operator++() + { + --mIndex; + return *this; + } + T& operator*() const { return mBuffer[mIndex]; } + T* operator->() const { return &mBuffer[mIndex]; } + s32 getIndex() const { return mIndex; } + + private: + s32 mIndex; + T* mBuffer; + }; + + reverseIterator rbegin() { return reverseIterator(mBuffer, mSize - 1); } + reverseIterator rbegin(s32 index) { return reverseIterator(mBuffer, index); } + reverseIterator rend() { return reverseIterator(mBuffer, -1); } + + void allocBuffer(s32 size, s32 alignment) + { + SEAD_ASSERT(mBuffer == nullptr); + if (size > 0) + { + T* buffer = new (alignment) T[size]; + if (buffer) + { + mSize = size; + mBuffer = buffer; + SEAD_ASSERT_MSG(PtrUtil::isAlignedPow2(mBuffer, sead::Mathi::abs(alignment)), + "don't set alignment for a class with destructor"); + } + } + else + { + SEAD_ASSERT_MSG(false, "size[%d] must be larger than zero", size); + } + } + + void allocBuffer(s32 size, Heap* heap, s32 alignment = sizeof(void*)) + { + SEAD_ASSERT(mBuffer == nullptr); + if (size > 0) + { + T* buffer = new (heap, alignment) T[size]; + if (buffer) + { + mSize = size; + mBuffer = buffer; + SEAD_ASSERT_MSG(PtrUtil::isAlignedPow2(mBuffer, sead::Mathi::abs(alignment)), + "don't set alignment for a class with destructor"); + } + } + else + { + SEAD_ASSERT_MSG(false, "size[%d] must be larger than zero", size); + } + } + + bool tryAllocBuffer(s32 size, s32 alignment = sizeof(void*)) + { + SEAD_ASSERT(mBuffer == nullptr); + if (size > 0) + { + T* buffer = new (alignment, std::nothrow) T[size]; + if (buffer) + { + mSize = size; + mBuffer = buffer; + SEAD_ASSERT_MSG(PtrUtil::isAlignedPow2(mBuffer, sead::Mathi::abs(alignment)), + "don't set alignment for a class with destructor"); + return true; + } + return false; + } + SEAD_ASSERT_MSG(false, "size[%d] must be larger than zero", size); + return false; + } + + bool tryAllocBuffer(s32 size, Heap* heap, s32 alignment = sizeof(void*)) + { + SEAD_ASSERT(mBuffer == nullptr); + if (size > 0) + { + T* buffer = new (heap, alignment, std::nothrow) T[size]; + if (buffer) + { + mSize = size; + mBuffer = buffer; + SEAD_ASSERT_MSG(PtrUtil::isAlignedPow2(mBuffer, sead::Mathi::abs(alignment)), + "don't set alignment for a class with destructor"); + return true; + } + return false; + } + SEAD_ASSERT_MSG(false, "size[%d] must be larger than zero", size); + return false; + } + + inline bool allocBufferAssert(s32 size, Heap* heap, s32 alignment = sizeof(void*)) + { + if (tryAllocBuffer(size, heap, alignment)) + return true; + AllocFailAssert(heap, sizeof(T) * size, alignment); + return false; + } + + void freeBuffer() + { + if (mBuffer) + { + delete[] mBuffer; + mBuffer = nullptr; + mSize = 0; + } + } + + void setBuffer(s32 size, T* bufferptr) + { + if (size < 1) + { + SEAD_ASSERT_MSG(false, "size[%d] must be larger than zero", size); + return; + } + if (!bufferptr) + { + SEAD_ASSERT_MSG(false, "bufferptr is null"); + return; + } + mSize = size; + mBuffer = bufferptr; + } + + bool isBufferReady() const { return mBuffer != nullptr; } + + bool isIndexValid(s32 idx) const { return u32(idx) < u32(mSize); } + + T& operator()(s32 idx) { return *unsafeGet(idx); } + const T& operator()(s32 idx) const { return *unsafeGet(idx); } + + T& operator[](s32 idx) + { + if (u32(mSize) <= u32(idx)) + { + SEAD_ASSERT_MSG(false, "index exceeded [%d/%d]", idx, mSize); + return mBuffer[0]; + } + return mBuffer[idx]; + } + + const T& operator[](s32 idx) const + { + if (u32(mSize) <= u32(idx)) + { + SEAD_ASSERT_MSG(false, "index exceeded [%d/%d]", idx, mSize); + return mBuffer[0]; + } + return mBuffer[idx]; + } + + T* get(s32 idx) + { + if (u32(mSize) <= u32(idx)) + { + SEAD_ASSERT_MSG(false, "index exceeded [%d/%d]", idx, mSize); + return nullptr; + } + return &mBuffer[idx]; + } + + const T* get(s32 idx) const + { + if (u32(mSize) <= u32(idx)) + { + SEAD_ASSERT_MSG(false, "index exceeded [%d/%d]", idx, mSize); + return nullptr; + } + return &mBuffer[idx]; + } + + T* unsafeGet(s32 idx) + { + SEAD_ASSERT_MSG(u32(idx) < u32(mSize), "index exceeded [%d/%d]", idx, mSize); + return &mBuffer[idx]; + } + const T* unsafeGet(s32 idx) const + { + SEAD_ASSERT_MSG(u32(idx) < u32(mSize), "index exceeded [%d/%d]", idx, mSize); + return &mBuffer[idx]; + } + + T& front() { return mBuffer[0]; } + const T& front() const { return mBuffer[0]; } + + T& back() { return mBuffer[mSize - 1]; } + const T& back() const { return mBuffer[mSize - 1]; } + + s32 size() const { return mSize; } + s32 getSize() const { return mSize; } + + T* getBufferPtr() { return mBuffer; } + const T* getBufferPtr() const { return mBuffer; } + + u32 getByteSize() const { return mSize * sizeof(T); } + + void fill(const T& v) + { + for (s32 i = 0; i < mSize; ++i) + mBuffer[i] = v; + } + + using CompareCallback = s32 (*)(const T* lhs, const T* rhs); + + s32 binarySearch(const T& item) const { return binarySearch(item, compareT); } + + s32 binarySearch(const T& item, CompareCallback cmp) const + { + if (mSize == 0) + return -1; + + s32 a = 0; + s32 b = mSize - 1; + while (a < b) + { + const s32 m = (a + b) / 2; + const s32 c = cmp(&mBuffer[m], &item); + if (c == 0) + return m; + if (c < 0) + a = m + 1; + else + b = m; + } + + if (cmp(&mBuffer[a], &item) == 0) + return a; + + return -1; + } + + template + s32 binarySearch(const Key& key, s32 (*cmp)(const T& item, const Key& key)) const + { + if (mSize == 0) + return -1; + + s32 a = 0; + s32 b = mSize - 1; + while (a < b) + { + const s32 m = (a + b) / 2; + const s32 c = cmp(mBuffer[m], key); + if (c == 0) + return m; + if (c < 0) + a = m + 1; + else + b = m; + } + + if (cmp(mBuffer[a], key) == 0) + return a; + + return -1; + } + + template + s32 binarySearchC(CustomCompareCallback cmp) const + { + if (mSize == 0) + return -1; + + s32 a = 0; + s32 b = mSize - 1; + while (a < b) + { + const s32 m = (a + b) / 2; + const s32 c = cmp(mBuffer[m]); + if (c == 0) + return m; + if (c < 0) + a = m + 1; + else + b = m; + } + + if (cmp(mBuffer[a]) == 0) + return a; + + return -1; + } + + /// Sort elements with indices in [start_idx .. end_idx] using heapsort. + void heapSort(s32 start_idx, s32 end_idx) + { + if (start_idx >= mSize || end_idx >= mSize || end_idx - start_idx < 1) + return; + // FIXME: Nintendo implemented heap sort manually without using + std::make_heap(mBuffer + start_idx, mBuffer + end_idx); + std::sort_heap(mBuffer + start_idx, mBuffer + end_idx); + } + + /// Sort elements with indices in [start_idx .. end_idx] using heapsort. + void heapSort(s32 start_idx, s32 end_idx, CompareCallback cmp) + { + if (start_idx >= mSize || end_idx >= mSize || end_idx - start_idx < 1) + return; + // FIXME: Nintendo implemented heap sort manually without using + const auto cmp_ = [cmp](const T& a, const T& b) { return cmp(&a, &b) < 0; }; + std::make_heap(mBuffer + start_idx, mBuffer + end_idx, cmp_); + std::sort_heap(mBuffer + start_idx, mBuffer + end_idx, cmp_); + } + +protected: + static s32 compareT(const T* lhs, const T* rhs) + { + if (*lhs < *rhs) + return -1; + if (*rhs < *lhs) + return 1; + return 0; + } + + s32 mSize; + T* mBuffer; +}; + +} // namespace sead + +#endif // SEAD_BUFFER_H_ diff --git a/lib/sead/include/container/seadFreeList.h b/lib/sead/include/container/seadFreeList.h new file mode 100644 index 00000000..93e23685 --- /dev/null +++ b/lib/sead/include/container/seadFreeList.h @@ -0,0 +1,74 @@ +#pragma once + +#include + +#include "basis/seadRawPrint.h" +#include "basis/seadTypes.h" + +namespace sead +{ +class FreeList +{ +public: + void setWork(void* work, s32 elem_size, s32 num); + void reset(); + + void* alloc(); + void free(void* ptr); + + void* getFree() const { return mFree; } + void* work() const { return mWork; } + + static const size_t cPtrSize = sizeof(void*); + +private: + struct Node + { + Node* nextFree; + }; + + Node* mFree = nullptr; + void* mWork = nullptr; +}; + +inline void FreeList::setWork(void* work, s32 elem_size, s32 num) +{ + SEAD_ASSERT(work); + SEAD_ASSERT(elem_size > 0 && elem_size % cPtrSize == 0); + SEAD_ASSERT(num > 0); + + const s32 idx_multiplier = elem_size / cPtrSize; + void** const ptrs = new (work) void*[num * idx_multiplier]; + + mFree = new (work) Node; + + // Create the linked list. + for (s32 i = 0; i < num - 1; ++i) + new (&ptrs[i * idx_multiplier]) Node{new (&ptrs[(i + 1) * idx_multiplier]) Node}; + + new (&ptrs[(num - 1) * idx_multiplier]) Node{nullptr}; + + mWork = work; +} + +inline void FreeList::reset() +{ + mFree = nullptr; + mWork = nullptr; +} + +inline void* FreeList::alloc() +{ + if (!mFree) + return nullptr; + + void* ptr = mFree; + mFree = mFree->nextFree; + return ptr; +} + +inline void FreeList::free(void* ptr) +{ + mFree = new (ptr) Node{mFree}; +} +} // namespace sead diff --git a/lib/sead/include/container/seadListImpl.h b/lib/sead/include/container/seadListImpl.h new file mode 100644 index 00000000..c78979ba --- /dev/null +++ b/lib/sead/include/container/seadListImpl.h @@ -0,0 +1,121 @@ +#ifndef SEAD_LIST_IMPL_H_ +#define SEAD_LIST_IMPL_H_ + +#include + +namespace sead +{ +class Random; + +class ListNode +{ +public: + ListNode* next() const { return mNext; } + ListNode* prev() const { return mPrev; } + bool isLinked() const { return mNext || mPrev; } + +private: + friend class ListImpl; + + void init_() { *this = {}; } + void insertBack_(ListNode* node); + void insertFront_(ListNode* node); + void erase_(); + + ListNode* mPrev = nullptr; + ListNode* mNext = nullptr; +}; + +class ListImpl +{ +public: + __attribute__((always_inline)) ListImpl() : mStartEnd(), mCount(0) + { + mStartEnd.mNext = &mStartEnd; + mStartEnd.mPrev = &mStartEnd; + } + + bool isEmpty() const { return mCount == 0; } + s32 size() const { return mCount; } + + void reverse(); + void shuffle(); + void shuffle(Random* random); + bool checkLinks() const; + +protected: + using CompareCallbackImpl = int (*)(const void*, const void*); + + template + void sort(s32 offset, const ComparePredicate& cmp) + { + this->mergeSort(offset, cmp); + } + + template + void mergeSort(s32 offset, const ComparePredicate& cmp) + { + this->mergeSortImpl_(mStartEnd.mNext, mStartEnd.mPrev, size(), offset, + cmp); + } + + void pushBack(ListNode* item) + { + mStartEnd.insertFront_(item); + ++mCount; + } + + void pushFront(ListNode* item) + { + mStartEnd.insertBack_(item); + ++mCount; + } + + ListNode* popBack(); + ListNode* popFront(); + + void insertBefore(ListNode* node, ListNode* node_to_insert) + { + node->insertFront_(node_to_insert); + ++mCount; + } + + void insertAfter(ListNode* node, ListNode* node_to_insert) + { + node->insertBack_(node_to_insert); + ++mCount; + } + + void erase(ListNode* item) + { + item->erase_(); + --mCount; + } + + ListNode* front() const { return mCount >= 1 ? mStartEnd.mNext : nullptr; } + ListNode* back() const { return mCount >= 1 ? mStartEnd.mPrev : nullptr; } + ListNode* nth(int n) const; + s32 indexOf(const ListNode*) const; + + void swap(ListNode* n1, ListNode* n2); + void moveAfter(ListNode* basis, ListNode* n); + void moveBefore(ListNode* basis, ListNode* n); + + ListNode* find(const void* ptr, s32 offset, CompareCallbackImpl cmp) const; + void uniq(s32 offset, CompareCallbackImpl cmp); + + void clear(); + + // FIXME: this should take an rvalue reference for predicate. + template + static void mergeSortImpl_(ListNode* front, ListNode* back, s32 num, s32 offset, + const ComparePredicate& predicate); + +protected: + ListNode mStartEnd; + s32 mCount; +}; + +} // namespace sead + +#endif // SEAD_LIST_IMPL_H_ diff --git a/lib/sead/include/container/seadObjArray.h b/lib/sead/include/container/seadObjArray.h new file mode 100644 index 00000000..df2b4dec --- /dev/null +++ b/lib/sead/include/container/seadObjArray.h @@ -0,0 +1,271 @@ +#pragma once + +#include +#include "basis/seadNew.h" +#include "basis/seadRawPrint.h" +#include "container/seadFreeList.h" +#include "container/seadPtrArray.h" + +namespace sead +{ +/// An ObjArray is a container that allocates elements using a FreeList and also keeps an array of +/// pointers for fast access to each element. +template +class ObjArray : public PtrArrayImpl +{ +public: + ObjArray() = default; + ObjArray(s32 max_num, void* buf) { setBuffer(max_num, buf); } + + void allocBuffer(s32 capacity, Heap* heap, s32 alignment = sizeof(void*)) + { + SEAD_ASSERT(mPtrs == nullptr); + + if (capacity < 1) + { + SEAD_ASSERT_MSG(false, "capacity[%d] must be larger than zero", capacity); + return; + } + + setBuffer(capacity, + new (heap, alignment, std::nothrow) u8[calculateWorkBufferSize(capacity)]); + } + + bool tryAllocBuffer(s32 capacity, Heap* heap, s32 alignment = sizeof(void*)) + { + SEAD_ASSERT(mPtrs == nullptr); + + if (capacity < 1) + { + SEAD_ASSERT_MSG(false, "capacity[%d] must be larger than zero", capacity); + return false; + } + + auto* buf = new (heap, alignment, std::nothrow) u8[calculateWorkBufferSize(capacity)]; + if (!buf) + return false; + + setBuffer(capacity, buf); + return true; + } + + void setBuffer(s32 max_num, void* buf) + { + if (!buf) + { + SEAD_ASSERT_MSG(false, "buf is null"); + return; + } + + mFreeList.setWork(buf, ElementSize, max_num); + PtrArrayImpl::setBuffer(max_num, reinterpret_cast(buf) + ElementSize * max_num); + } + + void freeBuffer() + { + if (!isBufferReady()) + return; + + clear(); + + if (mFreeList.work()) + delete[] static_cast(mFreeList.work()); + + mFreeList.reset(); + mPtrs = nullptr; + mPtrNumMax = 0; + } + + T* at(s32 pos) const { return static_cast(PtrArrayImpl::at(pos)); } + T* unsafeAt(s32 pos) const { return static_cast(PtrArrayImpl::unsafeAt(pos)); } + T* operator()(s32 pos) const { return unsafeAt(pos); } + T* operator[](s32 pos) const { return at(pos); } + + // XXX: Does this use at()? + T* front() const { return at(0); } + T* back() const { return at(mPtrNum - 1); } + + void pushBack(const T& item) + { + if (isFull()) + SEAD_ASSERT_MSG(false, "buffer full."); + else + PtrArrayImpl::pushBack(alloc(item)); + } + + template + T* emplaceBack(Args&&... args) + { + if (isFull()) + { + SEAD_ASSERT_MSG(false, "buffer full."); + return nullptr; + } + T* item = new (mFreeList.alloc()) T(std::forward(args)...); + PtrArrayImpl::pushBack(item); + return item; + } + + void insert(s32 pos, const T& item) { PtrArrayImpl::insert(pos, alloc(item)); } + + void erase(int index) { erase(index, 1); } + + void erase(int index, int count) + { + if (index + count <= size()) + { + for (int i = index; i < index + count; ++i) + { + auto* ptr = unsafeAt(i); + ptr->~T(); + mFreeList.free(ptr); + } + } + PtrArrayImpl::erase(index, count); + } + + void clear() + { + for (s32 i = 0; i < mPtrNum; ++i) + { + auto* ptr = unsafeAt(i); + ptr->~T(); + mFreeList.free(ptr); + } + mPtrNum = 0; + } + + using CompareCallback = s32 (*)(const T*, const T*); + + void sort() { sort(compareT); } + void sort(CompareCallback cmp) { PtrArrayImpl::sort_(cmp); } + void heapSort() { heapSort(compareT); } + void heapSort(CompareCallback cmp) { PtrArrayImpl::heapSort_(cmp); } + + bool equal(const ObjArray& other, CompareCallback cmp) const + { + return PtrArrayImpl::equal(other, cmp); + } + + s32 compare(const ObjArray& other, CompareCallback cmp) const + { + return PtrArrayImpl::compare(other, cmp); + } + + s32 binarySearch(const T* ptr) const { return PtrArrayImpl::binarySearch(ptr, compareT); } + s32 binarySearch(const T* ptr, CompareCallback cmp) const + { + return PtrArrayImpl::binarySearch(ptr, cmp); + } + + bool operator==(const ObjArray& other) const { return equal(other, compareT); } + bool operator!=(const ObjArray& other) const { return !(*this == other); } + bool operator<(const ObjArray& other) const { return compare(other) < 0; } + bool operator<=(const ObjArray& other) const { return compare(other) <= 0; } + bool operator>(const ObjArray& other) const { return compare(other) > 0; } + bool operator>=(const ObjArray& other) const { return compare(other) >= 0; } + + void uniq() { PtrArrayImpl::uniq(compareT); } + void uniq(CompareCallback cmp) { PtrArrayImpl::uniq(cmp); } + + class iterator + { + public: + iterator(T* const* pptr) : mPPtr{pptr} {} + bool operator==(const iterator& other) const { return mPPtr == other.mPPtr; } + bool operator!=(const iterator& other) const { return !(*this == other); } + iterator& operator++() + { + ++mPPtr; + return *this; + } + T& operator*() const { return **mPPtr; } + T* operator->() const { return *mPPtr; } + + private: + T* const* mPPtr; + }; + + iterator begin() const { return iterator(data()); } + iterator end() const { return iterator(data() + mPtrNum); } + + class constIterator + { + public: + constIterator(const T* const* pptr) : mPPtr{pptr} {} + bool operator==(const constIterator& other) const { return mPPtr == other.mPPtr; } + bool operator!=(const constIterator& other) const { return !(*this == other); } + constIterator& operator++() + { + ++mPPtr; + return *this; + } + const T& operator*() const { return **mPPtr; } + const T* operator->() const { return *mPPtr; } + + private: + const T* const* mPPtr; + }; + + constIterator constBegin() const { return constIterator(data()); } + constIterator constEnd() const { return constIterator(data() + mPtrNum); } + + T** data() const { return reinterpret_cast(mPtrs); } + +private: + union Node + { + void* next_node; + T elem; + }; + +public: + static constexpr size_t ElementSize = sizeof(Node); + + static constexpr size_t calculateWorkBufferSize(size_t n) + { + return n * (ElementSize + sizeof(T*)); + } + +protected: + T* alloc(const T& item) + { + void* storage = mFreeList.alloc(); + if (!storage) + return nullptr; + return new (storage) T(item); + } + + static int compareT(const void* a_, const void* b_) + { + const T* a = static_cast(a_); + const T* b = static_cast(b_); + if (*a < *b) + return -1; + if (*b < *a) + return 1; + return 0; + } + + sead::FreeList mFreeList; +}; + +template +class FixedObjArray : public ObjArray +{ +public: + FixedObjArray() : ObjArray(N, &mWork) {} + + // These do not make sense for a *fixed* array. + void setBuffer(s32 ptrNumMax, void* buf) = delete; + void allocBuffer(s32 ptrNumMax, Heap* heap, s32 alignment = sizeof(void*)) = delete; + bool tryAllocBuffer(s32 ptrNumMax, Heap* heap, s32 alignment = sizeof(void*)) = delete; + void freeBuffer() = delete; + +private: + std::aligned_storage_t::calculateWorkBufferSize(N), + std::max(alignof(T), alignof(T*))> + mWork; +}; + +} // namespace sead diff --git a/lib/sead/include/container/seadObjList.h b/lib/sead/include/container/seadObjList.h new file mode 100644 index 00000000..ad719eb7 --- /dev/null +++ b/lib/sead/include/container/seadObjList.h @@ -0,0 +1,245 @@ +#pragma once + +#include +#include "basis/seadNew.h" +#include "basis/seadRawPrint.h" +#include "basis/seadTypes.h" +#include "container/seadFreeList.h" +#include "container/seadListImpl.h" +#include "prim/seadPtrUtil.h" + +namespace sead +{ +template +class ObjList : public ListImpl +{ +public: + ObjList() = default; + ObjList(s32 max_num, void* buf) { setBuffer(max_num, buf); } + + void allocBuffer(s32 capacity, Heap* heap, s32 alignment = sizeof(void*)) + { + if (capacity < 1) + return; + + setBuffer(capacity, + new (heap, alignment, std::nothrow) u8[calculateWorkBufferSize(capacity)]); + } + + bool tryAllocBuffer(s32 capacity, Heap* heap, s32 alignment = sizeof(void*)) + { + if (capacity < 1) + return false; + + auto* buf = new (heap, alignment, std::nothrow) u8[calculateWorkBufferSize(capacity)]; + if (!buf) + return false; + + setBuffer(capacity, buf); + return true; + } + + void setBuffer(s32 max_num, void* buf) + { + if (!buf) + { + SEAD_ASSERT_MSG(false, "buf is null"); + return; + } + + mFreeList.setWork(buf, ElementSize, max_num); + mMaxNum = max_num; + } + + void freeBuffer() + { + if (!isBufferReady()) + return; + + clear(); + + if (mFreeList.work()) + delete[] static_cast(mFreeList.work()); + + mMaxNum = 0; + mFreeList.reset(); + } + + bool isBufferReady() const { return mFreeList.work() != nullptr; } + + bool isFull() const { return size() >= mMaxNum; } + + T* front() const { return listNodeToObjWithNullCheck(ListImpl::front()); } + T* back() const { return listNodeToObjWithNullCheck(ListImpl::back()); } + + T popBack() + { + auto* item = back(); + if (!item) + return {}; + + T copy = *item; + erase(item); + return copy; + } + + T popFront() + { + auto* item = front(); + if (!item) + return {}; + + T copy = *item; + erase(item); + return copy; + } + + template + T* emplaceBack(Args&&... args) + { + if (isFull()) + { + SEAD_ASSERT_MSG(false, "buffer full."); + return nullptr; + } + Node* item = new (mFreeList.alloc()) Node{T{std::forward(args)...}, {}}; + ListImpl::pushBack(&item->node); + return &item->item; + } + + void erase(T* item) + { + ListImpl::erase(objToListNode(item)); + item->~T(); + mFreeList.free(item); + } + + void clear() + { + ListNode* node = mStartEnd.next(); + while (node != &mStartEnd) + { + // Fetch the next pointer before erasing the item from the linked list. + ListNode* next = node->next(); + ListImpl::erase(node); + + auto* item = listNodeToObj(node); + item->~T(); + mFreeList.free(item); + + node = next; + } + } + + T* prev(const T* obj) const + { + ListNode* prev_node = objToListNode(obj)->prev(); + if (prev_node == &mStartEnd) + return nullptr; + return listNodeToObj(prev_node); + } + + T* next(const T* obj) const + { + ListNode* next_node = objToListNode(obj)->next(); + if (next_node == &mStartEnd) + return nullptr; + return listNodeToObj(next_node); + } + + T* nth(s32 n) const { return listNodeToObjWithNullCheck(ListImpl::nth(n)); } + + s32 indexOf(const T* obj) const { return ListImpl::indexOf(objToListNode(obj)); } + + bool isNodeLinked(const T* obj) const { return objToListNode(obj)->isLinked(); } + + class iterator + { + public: + explicit iterator(T* ptr) : mPtr{ptr} {} + bool operator==(const iterator& other) const { return mPtr == other.mPtr; } + bool operator!=(const iterator& other) const { return !operator==(other); } + iterator& operator++() + { + constexpr auto offset = Node::getListNodeOffset(); + auto* node = static_cast(PtrUtil::addOffset(mPtr, offset))->next(); + mPtr = static_cast(PtrUtil::addOffset(node, -offset)); + return *this; + } + T& operator*() const { return *mPtr; } + T* operator->() const { return mPtr; } + + private: + T* mPtr; + }; + + iterator begin() const { return iterator(listNodeToObj(mStartEnd.next())); } + iterator end() const { return iterator(listNodeToObj(const_cast(&mStartEnd))); } + iterator begin(T* ptr) const { return iterator(ptr); } + + static constexpr size_t calculateWorkBufferSize(size_t n) { return n * ElementSize; } + +private: + struct Node + { + static constexpr auto getListNodeOffset() { return offsetof(Node, node); } + T item; + ListNode node; + }; + static_assert(offsetof(Node, item) == 0, "item must be at offset 0 in Node"); + + ListNode* objToListNode(T* obj) const + { + return static_cast(PtrUtil::addOffset(obj, Node::getListNodeOffset())); + } + + const ListNode* objToListNode(const T* obj) const + { + return static_cast(PtrUtil::addOffset(obj, Node::getListNodeOffset())); + } + + T* listNodeToObj(ListNode* node) const + { + return static_cast(PtrUtil::addOffset(node, -Node::getListNodeOffset())); + } + + const T* listNodeToObj(const ListNode* node) const + { + return static_cast(PtrUtil::addOffset(node, -Node::getListNodeOffset())); + } + + T* listNodeToObjWithNullCheck(ListNode* node) const + { + return node ? listNodeToObj(node) : nullptr; + } + + const T* listNodeToObjWithNullCheck(const ListNode* node) const + { + return node ? listNodeToObj(node) : nullptr; + } + + static constexpr size_t ElementSize = std::max(sizeof(Node), FreeList::cPtrSize); + + sead::FreeList mFreeList; + s32 mMaxNum = 0; +}; + +template +class FixedObjList : public ObjList +{ +public: + FixedObjList() : ObjList(N, &mWork) {} + + // These do not make sense for a *fixed* array. + void setBuffer(s32 ptrNumMax, void* buf) = delete; + void allocBuffer(s32 ptrNumMax, Heap* heap, s32 alignment = sizeof(void*)) = delete; + bool tryAllocBuffer(s32 ptrNumMax, Heap* heap, s32 alignment = sizeof(void*)) = delete; + void freeBuffer() = delete; + +private: + std::aligned_storage_t::calculateWorkBufferSize(N), + std::max(alignof(T), alignof(T*))> + mWork; +}; + +} // namespace sead diff --git a/lib/sead/include/container/seadOffsetList.h b/lib/sead/include/container/seadOffsetList.h new file mode 100644 index 00000000..76ec2cbf --- /dev/null +++ b/lib/sead/include/container/seadOffsetList.h @@ -0,0 +1,219 @@ +#ifndef SEAD_OFFSET_LIST_H_ +#define SEAD_OFFSET_LIST_H_ + +#include +#include +#include +#include + +namespace sead +{ +template +class OffsetList : public ListImpl +{ +public: + OffsetList() = default; + + void initOffset(s32 offset) { mOffset = offset; } + + void clear() { ListImpl::clear(); } + + void pushBack(T* item) + { + SEAD_ASSERT(mOffset >= 0); + ListImpl::pushBack(objToListNode(item)); + } + + void pushFront(T* item) + { + SEAD_ASSERT(mOffset >= 0); + ListImpl::pushFront(objToListNode(item)); + } + + T* popBack() { return listNodeToObjWithNullCheck(ListImpl::popBack()); } + + T* popFront() { return listNodeToObjWithNullCheck(ListImpl::popFront()); } + + void insertBefore(const T* obj, T* obj_to_insert) + { + ListImpl::insertBefore(const_cast(objToListNode(obj)), + objToListNode(obj_to_insert)); + } + void insertAfter(const T* obj, T* obj_to_insert) + { + ListImpl::insertAfter(const_cast(objToListNode(obj)), + objToListNode(obj_to_insert)); + } + + void erase(T* item) { ListImpl::erase(objToListNode(item)); } + + T* front() const { return listNodeToObjWithNullCheck(ListImpl::front()); } + + T* back() const { return listNodeToObjWithNullCheck(ListImpl::back()); } + + T* prev(const T* obj) const + { + ListNode* prev_node = objToListNode(obj)->prev(); + if (prev_node == &mStartEnd) + return nullptr; + return listNodeToObj(prev_node); + } + + T* next(const T* obj) const + { + ListNode* next_node = objToListNode(obj)->next(); + if (next_node == &mStartEnd) + return nullptr; + return listNodeToObj(next_node); + } + + T* nth(s32 n) const { return listNodeToObjWithNullCheck(ListImpl::nth(n)); } + + s32 indexOf(const T* obj) const { return ListImpl::indexOf(objToListNode(obj)); } + + bool isNodeLinked(const T* obj) const { return objToListNode(obj)->isLinked(); } + + void swap(T* obj1, T* obj2) { ListImpl::swap(objToListNode(obj1), objToListNode(obj2)); } + void moveAfter(T* basis, T* obj) + { + ListImpl::moveAfter(objToListNode(basis), objToListNode(obj)); + } + void moveBefore(T* basis, T* obj) + { + ListImpl::moveBefore(objToListNode(basis), objToListNode(obj)); + } + + using CompareCallback = int (*)(const T*, const T*); + + void sort() { sort(compareT); } + void sort(CompareCallback cmp) { ListImpl::sort(mOffset, cmp); } + void mergeSort() { mergeSort(compareT); } + void mergeSort(CompareCallback cmp) { ListImpl::mergeSort(mOffset, cmp); } + + T* find(const T* obj) const { return find(obj, compareT); } + T* find(const T* obj, CompareCallback cmp) const + { + return listNodeToObj(ListImpl::find(obj, mOffset, cmp)); + } + + void uniq() { uniq(compareT); } + void uniq(CompareCallback cmp) { ListImpl::uniq(mOffset, cmp); } + + class iterator + { + public: + iterator(T* ptr, s32 offset) : mPtr{ptr}, mOffset{offset} {} + bool operator==(const iterator& other) const { return mPtr == other.mPtr; } + bool operator!=(const iterator& other) const { return !(*this == other); } + iterator& operator++() + { + ListNode* node = static_cast(PtrUtil::addOffset(mPtr, mOffset))->next(); + mPtr = static_cast(PtrUtil::addOffset(node, -mOffset)); + return *this; + } + T& operator*() const { return *mPtr; } + T* operator->() const { return mPtr; } + + private: + T* mPtr; + s32 mOffset; + }; + + iterator begin() const { return iterator(listNodeToObj(mStartEnd.next()), mOffset); } + iterator end() const + { + return iterator(listNodeToObj(const_cast(&mStartEnd)), mOffset); + } + iterator begin(T* ptr) const { return iterator(ptr, mOffset); } + + class robustIterator + { + public: + robustIterator(T* ptr, s32 offset) + : mPtr{ptr}, mNextNode(static_cast(PtrUtil::addOffset(ptr, offset))->next()), + mOffset{offset} + { + } + bool operator==(const robustIterator& other) const { return mPtr == other.mPtr; } + bool operator!=(const robustIterator& other) const { return !operator==(other); } + robustIterator& operator++() + { + mPtr = static_cast(PtrUtil::addOffset(mNextNode, -mOffset)); + mNextNode = mNextNode->next(); + return *this; + } + T& operator*() const { return *mPtr; } + T* operator->() const { return mPtr; } + + private: + T* mPtr; + ListNode* mNextNode; + s32 mOffset; + }; + + robustIterator robustBegin() const + { + return robustIterator(listNodeToObj(mStartEnd.next()), mOffset); + } + + robustIterator robustEnd() const + { + return robustIterator(listNodeToObj(const_cast(&mStartEnd)), mOffset); + } + + robustIterator robustBegin(T* ptr) const { return robustIterator(ptr, mOffset); } + + struct RobustRange + { + auto begin() const { return mList.robustBegin(); } + auto end() const { return mList.robustEnd(); } + const OffsetList& mList; + }; + RobustRange robustRange() const { return {*this}; } + +protected: + static int compareT(const T* lhs, const T* rhs) + { + if (lhs < rhs) + return -1; + if (lhs > rhs) + return 1; + return 0; + } + + ListNode* objToListNode(T* obj) const + { + return static_cast(PtrUtil::addOffset(obj, mOffset)); + } + + const ListNode* objToListNode(const T* obj) const + { + return static_cast(PtrUtil::addOffset(obj, mOffset)); + } + + T* listNodeToObj(ListNode* node) const + { + return static_cast(PtrUtil::addOffset(node, -mOffset)); + } + + const T* listNodeToObj(const ListNode* node) const + { + return static_cast(PtrUtil::addOffset(node, -mOffset)); + } + + T* listNodeToObjWithNullCheck(ListNode* node) const + { + return node ? listNodeToObj(node) : nullptr; + } + + const T* listNodeToObjWithNullCheck(const ListNode* node) const + { + return node ? listNodeToObj(node) : nullptr; + } + + s32 mOffset = -1; +}; + +} // namespace sead + +#endif // SEAD_OFFSET_LIST_H_ diff --git a/lib/sead/include/container/seadOrderedSet.h b/lib/sead/include/container/seadOrderedSet.h new file mode 100644 index 00000000..7093648c --- /dev/null +++ b/lib/sead/include/container/seadOrderedSet.h @@ -0,0 +1,189 @@ +#pragma once + +#include "container/seadTreeMap.h" + +namespace sead +{ +/// Requires Value to have operator< defined +/// This can be specialized, but all specializations must define `compare` as follows. +template +struct OrderedSetItemImpl +{ + OrderedSetItemImpl() = default; + // NOLINTNEXTLINE(google-explicit-constructor) + OrderedSetItemImpl(const Value& value_) : value(value_) {} + OrderedSetItemImpl& operator=(const Value& value_) + { + value = value_; + return *this; + } + + /// Returns -1 if this->value < rhs, 0 if this->value = rhs and 1 if this->value > rhs. + s32 compare(const OrderedSetItemImpl& rhs) const + { + if (value < rhs.value) + return -1; + if (rhs.value < value) + return 1; + return 0; + } + + Value value; +}; + +/// This is essentially std::set. Values are stored in a red-black tree in an order +/// determined by the partial order defined for Value (via operator<). +template +class OrderedSet : public TreeMapImpl> +{ +public: + using MapImpl = TreeMapImpl>; + class Node : public MapImpl::Node + { + public: + Node(OrderedSet* set, const Value& value) : mSet(set) { this->mKey = value; } + + void erase_() override; + + // Values cannot be modified. + const Value& value() const { return this->key().value; } + + private: + friend class OrderedSet; + OrderedSet* mSet; + }; + + /// Clears the set and frees the allocated buffer (if needed). + /// Should only be used if the buffer was allocated using allocBuffer. + void finalize() + { + clear(); + freeBuffer(); + } + + bool allocBuffer(s32 node_max, Heap* heap, s32 alignment = sizeof(void*)); + void setBuffer(s32 node_max, void* buffer); + /// Should only be used if the buffer was allocated using allocBuffer. + void freeBuffer(); + + const Value* insert(const Value& value); + void clear(); + + Node* find(const Value& value) const; + + // Callable must have the signature Value& + template + void forEach(const Callable& delegate) const; + + Node* startIterating() const { return static_cast(MapImpl::startIterating()); } + Node* nextNode(Node* node) const { return static_cast(MapImpl::nextNode(node)); } + +private: + void eraseNodeForClear_(typename MapImpl::Node* node); + + FreeList mFreeList; + s32 mSize = 0; + s32 mCapacity = 0; +}; + +template +inline bool OrderedSet::allocBuffer(s32 node_max, Heap* heap, s32 alignment) +{ + SEAD_ASSERT(mFreeList.work() == nullptr); + if (node_max <= 0) + { + SEAD_ASSERT_MSG(false, "node_max[%d] must be larger than zero", node_max); + AllocFailAssert(heap, node_max * sizeof(Node), alignment); + } + + void* work = AllocBuffer(node_max * sizeof(Node), heap, alignment); + if (!work) + return false; + setBuffer(node_max, work); + return true; +} + +template +inline void OrderedSet::setBuffer(s32 node_max, void* buffer) +{ + mCapacity = node_max; + mFreeList.setWork(buffer, sizeof(Node), node_max); +} + +template +inline void OrderedSet::freeBuffer() +{ + void* buffer = mFreeList.work(); + if (!buffer) + return; + + mSize = 0; + MapImpl::clear(); + ::operator delete[](buffer); + mCapacity = 0; + mFreeList.reset(); +} + +template +inline const Value* OrderedSet::insert(const Value& value) +{ + if (mSize >= mCapacity) + { + if (Node* node = find(value)) + { + node->mKey = value; + return &node->value(); + } + SEAD_ASSERT_MSG(false, "map is full."); + return nullptr; + } + + Node* node = new (mFreeList.alloc()) Node(this, value); + ++mSize; + MapImpl::insert(node); + return &node->value(); +} + +template +inline void OrderedSet::clear() +{ + Delegate1, typename MapImpl::Node*> delegate(this, + &OrderedSet::eraseNodeForClear_); + MapImpl::forEach(delegate); + mSize = 0; + MapImpl::clear(); +} + +template +inline typename OrderedSet::Node* OrderedSet::find(const Value& value) const +{ + return static_cast(MapImpl::find(value)); +} + +template +template +inline void OrderedSet::forEach(const Callable& delegate) const +{ + MapImpl::forEach([&delegate](auto* base_node) { + auto* node = static_cast(base_node); + delegate(node->value()); + }); +} + +template +inline void OrderedSet::eraseNodeForClear_(typename MapImpl::Node* node) +{ + // Note: Nintendo does not call the destructor, which is dangerous... + mFreeList.free(node); +} + +template +inline void OrderedSet::Node::erase_() +{ + OrderedSet* const map = mSet; + void* const this_ = this; + // Note: Nintendo does not call the destructor, which is dangerous... + map->mFreeList.free(this_); + --map->mSize; +} +} // namespace sead diff --git a/lib/sead/include/container/seadPtrArray.h b/lib/sead/include/container/seadPtrArray.h new file mode 100644 index 00000000..f597dfe8 --- /dev/null +++ b/lib/sead/include/container/seadPtrArray.h @@ -0,0 +1,377 @@ +#ifndef SEAD_PTR_ARRAY_H_ +#define SEAD_PTR_ARRAY_H_ + +#include +#include +#include +#include +#include + +namespace sead +{ +class Heap; +class Random; + +class PtrArrayImpl +{ +public: + PtrArrayImpl() = default; + PtrArrayImpl(s32 ptrNumMax, void* buf) { setBuffer(ptrNumMax, buf); } + + void setBuffer(s32 ptrNumMax, void* buf); + void allocBuffer(s32 ptrNumMax, Heap* heap, s32 alignment = sizeof(void*)); + bool tryAllocBuffer(s32 ptrNumMax, Heap* heap, s32 alignment = sizeof(void*)); + void freeBuffer(); + bool isBufferReady() const { return mPtrs != nullptr; } + + bool isEmpty() const { return mPtrNum == 0; } + bool isFull() const { return mPtrNum >= mPtrNumMax; } + + s32 size() const { return mPtrNum; } + s32 capacity() const { return mPtrNumMax; } + + void erase(s32 position) { erase(position, 1); } + void erase(s32 position, s32 count); + void clear() { mPtrNum = 0; } + + // TODO + void resize(s32 size); + // TODO + void unsafeResize(s32 size); + + void swap(s32 pos1, s32 pos2) + { + auto* ptr = mPtrs[pos1]; + mPtrs[pos1] = mPtrs[pos2]; + mPtrs[pos2] = ptr; + } + void reverse(); + void shuffle() + { + Random random; + shuffle(&random); + } + void shuffle(Random* random); + +protected: + using CompareCallbackImpl = int (*)(const void* a, const void* b); + + void* at(s32 idx) const + { + if (u32(mPtrNum) <= u32(idx)) + { + SEAD_ASSERT_MSG(false, "index exceeded [%d/%d]", idx, mPtrNum); + return nullptr; + } + return mPtrs[idx]; + } + + void* unsafeAt(s32 idx) const { return mPtrs[idx]; } + + // XXX: should this use at()? + void* front() const { return mPtrs[0]; } + void* back() const { return mPtrs[mPtrNum - 1]; } + + void pushBack(void* ptr) + { + if (isFull()) + { + SEAD_ASSERT_MSG(false, "list is full."); + return; + } + // Simplest insert case, so this is implemented directly without using insert(). + mPtrs[mPtrNum] = ptr; + ++mPtrNum; + } + + void pushFront(void* ptr) { insert(0, ptr); } + + void* popBack() { return isEmpty() ? nullptr : mPtrs[--mPtrNum]; } + + void* popFront() + { + if (isEmpty()) + return nullptr; + + void* result = mPtrs[0]; + erase(0); + return result; + } + + void replace(s32 idx, void* ptr) { mPtrs[idx] = ptr; } + + void* find(const void* ptr, CompareCallbackImpl cmp) const + { + for (s32 i = 0; i < mPtrNum; ++i) + { + if (cmp(mPtrs[i], ptr) == 0) + return mPtrs[i]; + } + return nullptr; + } + + s32 search(const void* ptr, CompareCallbackImpl cmp) const + { + for (s32 i = 0; i < mPtrNum; ++i) + { + if (cmp(mPtrs[i], ptr) == 0) + return i; + } + return -1; + } + + bool equal(const PtrArrayImpl& other, CompareCallbackImpl cmp) const + { + if (mPtrNum != other.mPtrNum) + return false; + + for (s32 i = 0; i < mPtrNum; ++i) + { + if (cmp(mPtrs[i], other.mPtrs[i]) != 0) + return false; + } + return true; + } + + s32 indexOf(const void* ptr) const + { + for (s32 i = 0; i < mPtrNum; ++i) + { + if (mPtrs[i] == ptr) + return i; + } + return -1; + } + + void createVacancy(s32 pos, s32 count) + { + if (mPtrNum <= pos) + return; + + MemUtil::copyOverlap(mPtrs + pos + count, mPtrs + pos, + s32(sizeof(void*)) * (mPtrNum - pos)); + } + + void insert(s32 idx, void* ptr); + void insertArray(s32 idx, void* array, s32 array_length, s32 elem_size); + bool checkInsert(s32 idx, s32 num); + + template + void sort_(Compare cmp) + { + // Note: Nintendo did not use + std::sort(mPtrs, mPtrs + size(), [&](const void* a, const void* b) { + return cmp(static_cast(a), static_cast(b)) < 0; + }); + } + + template + void heapSort_(Compare cmp) + { + // Note: Nintendo did not use + const auto less_cmp = [&](const void* a, const void* b) { + return cmp(static_cast(a), static_cast(b)) < 0; + }; + std::make_heap(mPtrs, mPtrs + size(), less_cmp); + std::sort_heap(mPtrs, mPtrs + size(), less_cmp); + } + + void heapSort(CompareCallbackImpl cmp); + + s32 compare(const PtrArrayImpl& other, CompareCallbackImpl cmp) const; + void uniq(CompareCallbackImpl cmp); + + s32 binarySearch(const void* ptr, CompareCallbackImpl cmp) const + { + if (mPtrNum == 0) + return -1; + + s32 a = 0; + s32 b = mPtrNum - 1; + while (a < b) + { + const s32 m = (a + b) / 2; + const s32 c = cmp(mPtrs[m], ptr); + if (c == 0) + return m; + if (c < 0) + a = m + 1; + else + b = m; + } + + if (cmp(mPtrs[a], ptr) == 0) + return a; + + return -1; + } + + s32 mPtrNum = 0; + s32 mPtrNumMax = 0; + void** mPtrs = nullptr; +}; + +template +class PtrArray : public PtrArrayImpl +{ +public: + PtrArray() = default; + PtrArray(s32 ptrNumMax, T** buf) : PtrArrayImpl(ptrNumMax, buf) {} + + T* at(s32 pos) const { return static_cast(PtrArrayImpl::at(pos)); } + T* unsafeAt(s32 pos) const { return static_cast(PtrArrayImpl::unsafeAt(pos)); } + T* operator()(s32 pos) const { return unsafeAt(pos); } + T* operator[](s32 pos) const { return at(pos); } + + // XXX: Does this use at()? + T* front() const { return at(0); } + T* back() const { return at(mPtrNum - 1); } + + void pushBack(T* ptr) { PtrArrayImpl::pushBack(constCast(ptr)); } + void pushFront(T* ptr) { PtrArrayImpl::pushFront(constCast(ptr)); } + + T* popBack() { return static_cast(PtrArrayImpl::popBack()); } + T* popFront() { return static_cast(PtrArrayImpl::popFront()); } + + void insert(s32 pos, T* ptr) { PtrArrayImpl::insert(pos, constCast(ptr)); } + void insert(s32 pos, T* array, s32 count) + { + // XXX: is this right? + PtrArrayImpl::insertArray(pos, constCast(array), count, sizeof(T)); + } + void replace(s32 pos, T* ptr) { PtrArrayImpl::replace(pos, constCast(ptr)); } + + s32 indexOf(const T* ptr) const { return PtrArrayImpl::indexOf(ptr); } + + using CompareCallback = s32 (*)(const T*, const T*); + + void sort() { sort(compareT); } + void sort(CompareCallback cmp) { PtrArrayImpl::sort_(cmp); } + void heapSort() { heapSort(compareT); } + void heapSort(CompareCallback cmp) { PtrArrayImpl::heapSort_(cmp); } + + bool equal(const PtrArray& other, CompareCallback cmp) const + { + return PtrArrayImpl::equal(other, cmp); + } + + s32 compare(const PtrArray& other, CompareCallback cmp) const + { + return PtrArrayImpl::compare(other, cmp); + } + + T* find(const T* ptr) const + { + return PtrArrayImpl::find(ptr, + [](const void* a, const void* b) { return a == b ? 0 : -1; }); + } + T* find(const T* ptr, CompareCallback cmp) const { return PtrArrayImpl::find(ptr, cmp); } + s32 search(const T* ptr) const + { + return PtrArrayImpl::search(ptr, + [](const void* a, const void* b) { return a == b ? 0 : -1; }); + } + s32 search(const T* ptr, CompareCallback cmp) const { return PtrArrayImpl::search(ptr, cmp); } + s32 binarySearch(const T* ptr) const { return PtrArrayImpl::binarySearch(ptr, compareT); } + s32 binarySearch(const T* ptr, CompareCallback cmp) const + { + return PtrArrayImpl::binarySearch(ptr, cmp); + } + + bool operator==(const PtrArray& other) const { return equal(other, compareT); } + bool operator!=(const PtrArray& other) const { return !(*this == other); } + bool operator<(const PtrArray& other) const { return compare(other) < 0; } + bool operator<=(const PtrArray& other) const { return compare(other) <= 0; } + bool operator>(const PtrArray& other) const { return compare(other) > 0; } + bool operator>=(const PtrArray& other) const { return compare(other) >= 0; } + + void uniq() { PtrArrayImpl::uniq(compareT); } + void uniq(CompareCallback cmp) { PtrArrayImpl::uniq(cmp); } + + class iterator + { + public: + iterator(T* const* pptr) : mPPtr{pptr} {} + bool operator==(const iterator& other) const { return mPPtr == other.mPPtr; } + bool operator!=(const iterator& other) const { return !(*this == other); } + iterator& operator++() + { + ++mPPtr; + return *this; + } + T& operator*() const { return **mPPtr; } + T* operator->() const { return *mPPtr; } + + private: + T* const* mPPtr; + }; + + iterator begin() const { return iterator(data()); } + iterator end() const { return iterator(data() + mPtrNum); } + + class constIterator + { + public: + constIterator(const T* const* pptr) : mPPtr{pptr} {} + bool operator==(const constIterator& other) const { return mPPtr == other.mPPtr; } + bool operator!=(const constIterator& other) const { return !(*this == other); } + constIterator& operator++() + { + ++mPPtr; + return *this; + } + const T& operator*() const { return **mPPtr; } + const T* operator->() const { return *mPPtr; } + + private: + const T* const* mPPtr; + }; + + constIterator constBegin() const { return constIterator(data()); } + constIterator constEnd() const { return constIterator(data() + mPtrNum); } + + T** data() const { return reinterpret_cast(mPtrs); } + T** dataBegin() const { return data(); } + T** dataEnd() const { return data() + mPtrNum; } + +protected: + static void* constCast(const T* ptr) + { + // Unfortunately, we need to cast away const because several PtrArrayImpl functions + // only take void* even though the pointed-to object isn't actually modified. + return static_cast(const_cast*>(ptr)); + } + + static int compareT(const void* a_, const void* b_) + { + const T* a = static_cast(a_); + const T* b = static_cast(b_); + if (*a < *b) + return -1; + if (*b < *a) + return 1; + return 0; + } +}; + +template +class FixedPtrArray : public PtrArray +{ +public: + FixedPtrArray() : PtrArray(N, mWork) {} + + // These do not make sense for a *fixed* array. + void setBuffer(s32 ptrNumMax, void* buf) = delete; + void allocBuffer(s32 ptrNumMax, Heap* heap, s32 alignment = sizeof(void*)) = delete; + bool tryAllocBuffer(s32 ptrNumMax, Heap* heap, s32 alignment = sizeof(void*)) = delete; + void freeBuffer() = delete; + +private: + // Nintendo uses an untyped u8[N*sizeof(void*)] buffer. That is undefined behavior, + // so we will not do that. + T* mWork[N]; +}; + +} // namespace sead + +#endif // SEAD_PTR_ARRAY_H_ diff --git a/lib/sead/include/container/seadRingBuffer.h b/lib/sead/include/container/seadRingBuffer.h new file mode 100644 index 00000000..ff9c08fd --- /dev/null +++ b/lib/sead/include/container/seadRingBuffer.h @@ -0,0 +1,337 @@ +#pragma once + +#include +#include + +#include +#include +#include +#include +#include + +namespace sead +{ +class Heap; + +template +class RingBuffer +{ +public: + RingBuffer() = default; + RingBuffer(s32 capacity, T* buffer) { setBuffer(capacity, buffer); } + template + explicit RingBuffer(T (&array)[N]) : RingBuffer(N, array) + { + } + + class iterator + { + public: + explicit iterator(RingBuffer* buffer, s32 index = 0) : mIndex(index), mBuffer(buffer) {} + bool operator==(const iterator& rhs) const + { + return mIndex == rhs.mIndex && mBuffer == rhs.mBuffer; + } + bool operator!=(const iterator& rhs) const { return !operator==(rhs); } + iterator& operator++() + { + ++mIndex; + return *this; + } + T& operator*() const { return buffer()(mIndex); } + T* operator->() const { return &buffer()(mIndex); } + s32 getIndex() const { return mIndex; } + + private: + RingBuffer& buffer() const { return *mBuffer; } + + s32 mIndex; + RingBuffer* mBuffer; + }; + + class constIterator + { + public: + explicit constIterator(const RingBuffer* buffer, s32 index = 0) + : mIndex(index), mBuffer(buffer) + { + } + bool operator==(const constIterator& rhs) const + { + return mIndex == rhs.mIndex && mBuffer == rhs.mBuffer; + } + bool operator!=(const constIterator& rhs) const { return !operator==(rhs); } + constIterator& operator++() + { + ++mIndex; + return *this; + } + const T& operator*() const { return buffer()(mIndex); } + const T* operator->() const { return &buffer()(mIndex); } + s32 getIndex() const { return mIndex; } + + private: + const RingBuffer& buffer() const { return *mBuffer; } + + s32 mIndex; + const RingBuffer* mBuffer; + }; + + iterator begin() { return iterator(this); } + constIterator begin() const { return constIterator(this); } + iterator begin(s32 start_idx) { return iterator(this, wrapIndex(start_idx)); } + constIterator begin(s32 start_idx) const { return constIterator(this, wrapIndex(start_idx)); } + iterator end() { return iterator(this, mSize); } + constIterator end() const { return constIterator(this, mSize); } + + void allocBuffer(s32 capacity, s32 alignment) { void(tryAllocBuffer(capacity, alignment)); } + + void allocBuffer(s32 capacity, Heap* heap, s32 alignment = sizeof(void*)) + { + static_cast(tryAllocBuffer(capacity, heap, alignment)); + } + + bool tryAllocBuffer(s32 capacity, s32 alignment = sizeof(void*)) + { + SEAD_ASSERT(mBuffer == nullptr); + if (capacity > 0) + { + T* buffer = new (alignment, std::nothrow) T[capacity]; + if (buffer) + { + mBuffer = buffer; + mHead = mSize = 0; + mCapacity = capacity; + SEAD_ASSERT_MSG(PtrUtil::isAlignedPow2(mBuffer, sead::Mathi::abs(alignment)), + "don't set alignment for a class with destructor"); + return true; + } + return false; + } + SEAD_ASSERT_MSG(false, "numMax[%d] must be larger than zero", capacity); + return false; + } + + bool tryAllocBuffer(s32 capacity, Heap* heap, s32 alignment = sizeof(void*)) + { + SEAD_ASSERT(mBuffer == nullptr); + if (capacity > 0) + { + T* buffer = new (heap, alignment, std::nothrow) T[capacity]; + if (buffer) + { + mBuffer = buffer; + mHead = mSize = 0; + mCapacity = capacity; + SEAD_ASSERT_MSG(PtrUtil::isAlignedPow2(mBuffer, sead::Mathi::abs(alignment)), + "don't set alignment for a class with destructor"); + return true; + } + return false; + } + SEAD_ASSERT_MSG(false, "numMax[%d] must be larger than zero", capacity); + return false; + } + + void allocBufferAssert(s32 size, Heap* heap, s32 alignment = sizeof(void*)) + { + if (!tryAllocBuffer(size, heap, alignment)) + AllocFailAssert(heap, sizeof(T) * size, alignment); + } + + void freeBuffer() + { + if (mBuffer) + { + delete[] mBuffer; + mBuffer = nullptr; + mCapacity = 0; + mHead = 0; + mSize = 0; + } + } + + void setBuffer(s32 capacity, T* bufferptr) + { + if (capacity < 1) + { + SEAD_ASSERT_MSG(false, "numMax[%d] must be larger than zero", capacity); + return; + } + if (!bufferptr) + { + SEAD_ASSERT_MSG(false, "bufferptr is null"); + return; + } + mBuffer = bufferptr; + mHead = mSize = 0; + mCapacity = capacity; + } + + bool isBufferReady() const { return mBuffer != nullptr; } + + T& operator[](s32 idx) + { + if (u32(mSize) <= u32(idx)) + { + SEAD_ASSERT_MSG(false, "index exceeded [%d/%d/%d]", idx, mSize, mCapacity); + return mBuffer[0]; + } + return *unsafeGet(idx); + } + + const T& operator[](s32 idx) const + { + if (u32(mSize) <= u32(idx)) + { + SEAD_ASSERT_MSG(false, "index exceeded [%d/%d/%d]", idx, mSize, mCapacity); + return mBuffer[0]; + } + return *unsafeGet(idx); + } + + T* get(s32 idx) + { + if (u32(mSize) <= u32(idx)) + { + SEAD_ASSERT_MSG(false, "index exceeded [%d/%d/%d]", idx, mSize, mCapacity); + return nullptr; + } + return unsafeGet(idx); + } + + const T* get(s32 idx) const + { + if (u32(mSize) <= u32(idx)) + { + SEAD_ASSERT_MSG(false, "index exceeded [%d/%d/%d]", idx, mSize, mCapacity); + return nullptr; + } + + return unsafeGet(idx); + } + + T& operator()(s32 idx) { return *unsafeGet(idx); } + const T& operator()(s32 idx) const { return *unsafeGet(idx); } + + T* unsafeGet(s32 idx) { return &mBuffer[calcRealIdx(idx)]; } + const T* unsafeGet(s32 idx) const { return &mBuffer[calcRealIdx(idx)]; } + + T& front() { return *unsafeGet(0); } + const T& front() const { return *unsafeGet(0); } + + T& back() + { + if (mSize < 1) + { + SEAD_ASSERT_MSG(false, "no element"); + return mBuffer[0]; + } + return *unsafeGet(mSize - 1); + } + + const T& back() const + { + if (mSize < 1) + { + SEAD_ASSERT_MSG(false, "no element"); + return mBuffer[0]; + } + return *unsafeGet(mSize - 1); + } + + s32 capacity() const { return mCapacity; } + s32 size() const { return mSize; } + + bool empty() const { return mSize == 0; } + explicit operator bool() const { return !empty(); } + + T* data() { return mBuffer; } + const T* data() const { return mBuffer; } + + void forcePushBack(const T& item) + { + if (mSize < mCapacity) + { + pushBack(item); + return; + } + + if (mSize >= 1) + popFront(); + pushBack(item); + } + + bool pushBack(const T& item) + { + if (mSize >= mCapacity) + return false; + *unsafeGet(mSize++) = item; + return true; + } + + void forcePushBackwards(const T& item, u32 offset = 1) + { + mHead = (mHead < 1 ? mCapacity : mHead) - offset; + ++mSize; + *unsafeGet(0) = item; + } + + bool pushBackwards(const T& item) + { + if (mSize >= mCapacity) + return false; + forcePushBackwards(item); + return true; + } + + T popFront() + { + if (mSize >= 1) + { + T item = *unsafeGet(0); + mHead = mHead + 1 < mCapacity ? mHead + 1 : 0; + --mSize; + return item; + } + SEAD_ASSERT_MSG(false, "no element"); + return {}; + } + + void clear() { mHead = mSize = 0; } + +protected: + s32 calcRealIdx(s32 idx) const + { + s32 real_idx = mHead + idx; + if (real_idx >= mCapacity) + real_idx -= mCapacity; + return real_idx; + } + + s32 wrapIndex(s32 idx) const { return u32(idx) > u32(mSize) ? 0 : idx; } + + T* mBuffer = nullptr; + s32 mCapacity = 0; + s32 mHead = 0; + s32 mSize = 0; +}; + +template +class FixedRingBuffer : public RingBuffer +{ +public: + FixedRingBuffer() { RingBuffer::setBuffer(N, mData); } + + void allocBuffer(s32 capacity, s32 alignment) = delete; + void allocBuffer(s32 capacity, Heap* heap, s32 alignment) = delete; + bool tryAllocBuffer(s32 capacity, s32 alignment) = delete; + bool tryAllocBuffer(s32 capacity, Heap* heap, s32 alignment) = delete; + void allocBufferAssert(s32 size, Heap* heap, s32 alignment) = delete; + void freeBuffer() = delete; + void setBuffer(s32 capacity, T* bufferptr) = delete; + +private: + T mData[N]; +}; +} // namespace sead diff --git a/lib/sead/include/container/seadSafeArray.h b/lib/sead/include/container/seadSafeArray.h new file mode 100644 index 00000000..2de1d8ee --- /dev/null +++ b/lib/sead/include/container/seadSafeArray.h @@ -0,0 +1,158 @@ +#pragma once + +#include +#include +#include +#include + +namespace sead +{ +/// A lightweight std::array like wrapper for a C style array. +template +class SafeArray +{ +public: + T mBuffer[N]; + + T& operator[](s32 idx) + { + if (u32(idx) < N) + return mBuffer[idx]; +#ifdef MATCHING_HACK_NX_CLANG + // Force __LINE__ to be an odd number that cannot be encoded as an immediate for ORR. + // Otherwise, LLVM's register coalescer can get rid of too many register copies, + // which messes up register allocation. +#line 44 +#endif + SEAD_ASSERT_MSG(false, "range over [0, %d) : %d", N, idx); + return mBuffer[0]; + } + + const T& operator[](s32 idx) const + { + if (u32(idx) < N) + return mBuffer[idx]; +#ifdef MATCHING_HACK_NX_CLANG + // Force __LINE__ to be an even number that can be encoded as an immediate for ORR. + // Otherwise, LLVM's register coalescer can fail to get rid of some register copies, + // which messes up register allocation. +#line 59 +#endif + SEAD_ASSERT_MSG(false, "range over [0, %d) : %d", N, idx); + return mBuffer[0]; + } + + T& operator()(s32 idx) { return mBuffer[idx]; } + const T& operator()(s32 idx) const { return mBuffer[idx]; } + + T& front() { return mBuffer[0]; } + const T& front() const { return mBuffer[0]; } + T& back() { return mBuffer[N - 1]; } + const T& back() const { return mBuffer[N - 1]; } + + int size() const { return N; } + u32 getByteSize() const { return N * sizeof(T); } + + T* getBufferPtr() { return mBuffer; } + const T* getBufferPtr() const { return mBuffer; } + + void fill(const T& value) + { + for (s32 i = 0; i < N; ++i) + mBuffer[i] = value; + } + + class iterator + { + public: + iterator(T* buffer, s32 idx) : mBuffer(buffer), mIdx(idx) {} + bool operator==(const iterator& rhs) const + { + return mBuffer == rhs.mBuffer && mIdx == rhs.mIdx; + } + bool operator!=(const iterator& rhs) const { return !(*this == rhs); } + iterator& operator++() + { + ++mIdx; + return *this; + } + iterator& operator--() + { + --mIdx; + return *this; + } + T* operator->() const { return &mBuffer[mIdx]; } + T& operator*() const { return mBuffer[mIdx]; } + + private: + T* mBuffer; + s32 mIdx; + }; + + iterator begin() { return iterator(mBuffer, 0); } + iterator end() { return iterator(mBuffer, N); } + + class constIterator + { + public: + constIterator(const T* buffer, s32 idx) : mBuffer(buffer), mIdx(idx) {} + bool operator==(const constIterator& rhs) const + { + return mBuffer == rhs.mBuffer && mIdx == rhs.mIdx; + } + bool operator!=(const constIterator& rhs) const { return !(*this == rhs); } + constIterator& operator++() + { + ++mIdx; + return *this; + } + constIterator& operator--() + { + --mIdx; + return *this; + } + const T* operator->() const { return &mBuffer[mIdx]; } + const T& operator*() const { return mBuffer[mIdx]; } + + private: + const T* mBuffer; + s32 mIdx; + }; + + constIterator constBegin() const { return constIterator(mBuffer, 0); } + constIterator constEnd() const { return constIterator(mBuffer, N); } + + constIterator begin() const { return constIterator(mBuffer, 0); } + constIterator end() const { return constIterator(mBuffer, N); } +}; + +namespace detail +{ +// From https://en.cppreference.com/w/cpp/container/array/to_array +template +constexpr SafeArray, N> to_array_impl(T (&a)[N], std::index_sequence) +{ + return {{a[I]...}}; +} + +template +constexpr SafeArray, N> to_array_impl(T(&&a)[N], std::index_sequence) +{ + return {{std::move(a[I])...}}; +} +} // namespace detail + +// Implementation of C++20 std::to_array for sead::SafeArray. +template +constexpr sead::SafeArray, N> toArray(T (&a)[N]) +{ + return detail::to_array_impl(a, std::make_index_sequence{}); +} + +// Implementation of C++20 std::to_array for sead::SafeArray. +template +constexpr sead::SafeArray, N> toArray(T(&&a)[N]) +{ + return detail::to_array_impl(std::move(a), std::make_index_sequence{}); +} +} // namespace sead diff --git a/lib/sead/include/container/seadStrTreeMap.h b/lib/sead/include/container/seadStrTreeMap.h new file mode 100644 index 00000000..e74ac80d --- /dev/null +++ b/lib/sead/include/container/seadStrTreeMap.h @@ -0,0 +1,171 @@ +#pragma once + +#include "basis/seadTypes.h" +#include "container/seadFreeList.h" +#include "container/seadTreeMap.h" +#include "prim/seadDelegate.h" +#include "prim/seadSafeString.h" + +namespace sead +{ +/// Sorted associative container with fixed-length string keys. +/// This is essentially std::map +template +class StrTreeMap : public TreeMapImpl +{ +public: + using MapImpl = TreeMapImpl; + class Node : public MapImpl::Node + { + public: + Node(StrTreeMap* map, const SafeString& key, const Value& value) : mValue(value), mMap(map) + { + BufferedSafeString buffer(mKeyData, MaxKeyLength + 1); + buffer.copy(key); + this->mKey = buffer; + } + + void erase_() override; + + Value& value() { return mValue; } + const Value& value() const { return mValue; } + + private: + friend class StrTreeMap; + + Value mValue; + StrTreeMap* mMap; + char mKeyData[MaxKeyLength + 1]; + }; + + ~StrTreeMap(); + + void allocBuffer(s32 node_max, Heap* heap, s32 alignment = sizeof(void*)); + void setBuffer(s32 node_max, void* buffer); + void freeBuffer(); + + Value* insert(const SafeString& key, const Value& value); + void clear(); + + Node* find(const SafeString& key) const; + + // Callable must have the signature Key&, Value& + template + void forEach(const Callable& delegate) const; + +private: + void eraseNodeForClear_(typename MapImpl::Node* node); + + FreeList mFreeList; + s32 mSize = 0; + s32 mCapacity = 0; +}; + +template +inline void StrTreeMap::Node::erase_() +{ + StrTreeMap* const map = mMap; + void* const this_ = this; + // Note: Nintendo does not call the destructor, which is dangerous... + map->mFreeList.free(this_); + --map->mSize; +} + +template +inline StrTreeMap::~StrTreeMap() +{ + void* work = mFreeList.work(); + if (!work) + return; + + clear(); + freeBuffer(); +} + +template +inline void StrTreeMap::allocBuffer(s32 node_max, Heap* heap, s32 alignment) +{ + SEAD_ASSERT(mFreeList.work() == nullptr); + if (node_max <= 0) + { + SEAD_ASSERT_MSG(false, "node_max[%d] must be larger than zero", node_max); + AllocFailAssert(heap, node_max * sizeof(Node), alignment); + } + + void* work = AllocBuffer(node_max * sizeof(Node), heap, alignment); + if (work) + setBuffer(node_max, work); +} + +template +inline void StrTreeMap::setBuffer(s32 node_max, void* buffer) +{ + mCapacity = node_max; + mFreeList.setWork(buffer, sizeof(Node), node_max); +} + +template +inline void StrTreeMap::freeBuffer() +{ + void* buffer = mFreeList.work(); + if (!buffer) + return; + + ::operator delete[](buffer); + mCapacity = 0; + mFreeList.reset(); +} + +template +inline Value* StrTreeMap::insert(const SafeString& key, const Value& value) +{ + if (mSize >= mCapacity) + { + if (Node* node = find(key)) + { + node->value() = value; + return &node->value(); + } + SEAD_ASSERT_MSG(false, "map is full."); + return nullptr; + } + + Node* node = new (mFreeList.alloc()) Node(this, key, value); + ++mSize; + MapImpl::insert(node); + return &node->value(); +} + +template +inline void StrTreeMap::clear() +{ + Delegate1, typename MapImpl::Node*> delegate( + this, &StrTreeMap::eraseNodeForClear_); + MapImpl::forEach(delegate); + mSize = 0; + MapImpl::clear(); +} + +template +inline typename StrTreeMap::Node* StrTreeMap::find(const SafeString& key) const +{ + return static_cast(MapImpl::find(key)); +} + +template +template +inline void StrTreeMap::forEach(const Callable& delegate) const +{ + MapImpl::forEach([&delegate](auto* base_node) { + auto* node = static_cast(base_node); + delegate(node->key(), node->value()); + }); +} + +template +inline void StrTreeMap::eraseNodeForClear_(typename MapImpl::Node* node) +{ + // Note: Nintendo does not call the destructor, which is dangerous... + mFreeList.free(node); +} +} // namespace sead diff --git a/lib/sead/include/container/seadTList.h b/lib/sead/include/container/seadTList.h new file mode 100644 index 00000000..eabe3722 --- /dev/null +++ b/lib/sead/include/container/seadTList.h @@ -0,0 +1,217 @@ +#ifndef SEAD_TLIST_H_ +#define SEAD_TLIST_H_ + +#include + +namespace sead +{ +template +class TListNode; + +template +class TList : public ListImpl +{ +public: + using CompareCallback = int (*)(const T*, const T*); + + TList() : ListImpl() {} + + void pushBack(TListNode* item) + { + item->erase(); + item->mList = this; + ListImpl::pushBack(item); + } + + void pushFront(TListNode* item) + { + item->erase(); + item->mList = this; + ListImpl::pushFront(item); + } + + TListNode* popBack() { return static_cast*>(ListImpl::popBack()); } + TListNode* popFront() { return static_cast*>(ListImpl::popFront()); } + + void insertBefore(TListNode* node, TListNode* node_to_insert) + { + ListImpl::insertBefore(node, node_to_insert); + } + + void insertAfter(TListNode* node, TListNode* node_to_insert) + { + ListImpl::insertAfter(node, node_to_insert); + } + + void erase(TListNode* item) + { + if (!item->mList) + return; + item->mList = nullptr; + ListImpl::erase(item); + } + + TListNode* front() const { return static_cast*>(ListImpl::front()); } + TListNode* back() const { return static_cast*>(ListImpl::back()); } + TListNode* nth(int n) const { return static_cast*>(ListImpl::nth(n)); } + s32 indexOf(const TListNode* node) const { return ListImpl::indexOf(node); } + + void swap(TListNode* n1, TListNode* n2) { ListImpl::swap(n1, n2); } + void moveAfter(TListNode* basis, TListNode* n) { ListImpl::moveAfter(basis, n); } + void moveBefore(TListNode* basis, TListNode* n) { ListImpl::moveBefore(basis, n); } + + void sort(s32 offset, CompareCallback cmp) { ListImpl::sort(offset, cmp); } + void mergeSort(s32 offset, CompareCallback cmp) { ListImpl::mergeSort(offset, cmp); } + + TListNode* find(const void* ptr, s32 offset, CompareCallback cmp) const + { + return static_cast*>(ListImpl::find(ptr, offset, cmp)); + } + void uniq(s32 offset, CompareCallback cmp) { ListImpl::uniq(offset, cmp); } + void clear() { ListImpl::clear(); } + + TListNode* prev(const TListNode* node) const + { + auto prev_node = static_cast*>(node->prev()); + if (prev_node == &mStartEnd) + return nullptr; + return prev_node; + } + + TListNode* next(const TListNode* node) const + { + auto next_node = static_cast*>(node->next()); + if (next_node == &mStartEnd) + return nullptr; + return next_node; + } + + class iterator + { + public: + iterator(TListNode* ptr) : mPtr(ptr) {} + + iterator& operator++() + { + mPtr = static_cast*>(mPtr->next()); + return *this; + } + + iterator& operator--() + { + mPtr = static_cast*>(mPtr->prev()); + return *this; + } + + T& operator*() const { return mPtr->mData; } + T* operator->() const { return &mPtr->mData; } + + friend bool operator==(iterator it1, iterator it2) { return it1.mPtr == it2.mPtr; } + friend bool operator!=(iterator it1, iterator it2) { return !(it1 == it2); } + + private: + TListNode* mPtr; + }; + + iterator begin() const { return iterator(static_cast*>(mStartEnd.next())); } + + iterator end() const + { + return iterator(static_cast*>(const_cast(&mStartEnd))); + } + + /// An iterator that is safe to use even if the list is mutated during iteration. + /// Unlike the regular iterator class, this exposes ListNode rather than T + /// to make it easier to modify the list. + class robustIterator + { + public: + explicit robustIterator(TListNode* ptr) : mPtr(ptr) + { + mPtrNext = static_cast*>(mPtr->next()); + } + + robustIterator& operator++() + { + mPtr = mPtrNext; + mPtrNext = static_cast*>(mPtrNext->next()); + return *this; + } + + robustIterator operator++(int) + { + robustIterator copy = *this; + mPtr = mPtrNext; + mPtrNext = static_cast*>(mPtr->next()); + return copy; + } + + TListNode& operator*() const { return *mPtr; } + TListNode* operator->() const { return mPtr; } + + friend bool operator==(robustIterator it1, robustIterator it2) + { + return it1.mPtr == it2.mPtr; + } + friend bool operator!=(robustIterator it1, robustIterator it2) { return !(it1 == it2); } + + private: + TListNode* mPtr; + TListNode* mPtrNext; + }; + + robustIterator robustBegin() const + { + return robustIterator(static_cast*>(mStartEnd.next())); + } + + robustIterator robustEnd() const + { + return robustIterator(static_cast*>(const_cast(&mStartEnd))); + } + + struct RobustRange + { + auto begin() const { return mList.robustBegin(); } + auto end() const { return mList.robustEnd(); } + const TList& mList; + }; + RobustRange robustRange() const { return {*this}; } + +private: + static int compareT(const T* a, const T* b) + { + if (*a < *b) + return -1; + if (*a > *b) + return 1; + return 0; + } +}; + +template +class TListNode : public ListNode +{ +public: + TListNode() : ListNode() + { + mData = nullptr; + mList = NULL; + } + + TListNode(T data) : ListNode(), mData(data), mList(nullptr) {} + + void erase() + { + TList* list = mList; + if (list != NULL) + list->erase(this); + } + + T mData; + TList* mList; +}; + +} // namespace sead + +#endif // SEAD_TLIST_H_ diff --git a/lib/sead/include/container/seadTreeMap.h b/lib/sead/include/container/seadTreeMap.h new file mode 100644 index 00000000..c6d7c774 --- /dev/null +++ b/lib/sead/include/container/seadTreeMap.h @@ -0,0 +1,584 @@ +#pragma once + +#include "basis/seadRawPrint.h" +#include "container/seadFreeList.h" +#include "prim/seadBitUtil.h" +#include "prim/seadDelegate.h" +#include "prim/seadSafeString.h" + +namespace sead +{ +template +class TreeMapNode; + +/// Sorted associative container, implemented using a left-leaning red-black tree. +/// For an explanation of the algorithm, see https://www.cs.princeton.edu/~rs/talks/LLRB/LLRB.pdf +template +class TreeMapImpl +{ +public: + using Node = TreeMapNode; + + void insert(Node* node); + void erase(const Key& key); + void clear(); + + Node* find(const Key& key) const { return find(mRoot, key); } + + template + void forEach(const Callable& callable) const + { + if (mRoot) + forEach(mRoot, callable); + } + + Node* startIterating() const + { + if (!mRoot) + return nullptr; + return startIterating(mRoot); + } + + Node* nextNode(Node* node) const + { + if (!node) + return nullptr; + + // If there is a right child node, explore that branch first. + if (node->mRight) + { + node->mRight->setParent(node); + return startIterating(node->mRight); + } + + // Otherwise, walk back up to the node P from which we reached this node + // by following P's left child pointer. + while (auto* const parent = node->getParent()) + { + if (parent->mLeft == node) + return parent; + node = parent; + } + return nullptr; + } + +protected: + /// Returns the left most child of a given node, marking each node with its parent + /// along the way. + static Node* startIterating(Node* node) + { + while (node->mLeft) + { + node->mLeft->setParent(node); + node = node->mLeft; + } + return node; + } + + Node* insert(Node* root, Node* node); + Node* erase(Node* root, const Key& key); + Node* find(Node* root, const Key& key) const; + + static inline Node* rotateLeft(Node* node); + static inline Node* rotateRight(Node* node); + static inline Node* moveRedLeft(Node* node); + static inline Node* moveRedRight(Node* node); + static Node* findMin(Node* node); + static Node* eraseMin(Node* node); + static inline Node* fixUp(Node* node); + static bool isRed(const Node* node) { return node && node->isRed(); } + static inline void flipColors(Node* node); + + template + static void forEach(Node* start, const Callable& callable); + + Node* mRoot = nullptr; +}; + +/// Requires Key to have a compare() member function, which returns -1 if lhs < rhs, 0 if lhs = rhs +/// and 1 if lhs > rhs. +template +class TreeMapNode +{ +public: + TreeMapNode() + { + mLeft = mRight = nullptr; + mColorAndPtr = 0; + } + + virtual ~TreeMapNode() = default; + virtual void erase_() = 0; + + const Key& key() const { return mKey; } + +protected: + friend class TreeMapImpl; + + enum class Color + { + Red = 0, + Black = 1, + }; + + void flipColor() { BitUtil::bitCastWrite(mColorAndPtr ^ 1u, &mColorAndPtr); } + void setColor(Color color) { mColorAndPtr = uintptr_t(color); } + + void setParent(TreeMapNode* parent) { mColorAndPtr = (mColorAndPtr & 1) | uintptr_t(parent); } + /// @warning Only valid if setParent has been called! + TreeMapNode* getParent() const { return reinterpret_cast(mColorAndPtr & ~1); } + + bool isRed() const { return (mColorAndPtr & 1u) == bool(Color::Red); } + + TreeMapNode* mLeft; + TreeMapNode* mRight; + uintptr_t mColorAndPtr; + Key mKey; +}; + +/// Requires Key to have operator< defined +/// This can be specialized, but all specializations must define `compare` and `key` as follows. +template +struct TreeMapKeyImpl +{ + TreeMapKeyImpl() = default; + TreeMapKeyImpl(const Key& key_) : key(key_) {} + TreeMapKeyImpl& operator=(const Key& key_) + { + key = key_; + return *this; + } + + /// Returns -1 if mKey < rhs, 0 if mKey = rhs and 1 if mKey > rhs. + s32 compare(const TreeMapKeyImpl& rhs) const + { + if (key < rhs.key) + return -1; + if (rhs.key < key) + return 1; + return 0; + } + + Key key; +}; + +/// Sorted associative container. +/// This is essentially std::map +template +class TreeMap : public TreeMapImpl> +{ +public: + using MapImpl = TreeMapImpl>; + class Node : public MapImpl::Node + { + public: + Node(TreeMap* map, const Key& key, const Value& value) : mValue(value), mMap(map) + { + this->mKey = key; + } + + void erase_() override; + + Value& value() { return mValue; } + const Value& value() const { return mValue; } + + private: + friend class TreeMap; + + Value mValue; + TreeMap* mMap; + }; + + ~TreeMap(); + + void allocBuffer(s32 node_max, Heap* heap, s32 alignment = sizeof(void*)); + void setBuffer(s32 node_max, void* buffer); + void freeBuffer(); + + Value* insert(const Key& key, const Value& value); + void clear(); + + Node* find(const Key& key) const; + + // Callable must have the signature Key&, Value& + template + void forEach(const Callable& delegate) const; + + Node* startIterating() const { return static_cast(MapImpl::startIterating()); } + Node* nextNode(Node* node) const { return static_cast(MapImpl::nextNode(node)); } + +private: + void eraseNodeForClear_(typename MapImpl::Node* node); + + FreeList mFreeList; + s32 mSize = 0; + s32 mCapacity = 0; +}; + +template +class IntrusiveTreeMap : public TreeMapImpl +{ +public: + using MapImpl = TreeMapImpl; + + Node* find(const Key& key) const { return static_cast(MapImpl::find(key)); } + + // Callable must have the signature Node* + template + void forEach(const Callable& delegate) const + { + MapImpl::forEach([delegate](auto* base_node) { + auto* node = static_cast(base_node); + delegate(node); + }); + } + + Node* startIterating() const { return static_cast(MapImpl::startIterating()); } + Node* nextNode(Node* node) const { return static_cast(MapImpl::nextNode(node)); } +}; + +template +inline void TreeMapImpl::insert(Node* node) +{ + mRoot = insert(mRoot, node); + mRoot->setColor(Node::Color::Black); +} + +template +inline TreeMapNode* TreeMapImpl::insert(Node* root, Node* node) +{ + if (!root) + { + node->mLeft = node->mRight = nullptr; + node->setColor(Node::Color::Red); + return node; + } + + const s32 cmp = node->key().compare(root->key()); + + if (cmp < 0) + { + root->mLeft = insert(root->mLeft, node); + } + else if (cmp > 0) + { + root->mRight = insert(root->mRight, node); + } + else if (root != node) + { + node->mRight = root->mRight; + node->mLeft = root->mLeft; + node->mColorAndPtr = root->mColorAndPtr; + root->erase_(); + root = node; + } + + if (isRed(root->mRight) && !isRed(root->mLeft)) + root = rotateLeft(root); + + if (isRed(root->mLeft) && isRed(root->mLeft->mLeft)) + root = rotateRight(root); + + if (isRed(root->mLeft) && isRed(root->mRight)) + flipColors(root); + + return root; +} + +template +inline void TreeMapImpl::erase(const Key& key) +{ + mRoot = erase(mRoot, key); + if (mRoot) + mRoot->setColor(Node::Color::Black); +} + +template +inline TreeMapNode* TreeMapImpl::erase(Node* root, const Key& key) +{ + if (key.compare(root->key()) < 0) + { + if (!isRed(root->mLeft) && !isRed(root->mLeft->mLeft)) + root = moveRedLeft(root); + root->mLeft = erase(root->mLeft, key); + } + else + { + if (isRed(root->mLeft)) + root = rotateRight(root); + + if (key.compare(root->key()) == 0 && !root->mRight) + { + root->erase_(); + return nullptr; + } + + if (!isRed(root->mRight) && !isRed(root->mRight->mLeft)) + root = moveRedRight(root); + + if (key.compare(root->key()) == 0) + { + Node* const min_node = findMin(root->mRight); + + Node* target = root->mRight; + if (root->mRight) + target = find(root->mRight, min_node->key()); + + target->mRight = eraseMin(root->mRight); + target->mLeft = root->mLeft; + target->mColorAndPtr = root->mColorAndPtr; + root->erase_(); + root = target; + } + else + { + root->mRight = erase(root->mRight, key); + } + } + return fixUp(root); +} + +template +inline void TreeMapImpl::clear() +{ + mRoot = nullptr; +} + +template +inline TreeMapNode* TreeMapImpl::find(Node* root, const Key& key) const +{ + Node* node = root; + while (node) + { + const s32 cmp = key.compare(node->key()); + if (cmp < 0) + node = node->mLeft; + else if (cmp > 0) + node = node->mRight; + else + return node; + } + + return nullptr; +} + +template +template +inline void TreeMapImpl::forEach(Node* start, const Callable& callable) +{ + Node* i = start; + do + { + Node* node = i; + if (i->mLeft) + forEach(i->mLeft, callable); + i = i->mRight; + callable(node); + } while (i); +} + +template +inline TreeMapNode* TreeMapImpl::rotateLeft(Node* node) +{ + TreeMapNode* j = node->mRight; + node->mRight = j->mLeft; + j->mLeft = node; + j->mColorAndPtr = node->mColorAndPtr; + node->setColor(Node::Color::Red); + return j; +} + +template +inline TreeMapNode* TreeMapImpl::rotateRight(Node* node) +{ + TreeMapNode* j = node->mLeft; + node->mLeft = j->mRight; + j->mRight = node; + j->mColorAndPtr = node->mColorAndPtr; + node->setColor(Node::Color::Red); + return j; +} + +// NON_MATCHING: this version matches the LLRB tree implementation and is better optimized; +// there is a useless store to node->mRight in the original version +template +inline TreeMapNode* TreeMapImpl::moveRedLeft(Node* node) +{ + flipColors(node); + if (isRed(node->mRight->mLeft)) + { + node->mRight = rotateRight(node->mRight); + node = rotateLeft(node); + flipColors(node); + } + return node; +} + +template +inline TreeMapNode* TreeMapImpl::moveRedRight(Node* node) +{ + flipColors(node); + if (isRed(node->mLeft->mLeft)) + { + node = rotateRight(node); + flipColors(node); + } + return node; +} + +template +inline TreeMapNode* TreeMapImpl::findMin(Node* node) +{ + while (node->mLeft) + node = node->mLeft; + return node; +} + +// NON_MATCHING: this version matches the LLRB tree implementation and is better optimized +template +inline TreeMapNode* TreeMapImpl::eraseMin(Node* node) +{ + if (!node->mLeft) + return nullptr; + + if (!isRed(node->mLeft) && !isRed(node->mLeft->mLeft)) + node = moveRedLeft(node); + + node->mLeft = eraseMin(node->mLeft); +#ifdef MATCHING_HACK_NX_CLANG + asm(""); +#endif + return fixUp(node); +} + +template +inline TreeMapNode* TreeMapImpl::fixUp(Node* node) +{ + if (isRed(node->mRight)) + node = rotateLeft(node); + + if (isRed(node->mLeft) && isRed(node->mLeft->mLeft)) + node = rotateRight(node); + + if (isRed(node->mLeft) && isRed(node->mRight)) + flipColors(node); + + return node; +} + +template +inline void TreeMapImpl::flipColors(Node* node) +{ + node->flipColor(); + node->mLeft->flipColor(); + node->mRight->flipColor(); +} + +template +inline void TreeMap::Node::erase_() +{ + TreeMap* const map = mMap; + void* const this_ = this; + // Note: Nintendo does not call the destructor, which is dangerous... + map->mFreeList.free(this_); + --map->mSize; +} + +template +inline TreeMap::~TreeMap() +{ + void* work = mFreeList.work(); + if (!work) + return; + + clear(); + freeBuffer(); +} + +template +inline void TreeMap::allocBuffer(s32 node_max, Heap* heap, s32 alignment) +{ + SEAD_ASSERT(mFreeList.work() == nullptr); + if (node_max <= 0) + { + SEAD_ASSERT_MSG(false, "node_max[%d] must be larger than zero", node_max); + AllocFailAssert(heap, node_max * sizeof(Node), alignment); + } + + void* work = AllocBuffer(node_max * sizeof(Node), heap, alignment); + if (work) + setBuffer(node_max, work); +} + +template +inline void TreeMap::setBuffer(s32 node_max, void* buffer) +{ + mCapacity = node_max; + mFreeList.setWork(buffer, sizeof(Node), node_max); +} + +template +inline void TreeMap::freeBuffer() +{ + void* buffer = mFreeList.work(); + if (!buffer) + return; + + ::operator delete[](buffer); + mCapacity = 0; + mFreeList.reset(); +} + +template +inline Value* TreeMap::insert(const Key& key, const Value& value) +{ + if (mSize >= mCapacity) + { + if (Node* node = find(key)) + { + node->value() = value; + return &node->value(); + } + SEAD_ASSERT_MSG(false, "map is full."); + return nullptr; + } + + Node* node = new (mFreeList.alloc()) Node(this, key, value); + ++mSize; + MapImpl::insert(node); + return &node->value(); +} + +template +inline void TreeMap::clear() +{ + Delegate1, typename MapImpl::Node*> delegate(this, + &TreeMap::eraseNodeForClear_); + MapImpl::forEach(delegate); + mSize = 0; + MapImpl::clear(); +} + +template +inline typename TreeMap::Node* TreeMap::find(const Key& key) const +{ + return static_cast(MapImpl::find(key)); +} + +template +template +inline void TreeMap::forEach(const Callable& delegate) const +{ + MapImpl::forEach([&delegate](auto* base_node) { + auto* node = static_cast(base_node); + delegate(node->key(), node->value()); + }); +} + +template +inline void TreeMap::eraseNodeForClear_(typename MapImpl::Node* node) +{ + // Note: Nintendo does not call the destructor, which is dangerous... + mFreeList.free(node); +} +} // namespace sead diff --git a/lib/sead/include/container/seadTreeNode.h b/lib/sead/include/container/seadTreeNode.h new file mode 100644 index 00000000..1233dcf4 --- /dev/null +++ b/lib/sead/include/container/seadTreeNode.h @@ -0,0 +1,64 @@ +#ifndef SEAD_TREENODE_H_ +#define SEAD_TREENODE_H_ + +#include + +namespace sead +{ +class TreeNode +{ +public: + TreeNode(); + + void clearLinks(); + s32 countChildren() const; + void detachAll(); + void detachSubTree(); + TreeNode* findRoot(); + const TreeNode* findRoot() const; + void insertAfterSelf(TreeNode* node); + void insertBeforeSelf(TreeNode* node); + void pushBackChild(TreeNode* node); + void pushBackSibling(TreeNode* node); + void pushFrontChild(TreeNode* node); + +protected: + void clearChildLinksRecursively_(); + + TreeNode* mParent; + TreeNode* mChild; + TreeNode* mNext; + TreeNode* mPrev; +}; + +template +class TTreeNode : public TreeNode +{ +public: + TTreeNode() = default; + explicit TTreeNode(T data) : mData(data) {} + + T& value() { return mData; } + const T& value() const { return mData; } + + TTreeNode* parent() const { return static_cast(mParent); } + TTreeNode* child() const { return static_cast(mChild); } + TTreeNode* next() const { return static_cast(mNext); } + TTreeNode* prev() const { return static_cast(mPrev); } + TTreeNode* findRoot() { return static_cast(TreeNode::findRoot()); } + const TTreeNode* findRoot() const { return static_cast(TreeNode::findRoot()); } + void insertAfterSelf(TTreeNode* node) { TreeNode::insertAfterSelf(node); } + void insertBeforeSelf(TTreeNode* node) { TreeNode::insertBeforeSelf(node); } + void pushBackChild(TTreeNode* node) { TreeNode::pushBackChild(node); } + void pushBackSibling(TTreeNode* node) { TreeNode::pushBackSibling(node); } + void pushFrontChild(TTreeNode* node) { TreeNode::pushFrontChild(node); } + + // TODO: probably iterators + +protected: + T mData; +}; + +} // namespace sead + +#endif // SEAD_TREENODE_H_ diff --git a/lib/sead/include/controller/seadController.h b/lib/sead/include/controller/seadController.h new file mode 100644 index 00000000..6247bacd --- /dev/null +++ b/lib/sead/include/controller/seadController.h @@ -0,0 +1,50 @@ +#pragma once + +#include "container/seadOffsetList.h" +#include "controller/seadControllerBase.h" + +namespace sead +{ +class ControllerMgr; +class ControllerAddon; + +namespace ControllerDefine +{ +enum AddonId : int +{ +}; +enum ControllerId : int +{ + _15 = 15, + _16 = 16 +}; +enum DeviceId : int +{ +}; + +} // namespace ControllerDefine + +class Controller : public ControllerBase +{ + SEAD_RTTI_OVERRIDE(Controller, ControllerBase) +public: + Controller(ControllerMgr*); + virtual ~Controller(); + virtual void calc(); + virtual bool isConnected(); + ControllerAddon* getAddonByOrder(ControllerDefine::AddonId, int); + ControllerAddon* getAddon(ControllerDefine::AddonId); + +protected: + virtual void calcImpl_() = 0; + virtual bool isIdle_(); + virtual void setIdle_(); + +private: + int mControllerId; + ControllerMgr* mMgr; + OffsetList mAddonList; + OffsetList _160; // unknown type +}; + +} // namespace sead diff --git a/lib/sead/include/controller/seadControllerBase.h b/lib/sead/include/controller/seadControllerBase.h new file mode 100644 index 00000000..9d78f9d6 --- /dev/null +++ b/lib/sead/include/controller/seadControllerBase.h @@ -0,0 +1,68 @@ +#pragma once + +#include "math/seadBoundBox.h" +#include "math/seadVector.h" +#include "prim/seadBitFlag.h" +#include "prim/seadRuntimeTypeInfo.h" + +namespace sead +{ +class ControllerBase +{ + SEAD_RTTI_BASE(ControllerBase) +public: + ControllerBase(int, int, int, int); + + void setRightStickCrossThreshold(float, float); + void setPointerBound(const BoundBox2f& bound); + void setPadRepeat(u32, u8, u8); + void setLeftStickCrossThreshold(float, float); + // unknown return type + u32 getPadHoldCount(int) const; + + BitFlag32 getButtonsTrigger() const { return mButtonsTrigger; } + BitFlag32 getButtonsRelease() const { return mButtonsRelease; } + BitFlag32 getButtonsRepeat() const { return mButtonsRepeat; } + BitFlag32 getButtonsHold() const { return mButtonsHold; } + const Vector2f& getTouchScreenPos() const { return mTouchScreenPos; } + const Vector2f& getLeftJoy() const { return mLeftJoy; } + const Vector2f& getRightJoy() const { return mRightJoy; } + +protected: + void updateDerivativeParams_(u32, bool); + void setPointerWithBound_(bool, bool, const Vector2f& bound); + void setIdleBase_(); + bool isIdleBase_(); + // unknown return type + u32 getStickHold_(u32, const Vector2f&, float, float, int); + // unknown return type + u32 createStickCrossMask_(); + +private: + BitFlag32 mButtonsTrigger; + BitFlag32 mButtonsRelease; + BitFlag32 mButtonsRepeat; + unsigned int mFlags; + int _18; + int _1c; + BoundBox2f mPointerBound; + int mPadHoldCounts[32]; + char _b0[32]; + char _d0[32]; + float mLeftStickThresholdX; + float mRightStickThresholdX; + float mLeftStickThresholdY; + float mRightStickThresholdY; + int _100; + int _104; + int _108; + int _10c; + unsigned int mIdleCounter; + sead::BitFlag32 mButtonsHold; + Vector2f mTouchScreenPos; + Vector2f mLeftJoy; + Vector2f mRightJoy; + Vector2f _130; +}; + +} // namespace sead diff --git a/lib/sead/include/controller/seadControllerMgr.h b/lib/sead/include/controller/seadControllerMgr.h new file mode 100644 index 00000000..c7108f57 --- /dev/null +++ b/lib/sead/include/controller/seadControllerMgr.h @@ -0,0 +1,45 @@ +#pragma once + +#include "container/seadOffsetList.h" +#include "container/seadPtrArray.h" +#include "controller/seadController.h" +#include "framework/seadCalculateTask.h" +#include "framework/seadTaskMgr.h" +#include "heap/seadDisposer.h" + +namespace sead +{ +class Controller; +class NinJoyNpadDevice; + +class ControllerMgr : public CalculateTask +{ + SEAD_TASK_SINGLETON(ControllerMgr) +public: + explicit ControllerMgr(const TaskConstructArg& arg); + ControllerMgr(); + + void calc() override; + void finalize(); + void finalizeDefault(); + int findControllerPort(const Controller* controller); + NinJoyNpadDevice* getControlDevice(ControllerDefine::DeviceId device_id); + // unknown return type + void* getControllerAddon(int, ControllerDefine::AddonId addon_id); + // unknown return type + void* getControllerAddonByOrder(int, ControllerDefine::AddonId addon_id, int); + Controller* getControllerByOrder(ControllerDefine::ControllerId controller_id, int); + // unknown return type, probably inherited from TaskBase + void* getFramework(); + void initialize(int, Heap* heap); + void initializeDefault(Heap* heap); + void prepare() override; + + Controller* getController(int port) { return mArray[port]; } + +private: + OffsetList mList; + PtrArray mArray; +}; + +} // namespace sead diff --git a/lib/sead/include/devenv/seadAssertConfig.h b/lib/sead/include/devenv/seadAssertConfig.h new file mode 100644 index 00000000..257e8682 --- /dev/null +++ b/lib/sead/include/devenv/seadAssertConfig.h @@ -0,0 +1,22 @@ +#pragma once + +#include "prim/seadDelegate.h" +#include "prim/seadDelegateEventSlot.h" + +namespace sead +{ +class AssertConfig +{ +public: + using AssertEvent = DelegateEvent; + + static void registerCallback(AssertEvent::Slot& slot); + static void unregisterCallback(AssertEvent::Slot& slot); + static void registerFinalCallback(IDelegate1* cb); + static void execCallbacks(const char* assertMessage); + +private: + static AssertEvent sAssertEvent; + static IDelegate1* sFinalCallback; +}; +} // namespace sead diff --git a/lib/sead/include/devenv/seadEnvUtil.h b/lib/sead/include/devenv/seadEnvUtil.h new file mode 100644 index 00000000..2e7a9d91 --- /dev/null +++ b/lib/sead/include/devenv/seadEnvUtil.h @@ -0,0 +1,18 @@ +#pragma once + +#include "prim/seadEnum.h" +#include "prim/seadSafeString.h" + +namespace sead +{ +SEAD_ENUM(RegionLanguageID, JPja, USen, USes, USfr, USpt, EUen, EUes, EUfr, EUde, EUit, EUpt, EUnl, EUru, KRko, CNzh, TWzh) + +class EnvUtil +{ +public: + static const SafeString& getRomType(); + static RegionLanguageID getRegionLanguage(); + static s32 getEnvironmentVariable(BufferedSafeString* out, const SafeString& variable); + static s32 resolveEnvronmentVariable(BufferedSafeString* out, const SafeString& str); +}; +} // namespace sead diff --git a/lib/sead/include/devenv/seadGameConfig.h b/lib/sead/include/devenv/seadGameConfig.h new file mode 100644 index 00000000..78b0b247 --- /dev/null +++ b/lib/sead/include/devenv/seadGameConfig.h @@ -0,0 +1,24 @@ +#pragma once + +#include "heap/seadDisposer.h" +#include "hostio/seadHostIONode.h" +#include "prim/seadSafeString.h" + +namespace sead +{ +class GameConfig : public hostio::Node +{ + SEAD_SINGLETON_DISPOSER(GameConfig) + GameConfig(); + virtual ~GameConfig(); + + static const SafeString cNodeName; + +protected: + struct FileWriteCallback + { + virtual ~FileWriteCallback(); + virtual void save(); + }; +}; +} // namespace sead diff --git a/lib/sead/include/devenv/seadStackTrace.h b/lib/sead/include/devenv/seadStackTrace.h new file mode 100644 index 00000000..35d88c7e --- /dev/null +++ b/lib/sead/include/devenv/seadStackTrace.h @@ -0,0 +1,55 @@ +#pragma once + +#include "basis/seadTypes.h" +#include "container/seadSafeArray.h" + +namespace sead +{ +class StackTraceBase +{ +public: + StackTraceBase(); + virtual ~StackTraceBase() = default; + + virtual uintptr_t get(s32 index) const = 0; + virtual s32 size() const = 0; + + void trace(const void*); + +protected: + virtual void clear_() = 0; + virtual void push_(uintptr_t addr) = 0; + virtual bool isFull_() = 0; +}; + +template +class StackTrace : public StackTraceBase +{ +public: + ~StackTrace() override = default; + + uintptr_t get(s32 index) const override + { + if (index >= mSize) + return 0; + return mBuffer[index]; + } + + s32 size() const override { return mSize; } + +protected: + void clear_() override { mSize = 0; } + + void push_(uintptr_t addr) override + { + mBuffer[mSize] = addr; + ++mSize; + } + + bool isFull_() override { return mSize >= mBuffer.size(); } + +private: + SafeArray mBuffer{}; + s32 mSize{}; +}; +} // namespace sead diff --git a/lib/sead/include/filedevice/cafe/seadCafeFSAFileDeviceCafe.h b/lib/sead/include/filedevice/cafe/seadCafeFSAFileDeviceCafe.h new file mode 100644 index 00000000..13f8f356 --- /dev/null +++ b/lib/sead/include/filedevice/cafe/seadCafeFSAFileDeviceCafe.h @@ -0,0 +1,65 @@ +#ifndef SEAD_CAFE_FSA_FILEDEVICE_H_ +#define SEAD_CAFE_FSA_FILEDEVICE_H_ + +#include + +#include +#include +#include +#include + +namespace sead +{ +class CafeFSAFileDevice : public FileDevice +{ + SEAD_RTTI_OVERRIDE(CafeFSAFileDevice, FileDevice) + +public: + CafeFSAFileDevice(const SafeString& name, const SafeString& devicePath); + virtual ~CafeFSAFileDevice() {} + + virtual bool doIsAvailable_() const; + virtual FileDevice* doOpen_(FileHandle* handle, const SafeString& path, FileOpenFlag flag); + virtual bool doClose_(FileHandle* handle); + virtual bool doRead_(u32* bytesRead, FileHandle* handle, u8* outBuffer, u32 bytesToRead); + virtual bool doWrite_(u32* bytesWritten, FileHandle* handle, const u8* inBuffer, + u32 bytesToWrite); + virtual bool doSeek_(FileHandle* handle, s32 offset, SeekOrigin origin); + virtual bool doGetCurrentSeekPos_(u32* seekPos, FileHandle* handle); + virtual bool doGetFileSize_(u32* fileSize, const SafeString& path); + virtual bool doGetFileSize_(u32* fileSize, FileHandle* handle); + virtual bool doIsExistFile_(bool* exists, const SafeString& path); + virtual bool doIsExistDirectory_(bool* exists, const SafeString& path); + virtual FileDevice* doOpenDirectory_(DirectoryHandle* handle, const SafeString& path); + virtual bool doCloseDirectory_(DirectoryHandle* handle); + virtual bool doReadDirectory_(u32* entriesRead, DirectoryHandle* handle, + DirectoryEntry* entries, u32 entriesToRead); + virtual bool doMakeDirectory_(const SafeString& path, u32); + virtual s32 doGetLastRawError_() const; + virtual void doResolvePath_(BufferedSafeString* out, const SafeString& path) const; + virtual void formatPathForFSA_(BufferedSafeString* out, const SafeString& path) const; + + FSClient* getUsableFSClient_() const; + FSFileHandle* getFileHandleInner_(FileHandle* handle); + FSDirHandle* getDirHandleInner_(DirectoryHandle* handle); + + const char* devicePath; + FSStatus status; + FSRetFlag openErrHandling; + FSRetFlag closeErrHandling; + FSRetFlag readErrHandling; + FSClient* client; +}; + +class CafeContentFileDevice : public CafeFSAFileDevice +{ + SEAD_RTTI_OVERRIDE(CafeContentFileDevice, CafeFSAFileDevice) + +public: + CafeContentFileDevice(); + virtual ~CafeContentFileDevice() {} +}; + +} // namespace sead + +#endif // SEAD_CAFE_FSA_FILEDEVICE_H_ diff --git a/lib/sead/include/filedevice/nin/seadNinAocFileDeviceNin.h b/lib/sead/include/filedevice/nin/seadNinAocFileDeviceNin.h new file mode 100644 index 00000000..85da7082 --- /dev/null +++ b/lib/sead/include/filedevice/nin/seadNinAocFileDeviceNin.h @@ -0,0 +1,14 @@ +#pragma once + +#include "filedevice/nin/seadNinFileDeviceBaseNin.h" + +namespace sead +{ +class NinAocFileDevice : public NinFileDeviceBase +{ + SEAD_RTTI_OVERRIDE(NinAocFileDevice, NinFileDeviceBase) + +public: + explicit NinAocFileDevice(const SafeString& mount); +}; +} // namespace sead diff --git a/lib/sead/include/filedevice/nin/seadNinContentFileDeviceNin.h b/lib/sead/include/filedevice/nin/seadNinContentFileDeviceNin.h new file mode 100644 index 00000000..1f4c7e34 --- /dev/null +++ b/lib/sead/include/filedevice/nin/seadNinContentFileDeviceNin.h @@ -0,0 +1,14 @@ +#pragma once + +#include "filedevice/nin/seadNinFileDeviceBaseNin.h" + +namespace sead +{ +class NinContentFileDevice : public NinFileDeviceBase +{ + SEAD_RTTI_OVERRIDE(NinContentFileDevice, NinFileDeviceBase) + +public: + NinContentFileDevice(); +}; +} // namespace sead diff --git a/lib/sead/include/filedevice/nin/seadNinFileDeviceBaseNin.h b/lib/sead/include/filedevice/nin/seadNinFileDeviceBaseNin.h new file mode 100644 index 00000000..80650f46 --- /dev/null +++ b/lib/sead/include/filedevice/nin/seadNinFileDeviceBaseNin.h @@ -0,0 +1,51 @@ +#pragma once + +#include +#include "filedevice/seadFileDevice.h" +#include "prim/seadSafeString.h" + +namespace sead +{ +class NinFileDeviceBase : public FileDevice +{ + SEAD_RTTI_OVERRIDE(NinFileDeviceBase, FileDevice) + +public: + NinFileDeviceBase(const SafeString& name, const SafeString& mount_point); + +protected: + struct FileHandleInner; + struct DirectoryHandleInner; + + bool doIsAvailable_() const override; + FileDevice* doOpen_(FileHandle* handle, const SafeString& path, FileOpenFlag flag) override; + bool doClose_(FileHandle* handle) override; + bool doFlush_(FileHandle* handle) override; + bool doRemove_(const SafeString& path) override; + bool doRead_(u32* bytesRead, FileHandle* handle, u8* outBuffer, u32 bytesToRead) override; + bool doWrite_(u32* bytesWritten, FileHandle* handle, const u8* inBuffer, + u32 bytesToWrite) override; + bool doSeek_(FileHandle* handle, s32 offset, SeekOrigin origin) override; + bool doGetCurrentSeekPos_(u32* seekPos, FileHandle* handle) override; + bool doGetFileSize_(u32* fileSize, const SafeString& path) override; + bool doGetFileSize_(u32* fileSize, FileHandle* handle) override; + bool doIsExistFile_(bool* exists, const SafeString& path) override; + bool doIsExistDirectory_(bool* exists, const SafeString& path) override; + FileDevice* doOpenDirectory_(DirectoryHandle* handle, const SafeString& path) override; + bool doCloseDirectory_(DirectoryHandle* handle) override; + bool doReadDirectory_(u32* entriesRead, DirectoryHandle* handle, DirectoryEntry* entries, + u32 entriesToRead) override; + bool doMakeDirectory_(const SafeString& path, u32 u_32) override; + s32 doGetLastRawError_() const override; + void doResolvePath_(BufferedSafeString* out, const SafeString& path) const override; + + virtual bool formatPathForFS_(BufferedSafeString* out, const SafeString& path) const; + + FileHandleInner* getFileHandleInner_(HandleBase* handle, bool construct = false) const; + DirectoryHandleInner* getDirectoryHandleInner_(HandleBase* handle, + bool construct = false) const; + + nn::Result mLastError = nn::ResultSuccess{}; + SafeString mMountPoint; +}; +} // namespace sead diff --git a/lib/sead/include/filedevice/nin/seadNinHostIOFileDevice.h b/lib/sead/include/filedevice/nin/seadNinHostIOFileDevice.h new file mode 100644 index 00000000..baca488d --- /dev/null +++ b/lib/sead/include/filedevice/nin/seadNinHostIOFileDevice.h @@ -0,0 +1,17 @@ +#pragma once + +#include "filedevice/nin/seadNinFileDeviceBaseNin.h" + +namespace sead +{ +class NinHostIOFileDevice : public NinFileDeviceBase +{ + SEAD_RTTI_OVERRIDE(NinHostIOFileDevice, NinFileDeviceBase) + +public: + NinHostIOFileDevice(); + + bool doIsAvailable_() const override; + bool formatPathForFS_(BufferedSafeString* out, const SafeString& path) const override; +}; +} // namespace sead diff --git a/lib/sead/include/filedevice/nin/seadNinSDFileDeviceNin.h b/lib/sead/include/filedevice/nin/seadNinSDFileDeviceNin.h new file mode 100644 index 00000000..7362ccde --- /dev/null +++ b/lib/sead/include/filedevice/nin/seadNinSDFileDeviceNin.h @@ -0,0 +1,16 @@ +#pragma once + +#include "filedevice/nin/seadNinFileDeviceBaseNin.h" + +namespace sead +{ +class NinSDFileDevice : public NinFileDeviceBase +{ + SEAD_RTTI_OVERRIDE(NinSDFileDevice, NinFileDeviceBase) + +public: + NinSDFileDevice(); + + bool doIsAvailable_() const override; +}; +} // namespace sead diff --git a/lib/sead/include/filedevice/nin/seadNinSaveFileDeviceNin.h b/lib/sead/include/filedevice/nin/seadNinSaveFileDeviceNin.h new file mode 100644 index 00000000..e36daac6 --- /dev/null +++ b/lib/sead/include/filedevice/nin/seadNinSaveFileDeviceNin.h @@ -0,0 +1,15 @@ +#pragma once + +#include "filedevice/nin/seadNinFileDeviceBaseNin.h" + +namespace sead +{ +class NinSaveFileDevice : public NinFileDeviceBase +{ + SEAD_RTTI_OVERRIDE(NinSaveFileDevice, NinFileDeviceBase) + +public: + explicit NinSaveFileDevice(const SafeString& mount); + bool tryCommit(); +}; +} // namespace sead diff --git a/lib/sead/include/filedevice/seadArchiveFileDevice.h b/lib/sead/include/filedevice/seadArchiveFileDevice.h new file mode 100644 index 00000000..4758e33b --- /dev/null +++ b/lib/sead/include/filedevice/seadArchiveFileDevice.h @@ -0,0 +1,55 @@ +#pragma once + +#include "filedevice/seadFileDevice.h" + +namespace sead +{ +class ArchiveRes; + +class ArchiveFileDevice : public FileDevice +{ + SEAD_RTTI_OVERRIDE(ArchiveFileDevice, FileDevice) +public: + explicit ArchiveFileDevice(ArchiveRes* archive_res); + ~ArchiveFileDevice() override = default; + + u8* tryLoadWithEntryID(s32 id, LoadArg& arg); + FileDevice* tryOpenWithEntryID(FileHandle* handle, s32 id, FileOpenFlag flag, u32 div_size); + s32 tryConvertPathToEntryID(const SafeString& path); + bool setCurrentDirectory(const SafeString& dir); + +protected: + struct ArchiveFileHandle; + + bool doIsAvailable_() const override { return true; } + u8* doLoad_(LoadArg& arg) override; + FileDevice* doOpen_(FileHandle* handle, const SafeString& path, FileOpenFlag flag) override; + bool doClose_(FileHandle* handle) override; + bool doFlush_(FileHandle* handle) override; + bool doRemove_(const SafeString& str) override; + bool doRead_(u32* bytesRead, FileHandle* handle, u8* outBuffer, u32 bytesToRead) override; + bool doWrite_(u32*, FileHandle*, const u8*, u32) override { return false; } + bool doSeek_(FileHandle* handle, s32 offset, SeekOrigin origin) override; + bool doGetCurrentSeekPos_(u32* seekPos, FileHandle* handle) override; + bool doGetFileSize_(u32* fileSize, const SafeString& path) override; + bool doGetFileSize_(u32* fileSize, FileHandle* handle) override; + bool doIsExistFile_(bool* exists, const SafeString& path) override; + bool doIsExistDirectory_(bool* exists, const SafeString& path) override; + FileDevice* doOpenDirectory_(DirectoryHandle* handle, const SafeString& path) override; + bool doCloseDirectory_(DirectoryHandle* handle) override; + bool doReadDirectory_(u32* entriesRead, DirectoryHandle* handle, DirectoryEntry* entry, + u32 entriesToRead) override; + bool doMakeDirectory_(const SafeString& path, u32 u_32) override; + s32 doGetLastRawError_() const override; + + virtual u8* doLoadWithEntryID_(s32 id, LoadArg& arg); + virtual FileDevice* doOpenWithEntryID_(FileHandle* handle, s32 id, FileOpenFlag flag); + virtual s32 doConvertPathToEntryID_(const SafeString& path); + virtual bool doSetCurrentDirectory_(const SafeString& path); + + ArchiveFileHandle* getArchiveFileHandle_(FileHandle* handle) const; + ArchiveFileHandle* constructArchiveFileHandle_(FileHandle* handle) const; + + ArchiveRes* mArchive; +}; +} // namespace sead diff --git a/lib/sead/include/filedevice/seadFileDevice.h b/lib/sead/include/filedevice/seadFileDevice.h new file mode 100644 index 00000000..79d02266 --- /dev/null +++ b/lib/sead/include/filedevice/seadFileDevice.h @@ -0,0 +1,419 @@ +#ifndef SEAD_FILEDEVICE_H_ +#define SEAD_FILEDEVICE_H_ + +#include +#include +#include +#include +#include +#include +#include + +namespace sead +{ +class FileDevice; + +using HandleBuffer = SafeArray; + +class HandleBase +{ +public: + HandleBase() = default; + HandleBase(const HandleBase&) = delete; + HandleBase& operator=(const HandleBase&) = delete; + virtual ~HandleBase() = default; + + FileDevice* getDevice() const { return mDevice; } + FileDevice* getOriginalDevice() const { return mOriginalDevice; } + bool isOpened() const { return mOriginalDevice != nullptr; } + +protected: + friend class FileDevice; + + FileDevice* mDevice = nullptr; + FileDevice* mOriginalDevice = nullptr; + HandleBuffer mHandleBuffer{}; +}; + +class FileHandle; +class DirectoryHandle; +struct DirectoryEntry; + +class FileDevice : public TListNode, public IDisposer +{ + SEAD_RTTI_BASE(FileDevice) + +public: + enum FileOpenFlag + { + cFileOpenFlag_ReadOnly = 0, // r + cFileOpenFlag_WriteOnly = 1, // w + cFileOpenFlag_ReadWrite = 2, // r+ + cFileOpenFlag_Create = 3 // w+ + }; + + enum SeekOrigin + { + cSeekOrigin_Begin = 0, + cSeekOrigin_Current = 1, + cSeekOrigin_End = 2 + }; + + struct LoadArg + { + SafeString path; + u8* buffer = nullptr; + u32 buffer_size = 0; + Heap* heap = nullptr; + s32 alignment = 0; + s32 buffer_size_alignment = 0; + /// Read chunk size + u32 div_size = 0; + bool assert_on_alloc_fail = true; + bool check_read_entire_file = true; + u32 read_size = 0; + u32 roundup_size = 0; + bool need_unload = false; + }; + + struct SaveArg + { + SafeString path = ""; + const u8* buffer = nullptr; + u32 buffer_size = 0; + u32 write_size = 0; + }; + +public: + FileDevice() : TListNode(this), IDisposer(), mDriveName(), mPermission(true) {} + + explicit FileDevice(const SafeString& name) + : TListNode(this), IDisposer(), mDriveName(), mPermission(true) + { + setDriveName(name); + } + + ~FileDevice() override; + + const SafeString& getDriveName() const { return mDriveName; } + void setDriveName(const SafeString& name) + { +#ifdef SEAD_DEBUG + if (name.include(':')) + SEAD_WARN("drive name should not include ':'. (in %s)", name.cstr()); +#endif + mDriveName = name; + } + + bool hasPermission() const { return mPermission; } + void setHasPermission(bool perm) { mPermission = perm; } + + bool isAvailable() const; + + u8* tryLoad(LoadArg& arg); + + bool save(SaveArg& arg) + { + if (!trySave(arg)) + { + SEAD_ASSERT_MSG(false, "file save error"); + return false; + } + return true; + } + bool trySave(SaveArg& arg); + + FileDevice* open(FileHandle* handle, const SafeString& path, FileOpenFlag flag, u32 divSize = 0) + { + auto* device = tryOpen(handle, path, flag, divSize); + if (!device) + { + SEAD_ASSERT_MSG(false, "file open error"); + return nullptr; + } + return device; + } + FileDevice* tryOpen(FileHandle* handle, const SafeString& path, FileOpenFlag flag, + u32 divSize = 0); + + bool close(FileHandle* handle) + { + if (!tryClose(handle)) + { + SEAD_ASSERT_MSG(false, "file close error"); + return false; + } + return true; + } + bool tryClose(FileHandle* handle); + + bool flush(FileHandle* handle) + { + if (!tryFlush(handle)) + { + SEAD_ASSERT_MSG(false, "file flush error"); + return false; + } + return true; + } + bool tryFlush(FileHandle* handle); + + bool remove(const SafeString& str) + { + if (!tryRemove(str)) + { + SEAD_ASSERT_MSG(false, "file remove error"); + return false; + } + return true; + } + bool tryRemove(const SafeString& str); + + u32 read(FileHandle* handle, u8* data, u32 size) + { + u32 bytes_read = 0; + if (!tryRead(&bytes_read, handle, data, size)) + SEAD_ASSERT_MSG(false, "file read error"); + return bytes_read; + } + bool tryRead(u32* bytesRead, FileHandle* handle, u8* outBuffer, u32 bytesToRead); + + u32 write(FileHandle* handle, const u8* data, u32 size) + { + u32 bytes_written = 0; + if (!tryWrite(&bytes_written, handle, data, size)) + SEAD_ASSERT_MSG(false, "file write error"); + return bytes_written; + } + bool tryWrite(u32* bytesWritten, FileHandle* handle, const u8* inBuffer, u32 bytesToWrite); + + bool seek(FileHandle* handle, s32 offset, SeekOrigin origin) + { + if (!trySeek(handle, offset, origin)) + { + SEAD_ASSERT_MSG(false, "file seek error"); + return false; + } + return true; + } + bool trySeek(FileHandle* handle, s32 offset, SeekOrigin origin); + + u32 getCurrentSeekPos(FileHandle* handle) + { + u32 seek_pos = 0; + if (!tryGetCurrentSeekPos(&seek_pos, handle)) + SEAD_ASSERT_MSG(false, "tryGetCurrentSeekPos error"); + return seek_pos; + } + bool tryGetCurrentSeekPos(u32* seekPos, FileHandle* handle); + + u32 getFileSize(const SafeString& path) + { + u32 file_size = 0; + if (!tryGetFileSize(&file_size, path)) + SEAD_ASSERT_MSG(false, "tryGetFileSize error"); + return file_size; + } + bool tryGetFileSize(u32* fileSize, const SafeString& path); + + u32 getFileSize(FileHandle* handle) + { + u32 file_size = 0; + if (!tryGetFileSize(&file_size, handle)) + SEAD_ASSERT_MSG(false, "tryGetFileSize error"); + return file_size; + } + bool tryGetFileSize(u32* size, FileHandle* handle); + + bool isExistFile(const SafeString& path) + { + bool exists = false; + if (!tryIsExistFile(&exists, path)) + SEAD_ASSERT_MSG(false, "tryIsExistFile error"); + return exists; + } + bool tryIsExistFile(bool* exists, const SafeString& path); + + bool isExistDirectory(const SafeString& path) + { + bool exists = false; + if (!tryIsExistDirectory(&exists, path)) + SEAD_ASSERT_MSG(false, "isExistDirectory failed"); + return exists; + } + bool tryIsExistDirectory(bool* exists, const SafeString& path); + + FileDevice* openDirectory(DirectoryHandle* handle, const SafeString& path) + { + auto* device = tryOpenDirectory(handle, path); + if (!device) + { + SEAD_ASSERT_MSG(false, "directory open error"); + return nullptr; + } + return device; + } + FileDevice* tryOpenDirectory(DirectoryHandle* handle, const SafeString& path); + + bool closeDirectory(DirectoryHandle* handle) + { + if (!tryCloseDirectory(handle)) + { + SEAD_ASSERT_MSG(false, "directory close error"); + return false; + } + return true; + } + bool tryCloseDirectory(DirectoryHandle* handle); + + u32 readDirectory(DirectoryHandle* handle, DirectoryEntry* entries, u32 num_entries) + { + u32 entries_read = 0; + if (!tryReadDirectory(&entries_read, handle, entries, num_entries)) + SEAD_ASSERT_MSG(false, "directory read error"); + return entries_read; + } + bool tryReadDirectory(u32* entriesRead, DirectoryHandle* handle, DirectoryEntry* entries, + + u32 entriesToRead); + + bool makeDirectory(const SafeString& path, u32 x) + { + if (!tryMakeDirectory(path, x)) + { + SEAD_ASSERT_MSG(false, "directory make error"); + return false; + } + return true; + } + bool tryMakeDirectory(const SafeString& path, u32); + + bool makeDirectoryWithParent(const SafeString& path, u32 x) + { + if (!tryMakeDirectoryWithParent(path, x)) + { + SEAD_ASSERT_MSG(false, "directory make with parent error"); + return false; + } + return true; + } + bool tryMakeDirectoryWithParent(const SafeString& path, u32); + + s32 getLastRawError() const; + + virtual void traceFilePath(const SafeString& path) const; + virtual void traceDirectoryPath(const SafeString& path) const; + virtual void resolveFilePath(BufferedSafeString* out, const SafeString& path) const; + virtual void resolveDirectoryPath(BufferedSafeString* out, const SafeString& path) const; + virtual bool isMatchDevice_(const HandleBase* handle) const; + +#ifdef SWITCH + static const s32 cBufferMinAlignment = 0x20; +#else + static const s32 cBufferMinAlignment = 0x40; +#endif + +protected: + virtual bool doIsAvailable_() const = 0; + virtual u8* doLoad_(LoadArg& arg); + virtual bool doSave_(SaveArg& arg); + virtual FileDevice* doOpen_(FileHandle* handle, const SafeString& path, FileOpenFlag flag) = 0; + virtual bool doClose_(FileHandle* handle) = 0; + virtual bool doFlush_(FileHandle* handle) = 0; + virtual bool doRemove_(const SafeString& str) = 0; + virtual bool doRead_(u32* bytesRead, FileHandle* handle, u8* outBuffer, u32 bytesToRead) = 0; + virtual bool doWrite_(u32* bytesWritten, FileHandle* handle, const u8* inBuffer, + u32 bytesToWrite) = 0; + virtual bool doSeek_(FileHandle* handle, s32 offset, SeekOrigin origin) = 0; + virtual bool doGetCurrentSeekPos_(u32* seekPos, FileHandle* handle) = 0; + virtual bool doGetFileSize_(u32* fileSize, const SafeString& path) = 0; + virtual bool doGetFileSize_(u32* fileSize, FileHandle* handle) = 0; + virtual bool doIsExistFile_(bool* exists, const SafeString& path) = 0; + virtual bool doIsExistDirectory_(bool* exists, const SafeString& path) = 0; + virtual FileDevice* doOpenDirectory_(DirectoryHandle* handle, const SafeString& path) = 0; + virtual bool doCloseDirectory_(DirectoryHandle* handle) = 0; + virtual bool doReadDirectory_(u32* entriesRead, DirectoryHandle* handle, + DirectoryEntry* entries, u32 entriesToRead) = 0; + virtual bool doMakeDirectory_(const SafeString& path, u32) = 0; + virtual s32 doGetLastRawError_() const = 0; + virtual void doTracePath_(const SafeString& path) const; + virtual void doResolvePath_(BufferedSafeString* out, const SafeString& path) const; + + void setFileHandleDivSize_(FileHandle* handle, u32 divSize) const; + void setHandleBaseFileDevice_(HandleBase* handle, FileDevice* device) const; + void setHandleBaseOriginalFileDevice_(HandleBase* handle, FileDevice* device) const; + HandleBuffer& getHandleBaseHandleBuffer_(HandleBase* handle) const; + + FixedSafeString<32> mDriveName; + bool mPermission; +}; + +class FileHandle : public HandleBase +{ +public: + FileHandle() : HandleBase(), mDivSize(0) {} + + virtual ~FileHandle() + { + FileDevice* _device = mOriginalDevice; + if (_device != NULL) + _device->tryClose(this); + } + + bool close(); + bool tryClose(); + + bool flush(); + bool tryFlush(); + + u32 read(u8* outBuffer, u32 bytesToRead); + bool tryRead(u32* actual_size, u8* data, u32 size); + + u32 write(const u8* data, u32 size); + bool tryWrite(u32* actual_size, const u8* data, u32 size); + + bool seek(s32 offset, FileDevice::SeekOrigin origin); + bool trySeek(s32 offset, FileDevice::SeekOrigin origin); + u32 getCurrentSeekPos(); + bool tryGetCurrentSeekPos(u32* pos); + + u32 getFileSize(); + bool tryGetFileSize(u32* size); + + u32 getDivSize() const { return mDivSize; } + +protected: + friend class FileDevice; + + s32 mDivSize; +}; + +class DirectoryHandle : public HandleBase +{ +public: + DirectoryHandle() : HandleBase() {} + + virtual ~DirectoryHandle() + { + FileDevice* _device = mOriginalDevice; + if (_device != NULL) + _device->tryCloseDirectory(this); + } + + bool close(); + bool tryClose(); + u32 read(DirectoryEntry* entries, u32 count); + bool tryRead(u32* actual_count, DirectoryEntry* entries, u32 count); +}; + +struct DirectoryEntry +{ + DirectoryEntry() : name(), is_directory(false) {} + + FixedSafeString<256> name; + bool is_directory; +}; + +} // namespace sead + +#endif // SEAD_FILEDEVICE_H_ diff --git a/lib/sead/include/filedevice/seadFileDeviceMgr.h b/lib/sead/include/filedevice/seadFileDeviceMgr.h new file mode 100644 index 00000000..89c2ece3 --- /dev/null +++ b/lib/sead/include/filedevice/seadFileDeviceMgr.h @@ -0,0 +1,81 @@ +#ifndef SEAD_FILEDEVICEMGR_H_ +#define SEAD_FILEDEVICEMGR_H_ + +#ifdef cafe +#include +#endif // cafe + +#include +#include +#include +#include +#include +#include + +namespace sead +{ +class FileDeviceMgr +{ + SEAD_SINGLETON_DISPOSER(FileDeviceMgr) + FileDeviceMgr(); + ~FileDeviceMgr(); + +public: + void traceFilePath(const SafeString& path) const; + void traceDirectoryPath(const SafeString& path) const; + void resolveFilePath(BufferedSafeString* out, const SafeString& path) const; + void resolveDirectoryPath(BufferedSafeString* out, const SafeString& path) const; + + void mount(FileDevice* device, const SafeString& name = SafeString::cEmptyString); + void unmount(FileDevice* device); + void unmount(const SafeString& name); + FileDevice* findDeviceFromPath(const SafeString& path, BufferedSafeString* pathNoDrive) const; + FileDevice* findDevice(const SafeString& name) const; + + FileDevice* tryOpen(FileHandle* handle, const SafeString& path, FileDevice::FileOpenFlag flag, + u32 divSize); + FileDevice* tryOpenDirectory(DirectoryHandle* handle, const SafeString& path); + + u8* tryLoad(FileDevice::LoadArg& arg); + void unload(u8* data); + bool trySave(FileDevice::SaveArg& arg); + + void mountSaveDataForDebug(Heap* heap); + void unmountSaveDataForDebug(); + + FileDevice* getMainFileDevice() const { return mMainFileDevice; } + FileDevice* getDefaultFileDevice() const { return mDefaultFileDevice; } + void setDefaultFileDevice(FileDevice* device) { mDefaultFileDevice = device; } + +#ifdef NNSDK + bool hasMountedHost() const { return mMountedHost; } + bool hasMountedSd() const { return mMountedSd; } +#endif + +private: + typedef TList DeviceList; + + void mount_(Heap* heap); + void unmount_(); + + DeviceList mDeviceList{}; + FileDevice* mDefaultFileDevice = nullptr; + MainFileDevice* mMainFileDevice = nullptr; + +#ifdef cafe + static void stateChangeCallback_(FSClient* client, FSVolumeState state, void* context); + + FSClient client; + u8 _1724[128]; + u8 _17A4[128]; + u32 _1824; +#elif defined(NNSDK) + u8* mRomCache = nullptr; + bool mMountedHost = false; + bool mMountedSd = false; +#endif +}; + +} // namespace sead + +#endif // SEAD_FILEDEVICEMGR_H_ diff --git a/lib/sead/include/filedevice/seadMainFileDevice.h b/lib/sead/include/filedevice/seadMainFileDevice.h new file mode 100644 index 00000000..0acf826d --- /dev/null +++ b/lib/sead/include/filedevice/seadMainFileDevice.h @@ -0,0 +1,112 @@ +#ifndef SEAD_MAIN_FILEDEVICE_H_ +#define SEAD_MAIN_FILEDEVICE_H_ + +#include +#include +#include +#include + +namespace sead +{ +class MainFileDevice : public FileDevice +{ + SEAD_RTTI_OVERRIDE(MainFileDevice, FileDevice) + +public: + explicit MainFileDevice(Heap* heap); + ~MainFileDevice() override; + + void traceFilePath(const SafeString& path) const override; + void traceDirectoryPath(const SafeString& path) const override; + void resolveFilePath(BufferedSafeString* out, const SafeString& path) const override; + void resolveDirectoryPath(BufferedSafeString* out, const SafeString& path) const override; + +protected: + bool doIsAvailable_() const override { return mFileDevice->isAvailable(); } + + FileDevice* doOpen_(FileHandle* handle, const SafeString& path, FileOpenFlag flag) override + { + return mFileDevice->tryOpen(handle, path, flag, handle->getDivSize()); + } + + bool doClose_(FileHandle* handle) override { return mFileDevice->tryClose(handle); } + + bool doFlush_(FileHandle* handle) override { return mFileDevice->tryFlush(handle); } + + bool doRemove_(const SafeString& str) override { return mFileDevice->tryRemove(str); } + + bool doRead_(u32* bytesRead, FileHandle* handle, u8* outBuffer, u32 bytesToRead) override + { + return mFileDevice->tryRead(bytesRead, handle, outBuffer, bytesToRead); + } + + bool doWrite_(u32* bytesWritten, FileHandle* handle, const u8* inBuffer, + u32 bytesToWrite) override + { + return mFileDevice->tryWrite(bytesWritten, handle, inBuffer, bytesToWrite); + } + + bool doSeek_(FileHandle* handle, s32 offset, SeekOrigin origin) override + { + return mFileDevice->trySeek(handle, offset, origin); + } + + bool doGetCurrentSeekPos_(u32* seekPos, FileHandle* handle) override + { + return mFileDevice->tryGetCurrentSeekPos(seekPos, handle); + } + + bool doGetFileSize_(u32* fileSize, const SafeString& path) override + { + return mFileDevice->tryGetFileSize(fileSize, path); + } + + bool doGetFileSize_(u32* fileSize, FileHandle* handle) override + { + return mFileDevice->tryGetFileSize(fileSize, handle); + } + + bool doIsExistFile_(bool* exists, const SafeString& path) override + { + return mFileDevice->tryIsExistFile(exists, path); + } + + bool doIsExistDirectory_(bool* exists, const SafeString& path) override + { + return mFileDevice->tryIsExistDirectory(exists, path); + } + + FileDevice* doOpenDirectory_(DirectoryHandle* handle, const SafeString& path) override + { + return mFileDevice->tryOpenDirectory(handle, path); + } + + bool doCloseDirectory_(DirectoryHandle* handle) override + { + return mFileDevice->tryCloseDirectory(handle); + } + + bool doReadDirectory_(u32* entriesRead, DirectoryHandle* handle, DirectoryEntry* entries, + u32 entriesToRead) override + { + return mFileDevice->tryReadDirectory(entriesRead, handle, entries, entriesToRead); + } + + bool doMakeDirectory_(const SafeString& path, u32 x) override + { + return mFileDevice->tryMakeDirectory(path, x); + } + + s32 doGetLastRawError_() const override { return mFileDevice->getLastRawError(); } + + bool isMatchDevice_(const HandleBase* handle) const override + { + return mFileDevice->isMatchDevice_(handle); + } + + FileDevice* mFileDevice; +}; + +} // namespace sead + +#endif // SEAD_MAIN_FILEDEVICE_H_ diff --git a/lib/sead/include/filedevice/seadPath.h b/lib/sead/include/filedevice/seadPath.h new file mode 100644 index 00000000..e54ad184 --- /dev/null +++ b/lib/sead/include/filedevice/seadPath.h @@ -0,0 +1,22 @@ +#ifndef SEAD_PATH_H_ +#define SEAD_PATH_H_ + +#include + +namespace sead +{ +class Path +{ +public: + static bool getDriveName(BufferedSafeString* drive_name, const SafeString& path); + static void getPathExceptDrive(BufferedSafeString* out, const SafeString& path); + static bool getExt(BufferedSafeString* ext, const SafeString& path); + static bool getFileName(BufferedSafeString* name, const SafeString& path); + static bool getBaseFileName(BufferedSafeString* name, const SafeString& path); + static bool getDirectoryName(BufferedSafeString* name, const SafeString& path); + static void join(BufferedSafeString* out, const char* path1, const char* path2); + static void changeDelimiter(BufferedSafeString* out, char delimiter); +}; +} // namespace sead + +#endif // SEAD_PATH_H_ diff --git a/lib/sead/include/framework/seadCalculateTask.h b/lib/sead/include/framework/seadCalculateTask.h new file mode 100644 index 00000000..91e8012b --- /dev/null +++ b/lib/sead/include/framework/seadCalculateTask.h @@ -0,0 +1,32 @@ +#pragma once + +#include "framework/seadMethodTree.h" +#include "framework/seadTaskBase.h" + +namespace sead +{ +class CalculateTask : public TaskBase +{ + SEAD_RTTI_OVERRIDE(CalculateTask, TaskBase) +public: + explicit CalculateTask(const TaskConstructArg& arg); + CalculateTask(const TaskConstructArg& arg, const char* name); + ~CalculateTask() override; + void pauseCalc(bool b) override; + void pauseDraw(bool b) override; + void pauseCalcRec(bool b) override; + void pauseDrawRec(bool b) override; + void pauseCalcChild(bool b) override; + void pauseDrawChild(bool b) override; + void attachCalcImpl() override; + void attachDrawImpl() override; + void detachCalcImpl() override; + void detachDrawImpl() override; + const RuntimeTypeInfo::Interface* getCorrespondingMethodTreeMgrTypeInfo() const override; + MethodTreeNode* getMethodTreeNode(s32 method_type) override; + virtual void calc() {} + +protected: + MethodTreeNode mCalcNode{nullptr}; +}; +} // namespace sead diff --git a/lib/sead/include/framework/seadFramework.h b/lib/sead/include/framework/seadFramework.h new file mode 100644 index 00000000..37344ffe --- /dev/null +++ b/lib/sead/include/framework/seadFramework.h @@ -0,0 +1,91 @@ +#ifndef SEAD_FRAMEWORK_H_ +#define SEAD_FRAMEWORK_H_ + +//#include +#include +//#include +//#include +//#include +//#include +#include +#include +#include +#include