Loads of WASM type registry.
continuous-integration/drone/push Build is failing
Details
continuous-integration/drone/push Build is failing
Details
This commit is contained in:
parent
82bc816151
commit
aac6c83bcf
|
@ -6,17 +6,23 @@
|
||||||
namespace PkmnLib::Library {
|
namespace PkmnLib::Library {
|
||||||
class ItemLibrary final : public CreatureLib::Library::ItemLibrary {
|
class ItemLibrary final : public CreatureLib::Library::ItemLibrary {
|
||||||
public:
|
public:
|
||||||
inline std::optional<ArbUt::BorrowedPtr<const Item>> TryGet(const ArbUt::BasicStringView& name) const {
|
inline std::optional<ArbUt::BorrowedPtr<const Item>> TryGet(const ArbUt::StringView& name) const {
|
||||||
auto res = CreatureLib::Library::ItemLibrary::TryGet(name.GetHash());
|
auto res = CreatureLib::Library::ItemLibrary::TryGet(name);
|
||||||
|
if (!res.has_value())
|
||||||
|
return {};
|
||||||
|
return res.value().ForceAs<const Item>();
|
||||||
|
}
|
||||||
|
inline std::optional<ArbUt::BorrowedPtr<const Item>> TryGet(u32 hashedKey) const {
|
||||||
|
auto res = CreatureLib::Library::ItemLibrary::TryGetByHash(hashedKey);
|
||||||
if (!res.has_value())
|
if (!res.has_value())
|
||||||
return {};
|
return {};
|
||||||
return res.value().ForceAs<const Item>();
|
return res.value().ForceAs<const Item>();
|
||||||
}
|
}
|
||||||
|
|
||||||
inline ArbUt::BorrowedPtr<const Item> Get(const ArbUt::BasicStringView& name) const {
|
inline ArbUt::BorrowedPtr<const Item> Get(const ArbUt::StringView& name) const {
|
||||||
return CreatureLib::Library::ItemLibrary::Get(name).ForceAs<const Item>();
|
return CreatureLib::Library::ItemLibrary::Get(name).ForceAs<const Item>();
|
||||||
}
|
}
|
||||||
inline ArbUt::BorrowedPtr<const Item> operator[](const ArbUt::BasicStringView& name) const { return Get(name); }
|
inline ArbUt::BorrowedPtr<const Item> operator[](const ArbUt::StringView& name) const { return Get(name); }
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -12,24 +12,24 @@ namespace PkmnLib::Library {
|
||||||
return Get(name);
|
return Get(name);
|
||||||
}
|
}
|
||||||
|
|
||||||
inline std::optional<ArbUt::BorrowedPtr<const MoveData>> TryGet(const ArbUt::BasicStringView& name) const {
|
inline std::optional<ArbUt::BorrowedPtr<const MoveData>> TryGet(const ArbUt::StringView& name) const {
|
||||||
auto res = CreatureLib::Library::AttackLibrary::TryGet(name);
|
auto res = CreatureLib::Library::AttackLibrary::TryGet(name);
|
||||||
if (!res.has_value())
|
if (!res.has_value())
|
||||||
return {};
|
return {};
|
||||||
return res.value().ForceAs<const MoveData>();
|
return res.value().ForceAs<const MoveData>();
|
||||||
}
|
}
|
||||||
inline std::optional<ArbUt::BorrowedPtr<const MoveData>> TryGet(u32 hash) const {
|
inline std::optional<ArbUt::BorrowedPtr<const MoveData>> TryGetByHash(u32 hash) const {
|
||||||
auto res = CreatureLib::Library::AttackLibrary::TryGet(hash);
|
auto res = CreatureLib::Library::AttackLibrary::TryGetByHash(hash);
|
||||||
if (!res.has_value())
|
if (!res.has_value())
|
||||||
return {};
|
return {};
|
||||||
return res.value().ForceAs<const MoveData>();
|
return res.value().ForceAs<const MoveData>();
|
||||||
}
|
}
|
||||||
|
|
||||||
inline ArbUt::BorrowedPtr<const MoveData> Get(const ArbUt::BasicStringView& name) const {
|
inline ArbUt::BorrowedPtr<const MoveData> Get(const ArbUt::StringView& name) const {
|
||||||
return CreatureLib::Library::AttackLibrary::Get(name).As<const MoveData>();
|
return CreatureLib::Library::AttackLibrary::Get(name).As<const MoveData>();
|
||||||
}
|
}
|
||||||
inline ArbUt::BorrowedPtr<const MoveData> Get(u32 hash) const {
|
inline ArbUt::BorrowedPtr<const MoveData> Get(u32 hash) const {
|
||||||
return CreatureLib::Library::AttackLibrary::Get(hash).As<const MoveData>();
|
return CreatureLib::Library::AttackLibrary::GetByHash(hash).As<const MoveData>();
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
#ifndef PKMNLIB_NATURELIBRARY_HPP
|
#ifndef PKMNLIB_NATURELIBRARY_HPP
|
||||||
#define PKMNLIB_NATURELIBRARY_HPP
|
#define PKMNLIB_NATURELIBRARY_HPP
|
||||||
|
|
||||||
|
#include <Arbutils/Collections/StringViewDictionary.hpp>
|
||||||
#include <Arbutils/Memory/Memory.hpp>
|
#include <Arbutils/Memory/Memory.hpp>
|
||||||
#include <Arbutils/Random.hpp>
|
#include <Arbutils/Random.hpp>
|
||||||
#include <CreatureLib/Library/Exceptions/CreatureException.hpp>
|
#include <CreatureLib/Library/Exceptions/CreatureException.hpp>
|
||||||
|
@ -9,7 +10,7 @@
|
||||||
namespace PkmnLib::Library {
|
namespace PkmnLib::Library {
|
||||||
class NatureLibrary {
|
class NatureLibrary {
|
||||||
private:
|
private:
|
||||||
std::unordered_map<ArbUt::StringView, std::unique_ptr<const Nature>> _items;
|
ArbUt::StringViewDictionary<std::unique_ptr<const Nature>> _items;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
explicit NatureLibrary(size_t size = 32) noexcept : _items(size) {}
|
explicit NatureLibrary(size_t size = 32) noexcept : _items(size) {}
|
||||||
|
@ -17,19 +18,23 @@ namespace PkmnLib::Library {
|
||||||
~NatureLibrary() = default;
|
~NatureLibrary() = default;
|
||||||
|
|
||||||
inline void LoadNature(const ArbUt::StringView& name, const Nature* nature) {
|
inline void LoadNature(const ArbUt::StringView& name, const Nature* nature) {
|
||||||
_items.insert({name, std::unique_ptr<const Nature>(nature)});
|
_items.GetStdMap().insert({name, std::unique_ptr<const Nature>(nature)});
|
||||||
}
|
}
|
||||||
|
|
||||||
inline ArbUt::BorrowedPtr<const Nature> GetNatureByName(const ArbUt::StringView& name) const {
|
inline ArbUt::BorrowedPtr<const Nature> GetNatureByName(const ArbUt::StringView& name) const {
|
||||||
return _items.at(name);
|
return _items.Get(name);
|
||||||
|
}
|
||||||
|
|
||||||
|
inline ArbUt::BorrowedPtr<const Nature> GetNatureByHash(u32 hash) const {
|
||||||
|
return _items.GetFromHash(hash);
|
||||||
}
|
}
|
||||||
|
|
||||||
inline const ArbUt::StringView& GetRandomNatureName(ArbUt::Random rand = ArbUt::Random()) const {
|
inline const ArbUt::StringView& GetRandomNatureName(ArbUt::Random rand = ArbUt::Random()) const {
|
||||||
auto i = rand.Get(_items.size());
|
auto i = rand.Get(_items.Count());
|
||||||
return std::next(std::begin(_items), i)->first;
|
return std::next(std::begin(_items), i)->first;
|
||||||
}
|
}
|
||||||
|
|
||||||
inline ArbUt::StringView GetNatureName(ArbUt::BorrowedPtr<const Nature> nature) {
|
inline const ArbUt::StringView& GetNatureName(ArbUt::BorrowedPtr<const Nature> nature) {
|
||||||
for (const auto& v : _items) {
|
for (const auto& v : _items) {
|
||||||
if (v.second.get() == nature.GetRaw()) {
|
if (v.second.get() == nature.GetRaw()) {
|
||||||
return v.first;
|
return v.first;
|
||||||
|
@ -38,7 +43,7 @@ namespace PkmnLib::Library {
|
||||||
throw ArbUt::Exception("Nature not found.");
|
throw ArbUt::Exception("Nature not found.");
|
||||||
}
|
}
|
||||||
|
|
||||||
size_t GetNatureCount() const noexcept { return _items.size(); }
|
size_t GetNatureCount() const noexcept { return _items.Count(); }
|
||||||
inline const ArbUt::StringView& GetNatureFromIndex(size_t index) const {
|
inline const ArbUt::StringView& GetNatureFromIndex(size_t index) const {
|
||||||
return std::next(std::begin(_items), index)->first;
|
return std::next(std::begin(_items), index)->first;
|
||||||
}
|
}
|
||||||
|
|
|
@ -12,19 +12,28 @@ namespace PkmnLib::Library {
|
||||||
public:
|
public:
|
||||||
SpeciesLibrary(size_t initialCapacity = 32) : CreatureLib::Library::SpeciesLibrary(initialCapacity) {}
|
SpeciesLibrary(size_t initialCapacity = 32) : CreatureLib::Library::SpeciesLibrary(initialCapacity) {}
|
||||||
|
|
||||||
inline std::optional<ArbUt::BorrowedPtr<const PokemonSpecies>>
|
inline std::optional<ArbUt::BorrowedPtr<const PokemonSpecies>> TryGet(const ArbUt::StringView& name) const {
|
||||||
TryGet(const ArbUt::BasicStringView& name) const {
|
|
||||||
auto res = CreatureLib::Library::SpeciesLibrary::TryGet(name);
|
auto res = CreatureLib::Library::SpeciesLibrary::TryGet(name);
|
||||||
if (!res.has_value())
|
if (!res.has_value())
|
||||||
return {};
|
return {};
|
||||||
return res.value().ForceAs<const PokemonSpecies>();
|
return res.value().ForceAs<const PokemonSpecies>();
|
||||||
}
|
}
|
||||||
|
|
||||||
inline ArbUt::BorrowedPtr<const PokemonSpecies> Get(const ArbUt::BasicStringView& name) const {
|
inline std::optional<ArbUt::BorrowedPtr<const PokemonSpecies>> TryGetByHash(u32 hashedKey) const {
|
||||||
return CreatureLib::Library::SpeciesLibrary::Get(name).As<const PokemonSpecies>();
|
auto res = CreatureLib::Library::SpeciesLibrary::TryGetByHash(hashedKey);
|
||||||
|
if (!res.has_value())
|
||||||
|
return {};
|
||||||
|
return res.value().ForceAs<const PokemonSpecies>();
|
||||||
}
|
}
|
||||||
|
|
||||||
ArbUt::BorrowedPtr<const PokemonSpecies> operator[](const ArbUt::BasicStringView& name) const {
|
inline ArbUt::BorrowedPtr<const PokemonSpecies> Get(const ArbUt::StringView& name) const {
|
||||||
|
return CreatureLib::Library::SpeciesLibrary::Get(name).As<const PokemonSpecies>();
|
||||||
|
}
|
||||||
|
inline ArbUt::BorrowedPtr<const PokemonSpecies> GetByHash(u32 hashedKey) const {
|
||||||
|
return CreatureLib::Library::SpeciesLibrary::GetByHash(hashedKey).As<const PokemonSpecies>();
|
||||||
|
}
|
||||||
|
|
||||||
|
ArbUt::BorrowedPtr<const PokemonSpecies> operator[](const ArbUt::StringView& name) const {
|
||||||
return Get(name);
|
return Get(name);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1,86 +0,0 @@
|
||||||
#include "CoreMethods.hpp"
|
|
||||||
#include <cstring>
|
|
||||||
#include "../WebAssemblyScriptResolver.hpp"
|
|
||||||
#include "WasmHelperFile.hpp"
|
|
||||||
#include "wasm.h"
|
|
||||||
|
|
||||||
wasm_func_t* CreateErrorFunc(wasm_store_t* store, WebAssemblyScriptResolver* resolver) {
|
|
||||||
// This is probably the most horrific function we need to expose. As we do not want the scripting library to be
|
|
||||||
// responsible for string formatting for size reasons, we pass a lot of data separately. This includes several
|
|
||||||
// strings.
|
|
||||||
return WasmHelpers::CreateFunc<void, i32, i32, i32, i32, i32, i32>(
|
|
||||||
store, resolver, [](void* env, const wasm_val_vec_t* args, wasm_val_vec_t*) -> wasm_trap_t* {
|
|
||||||
auto msg = args->data[0].of.i32;
|
|
||||||
auto msg_len = args->data[1].of.i32;
|
|
||||||
auto file = args->data[2].of.i32;
|
|
||||||
auto file_len = args->data[3].of.i32;
|
|
||||||
auto line = args->data[4].of.i32;
|
|
||||||
auto position = args->data[5].of.i32;
|
|
||||||
|
|
||||||
auto* resolver = (WebAssemblyScriptResolver*)env;
|
|
||||||
auto* msgPointer = wasm_memory_data(resolver->GetMemory()) + msg;
|
|
||||||
auto* filePointer = wasm_memory_data(resolver->GetMemory()) + file;
|
|
||||||
|
|
||||||
auto msgString = std::string_view(msgPointer, msg_len);
|
|
||||||
auto fileString = std::string_view(filePointer, file_len);
|
|
||||||
|
|
||||||
std::stringstream fullMessage;
|
|
||||||
fullMessage << "WASM Error with message: " << msgString << std::endl
|
|
||||||
<< "in file: " << fileString << ". Line: " << line << ":" << position;
|
|
||||||
|
|
||||||
wasm_message_t message;
|
|
||||||
wasm_name_new_from_string_nt(&message, fullMessage.str().c_str());
|
|
||||||
wasm_trap_t* trap = wasm_trap_new(resolver->GetStore(), &message);
|
|
||||||
wasm_name_delete(&message);
|
|
||||||
return trap;
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
wasm_func_t* CreatePrintFunc(wasm_store_t* store, WebAssemblyScriptResolver* resolver) {
|
|
||||||
return WasmHelpers::CreateFunc<void, i32, i32>(
|
|
||||||
store, resolver, [](void* env, const wasm_val_vec_t* args, wasm_val_vec_t*) -> wasm_trap_t* {
|
|
||||||
auto msg = args->data[0].of.i32;
|
|
||||||
auto msg_len = args->data[1].of.i32;
|
|
||||||
auto resolver = (WebAssemblyScriptResolver*)env;
|
|
||||||
auto* msgPointer = wasm_memory_data(resolver->GetMemory()) + msg;
|
|
||||||
auto msgString = std::string_view(msgPointer, msg_len);
|
|
||||||
std::cout << msgString << std::endl;
|
|
||||||
return nullptr;
|
|
||||||
});
|
|
||||||
;
|
|
||||||
}
|
|
||||||
|
|
||||||
wasm_func_t* ConstString_GetHash(wasm_store_t* store, WebAssemblyScriptResolver* resolver) {
|
|
||||||
return WasmHelpers::CreateFunc2<u32, const ArbUt::StringView*>(
|
|
||||||
store, resolver,
|
|
||||||
std::function<u32(WebAssemblyScriptResolver*, const ArbUt::StringView*)>(
|
|
||||||
[](WebAssemblyScriptResolver*, const ArbUt::StringView* sv) -> u32 { return sv->GetHash(); }));
|
|
||||||
}
|
|
||||||
|
|
||||||
wasm_func_t* ConstString_GetStr(wasm_store_t* store, WebAssemblyScriptResolver* resolver) {
|
|
||||||
return WasmHelpers::CreateFunc<i32, const ArbUt::StringView*>(
|
|
||||||
store, resolver, [](void* env, const wasm_val_vec_t* args, wasm_val_vec_t* returns) -> wasm_trap_t* {
|
|
||||||
auto resolver = (WebAssemblyScriptResolver*)env;
|
|
||||||
auto& constString = *(ArbUt::StringView*)args->data[0].of.i64;
|
|
||||||
|
|
||||||
// To allow webassembly to access the C String, we need to allocate it inside it's memory.
|
|
||||||
// Length + 1 to make room for the '\0'
|
|
||||||
auto stringPointer = resolver->AllocateMemory(constString.Length() + 1, std::alignment_of<const char>());
|
|
||||||
|
|
||||||
// After we have the pointer to the memory allocated for the string, copy the string with specified length
|
|
||||||
// to it, then suffix it with the null byte to end it.
|
|
||||||
strncpy(reinterpret_cast<char*>(stringPointer.first), constString.c_str(), constString.Length());
|
|
||||||
stringPointer.first[constString.Length()] = '\0';
|
|
||||||
|
|
||||||
returns->data[0] = WASM_I32_VAL(stringPointer.second);
|
|
||||||
return nullptr;
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
void WebAssemblyCoreMethods::Register(wasm_store_t* store, ArbUt::Dictionary<std::string, wasm_func_t*>& externs,
|
|
||||||
WebAssemblyScriptResolver* resolver) {
|
|
||||||
externs.Insert("_error", CreateErrorFunc(store, resolver));
|
|
||||||
externs.Insert("_print", CreatePrintFunc(store, resolver));
|
|
||||||
externs.Insert("arbutils_const_string_get_hash", ConstString_GetHash(store, resolver));
|
|
||||||
externs.Insert("arbutils_const_string_get_str", ConstString_GetStr(store, resolver));
|
|
||||||
}
|
|
|
@ -1,14 +0,0 @@
|
||||||
#ifndef PKMNLIB_COREMETHODS_HPP
|
|
||||||
#define PKMNLIB_COREMETHODS_HPP
|
|
||||||
|
|
||||||
#include <Arbutils/Collections/Dictionary.hpp>
|
|
||||||
#include <wasm.h>
|
|
||||||
|
|
||||||
class WebAssemblyScriptResolver;
|
|
||||||
class WebAssemblyCoreMethods {
|
|
||||||
public:
|
|
||||||
static void Register(wasm_store_t* store, ArbUt::Dictionary<std::string, wasm_func_t*>& externs,
|
|
||||||
WebAssemblyScriptResolver* resolver);
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif // PKMNLIB_COREMETHODS_HPP
|
|
|
@ -2,38 +2,115 @@
|
||||||
#include <type_traits>
|
#include <type_traits>
|
||||||
#include "../../../../Battling/Library/BattleLibrary.hpp"
|
#include "../../../../Battling/Library/BattleLibrary.hpp"
|
||||||
#include "../../WebAssemblyScriptResolver.hpp"
|
#include "../../WebAssemblyScriptResolver.hpp"
|
||||||
#include "../WasmHelperFile.hpp"
|
#include "../WASMHelperFile.hpp"
|
||||||
#include "wasm.h"
|
#include "wasm.h"
|
||||||
|
|
||||||
wasm_func_t* MoveLibrary_GetMoveByHash(wasm_store_t* store) {
|
using namespace PkmnLib::Library;
|
||||||
wasm_functype_t* type =
|
|
||||||
wasm_functype_new_2_1(wasm_valtype_new_i64(), wasm_valtype_new_i32(), wasm_valtype_new_i64());
|
#define BASELIBRARY_GET_VALUE_FUNC(type, value_type) \
|
||||||
auto* f = wasm_func_new(store, type, [](const wasm_val_vec_t* args, wasm_val_vec_t* returns) -> wasm_trap_t* {
|
wasm_func_t* type##Library_Get##type##ByHash(WebAssemblyScriptResolver* resolver) { \
|
||||||
auto moveLibrary = (PkmnLib::Library::MoveLibrary*)args->data[0].of.i64;
|
return WasmHelpers::CreateFunc<const value_type*, type##Library*, u32>( \
|
||||||
auto hash = (u32)args->data[1].of.i32;
|
resolver, {[](WebAssemblyScriptResolver*, type##Library* lib, u32 hash) -> const value_type* { \
|
||||||
auto opt = moveLibrary->TryGet(hash);
|
auto opt = lib->TryGetByHash(hash); \
|
||||||
if (!opt.has_value()) {
|
if (!opt.has_value()) { \
|
||||||
returns->data[0] = WASM_I64_VAL(0);
|
return nullptr; \
|
||||||
} else{
|
} \
|
||||||
returns->data[0] = WASM_I64_VAL(reinterpret_cast<i64>(moveLibrary->Get(hash).GetRaw()));
|
return opt.value(); \
|
||||||
}
|
}}); \
|
||||||
return nullptr;
|
}
|
||||||
});
|
|
||||||
wasm_functype_delete(type);
|
BASELIBRARY_GET_VALUE_FUNC(Species, PokemonSpecies)
|
||||||
return f;
|
BASELIBRARY_GET_VALUE_FUNC(Move, MoveData)
|
||||||
|
BASELIBRARY_GET_VALUE_FUNC(Item, CreatureLib::Library::Item)
|
||||||
|
|
||||||
|
#define REGISTER_BASE_LIB_FUNCS(typeName, type) \
|
||||||
|
externs.Insert(typeName "_library_get_" typeName "_by_hash", type##Library_Get##type##ByHash(resolver))
|
||||||
|
|
||||||
|
wasm_func_t* GrowthRates_CalculateLevelWithHash(WebAssemblyScriptResolver* resolver) {
|
||||||
|
return WasmHelpers::CreateFunc<level_int_t, CreatureLib::Library::GrowthRateLibrary*, u32, u32>(
|
||||||
|
resolver, {[](WebAssemblyScriptResolver*, CreatureLib::Library::GrowthRateLibrary* lib, u32 hash,
|
||||||
|
u32 experience) -> level_int_t { return lib->CalculateLevel(hash, experience); }});
|
||||||
}
|
}
|
||||||
|
|
||||||
void LibraryMethods::Register(wasm_store_t* store, ArbUt::Dictionary<std::string, wasm_func_t*>& externs,
|
wasm_func_t* GrowthRates_CalculateExperienceWithHash(WebAssemblyScriptResolver* resolver) {
|
||||||
|
return WasmHelpers::CreateFunc<u32, CreatureLib::Library::GrowthRateLibrary*, u32, level_int_t>(
|
||||||
|
resolver, {[](WebAssemblyScriptResolver*, CreatureLib::Library::GrowthRateLibrary* lib, u32 hash,
|
||||||
|
level_int_t level) -> u32 { return lib->CalculateExperience(hash, level); }});
|
||||||
|
}
|
||||||
|
|
||||||
|
wasm_func_t* TypeLibrary_GetTypeIdFromHash(WebAssemblyScriptResolver* resolver) {
|
||||||
|
return WasmHelpers::CreateFunc<u8, CreatureLib::Library::TypeLibrary*, u32>(
|
||||||
|
resolver, {[](WebAssemblyScriptResolver*, CreatureLib::Library::TypeLibrary* lib, u32 hash) -> u8 {
|
||||||
|
return lib->GetTypeIdByHash(hash);
|
||||||
|
}});
|
||||||
|
}
|
||||||
|
|
||||||
|
wasm_func_t* TypeLibrary_GetSingleEffectiveness(WebAssemblyScriptResolver* resolver) {
|
||||||
|
return WasmHelpers::CreateFunc<float, CreatureLib::Library::TypeLibrary*, u8, u8>(
|
||||||
|
resolver, {[](WebAssemblyScriptResolver*, CreatureLib::Library::TypeLibrary* lib, u8 attacking,
|
||||||
|
u8 defensive) -> float { return lib->GetSingleEffectiveness(attacking, defensive); }});
|
||||||
|
}
|
||||||
|
|
||||||
|
wasm_func_t* TypeLibrary_GetTypeName(WebAssemblyScriptResolver* resolver) {
|
||||||
|
return WasmHelpers::CreateFunc<const ArbUt::StringView*, CreatureLib::Library::TypeLibrary*, u8>(
|
||||||
|
resolver, {[](WebAssemblyScriptResolver*, CreatureLib::Library::TypeLibrary* lib,
|
||||||
|
u8 type) -> const ArbUt::StringView* { return &lib->GetTypeName(type); }});
|
||||||
|
}
|
||||||
|
|
||||||
|
wasm_func_t* NatureLibrary_GetNatureByHash(WebAssemblyScriptResolver* resolver) {
|
||||||
|
return WasmHelpers::CreateFunc<const Nature*, NatureLibrary*, u32>(
|
||||||
|
resolver, {[](WebAssemblyScriptResolver*, NatureLibrary* lib, u32 hash) -> const Nature* {
|
||||||
|
return lib->GetNatureByHash(hash);
|
||||||
|
}});
|
||||||
|
}
|
||||||
|
|
||||||
|
wasm_func_t* NatureLibrary_GetNatureName(WebAssemblyScriptResolver* resolver) {
|
||||||
|
return WasmHelpers::CreateFunc<const ArbUt::StringView*, NatureLibrary*, const Nature*>(
|
||||||
|
resolver, {[](WebAssemblyScriptResolver*, NatureLibrary* lib,
|
||||||
|
const Nature* nature) -> const ArbUt::StringView* { return &lib->GetNatureName(nature); }});
|
||||||
|
}
|
||||||
|
|
||||||
|
void LibraryMethods::Register(ArbUt::Dictionary<std::string, wasm_func_t*>& externs,
|
||||||
WebAssemblyScriptResolver* resolver) {
|
WebAssemblyScriptResolver* resolver) {
|
||||||
REGISTER_GETTER("battling_battle_library_get_data_library", PkmnLib::Battling::BattleLibrary, GetStaticLib, store,
|
REGISTER_GETTER("battle_library_get_data_library", PkmnLib::Battling::BattleLibrary, GetStaticLib, resolver)
|
||||||
resolver);
|
|
||||||
REGISTER_GETTER("library_data_library_get_move_library", PkmnLib::Library::PokemonLibrary, GetMoveLibrary, store,
|
|
||||||
resolver);
|
|
||||||
externs.Insert("library_move_library_get_move_by_hash", MoveLibrary_GetMoveByHash(store));
|
|
||||||
|
|
||||||
REGISTER_GETTER("library_move_data_get_base_power", CreatureLib::Library::AttackData, GetBasePower, store,
|
// Data Library
|
||||||
resolver);
|
REGISTER_GETTER("data_library_get_settings", PokemonLibrary, GetSettings, resolver)
|
||||||
|
REGISTER_GETTER("data_library_get_species_library", PokemonLibrary, GetSpeciesLibrary, resolver)
|
||||||
|
REGISTER_GETTER("data_library_get_move_library", PokemonLibrary, GetMoveLibrary, resolver)
|
||||||
|
REGISTER_GETTER("data_library_get_item_library", PokemonLibrary, GetItemLibrary, resolver)
|
||||||
|
REGISTER_GETTER("data_library_get_growth_rates", CreatureLib::Library::DataLibrary, GetGrowthRates, resolver)
|
||||||
|
REGISTER_GETTER("data_library_get_type_library", CreatureLib::Library::DataLibrary, GetTypeLibrary, resolver)
|
||||||
|
REGISTER_GETTER("data_library_get_talent_library", CreatureLib::Library::DataLibrary, GetTalentLibrary, resolver)
|
||||||
|
REGISTER_GETTER("data_library_get_nature_library", PokemonLibrary, GetNatureLibrary, resolver)
|
||||||
|
|
||||||
REGISTER_GETTER("library_move_data_get_name", CreatureLib::Library::AttackData, GetName, store,
|
// Library Settings
|
||||||
resolver);
|
REGISTER_GETTER("settings_get_max_level", CreatureLib::Library::LibrarySettings, GetMaximalLevel, resolver)
|
||||||
|
REGISTER_GETTER("settings_get_max_moves", CreatureLib::Library::LibrarySettings, GetMaximalAttacks, resolver)
|
||||||
|
REGISTER_GETTER("settings_get_shiny_rate", LibrarySettings, GetShinyRate, resolver)
|
||||||
|
|
||||||
|
// Base libraries
|
||||||
|
REGISTER_BASE_LIB_FUNCS("species", Species);
|
||||||
|
REGISTER_BASE_LIB_FUNCS("move", Move);
|
||||||
|
REGISTER_BASE_LIB_FUNCS("item", Item);
|
||||||
|
|
||||||
|
// Growth Rates
|
||||||
|
externs.Insert("growthrate_library_calculate_level_by_hash", GrowthRates_CalculateLevelWithHash(resolver));
|
||||||
|
externs.Insert("growthrate_library_calculate_experience_by_hash",
|
||||||
|
GrowthRates_CalculateExperienceWithHash(resolver));
|
||||||
|
|
||||||
|
// Type Library
|
||||||
|
externs.Insert("type_library_get_type_id_by_hash", TypeLibrary_GetTypeIdFromHash(resolver));
|
||||||
|
externs.Insert("type_library_get_single_effectiveness", TypeLibrary_GetSingleEffectiveness(resolver));
|
||||||
|
externs.Insert("type_library_get_type_name", TypeLibrary_GetTypeName(resolver));
|
||||||
|
|
||||||
|
// Nature Library
|
||||||
|
externs.Insert("nature_library_get_nature_by_hash", NatureLibrary_GetNatureByHash(resolver));
|
||||||
|
externs.Insert("nature_library_get_nature_name", NatureLibrary_GetNatureName(resolver));
|
||||||
|
|
||||||
|
// Natures
|
||||||
|
REGISTER_GETTER("nature_get_increased_modifier", Nature, GetIncreaseModifier, resolver)
|
||||||
|
REGISTER_GETTER("nature_get_decreased_modifier", Nature, GetDecreaseModifier, resolver)
|
||||||
|
REGISTER_GETTER("nature_get_increased_stat", Nature, GetIncreasedStat, resolver)
|
||||||
|
REGISTER_GETTER("nature_get_decreased_stat", Nature, GetDecreasedStat, resolver)
|
||||||
}
|
}
|
||||||
|
|
|
@ -6,7 +6,7 @@
|
||||||
class WebAssemblyScriptResolver;
|
class WebAssemblyScriptResolver;
|
||||||
class LibraryMethods {
|
class LibraryMethods {
|
||||||
public:
|
public:
|
||||||
static void Register(wasm_store_t* store, ArbUt::Dictionary<std::string, wasm_func_t*>& externs,
|
static void Register(ArbUt::Dictionary<std::string, wasm_func_t*>& externs,
|
||||||
WebAssemblyScriptResolver* resolver);
|
WebAssemblyScriptResolver* resolver);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,29 @@
|
||||||
|
#include "WASMMoveDataRegistry.hpp"
|
||||||
|
#include <type_traits>
|
||||||
|
#include "../../../../Battling/Library/BattleLibrary.hpp"
|
||||||
|
#include "../../WebAssemblyScriptResolver.hpp"
|
||||||
|
#include "../WASMHelperFile.hpp"
|
||||||
|
#include "wasm.h"
|
||||||
|
|
||||||
|
using namespace CreatureLib::Library;
|
||||||
|
|
||||||
|
wasm_func_t* MoveData_HasFlagByHash(WebAssemblyScriptResolver* resolver) {
|
||||||
|
return WasmHelpers::CreateFunc<bool, AttackData*, u32>(
|
||||||
|
resolver, {[](WebAssemblyScriptResolver*, AttackData* move, u32 flag) -> bool {
|
||||||
|
return move->HasFlag(flag);
|
||||||
|
}});
|
||||||
|
}
|
||||||
|
|
||||||
|
void WASMMoveDataRegistry::Register(ArbUt::Dictionary<std::string, wasm_func_t*>& externs,
|
||||||
|
WebAssemblyScriptResolver* resolver) {
|
||||||
|
REGISTER_GETTER("move_data_get_name", AttackData, GetName, resolver)
|
||||||
|
REGISTER_GETTER("move_data_get_type", AttackData, GetType, resolver)
|
||||||
|
REGISTER_GETTER("move_data_get_category", AttackData, GetCategory, resolver)
|
||||||
|
REGISTER_GETTER("move_data_get_base_power", AttackData, GetBasePower, resolver);
|
||||||
|
REGISTER_GETTER("move_data_get_accuracy", AttackData, GetAccuracy, resolver);
|
||||||
|
REGISTER_GETTER("move_data_get_base_usages", AttackData, GetBaseUsages, resolver);
|
||||||
|
REGISTER_GETTER("move_data_get_target", AttackData, GetTarget, resolver);
|
||||||
|
REGISTER_GETTER("move_data_get_priority", AttackData, GetPriority, resolver);
|
||||||
|
REGISTER_GETTER("move_data_has_secondary_effect", AttackData, HasSecondaryEffect, resolver);
|
||||||
|
externs.Insert("move_data_has_flag_by_hash", MoveData_HasFlagByHash(resolver));
|
||||||
|
}
|
|
@ -0,0 +1,14 @@
|
||||||
|
#ifndef PKMNLIB_WASMMOVEDATAREGISTRY_H
|
||||||
|
#define PKMNLIB_WASMMOVEDATAREGISTRY_H
|
||||||
|
|
||||||
|
#include <Arbutils/Collections/Dictionary.hpp>
|
||||||
|
#include <wasm.h>
|
||||||
|
|
||||||
|
class WebAssemblyScriptResolver;
|
||||||
|
class WASMMoveDataRegistry {
|
||||||
|
public:
|
||||||
|
static void Register(ArbUt::Dictionary<std::string, wasm_func_t*>& externs,
|
||||||
|
WebAssemblyScriptResolver* resolver);
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif // PKMNLIB_WASMMOVEDATAREGISTRY_H
|
|
@ -0,0 +1,22 @@
|
||||||
|
#ifndef PKMNLIB_TYPEREGISTRY_HPP
|
||||||
|
#define PKMNLIB_TYPEREGISTRY_HPP
|
||||||
|
|
||||||
|
#include <string>
|
||||||
|
#include "../WebAssemblyScriptResolver.hpp"
|
||||||
|
#include "Arbutils/Collections/Dictionary.hpp"
|
||||||
|
#include "Library/LibraryMethods.hpp"
|
||||||
|
#include "Library/WASMMoveDataRegistry.hpp"
|
||||||
|
#include "WASMCoreMethods.hpp"
|
||||||
|
#include "WASMStringView.hpp"
|
||||||
|
|
||||||
|
class TypeRegistry {
|
||||||
|
public:
|
||||||
|
static void Register(ArbUt::Dictionary<std::string, wasm_func_t*>& externs, WebAssemblyScriptResolver* resolver) {
|
||||||
|
WASMCoreMethods::Register(externs, resolver);
|
||||||
|
WASMStringView::Register(externs, resolver);
|
||||||
|
LibraryMethods::Register(externs, resolver);
|
||||||
|
WASMMoveDataRegistry::Register(externs, resolver);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif // PKMNLIB_TYPEREGISTRY_HPP
|
|
@ -0,0 +1,45 @@
|
||||||
|
#include "WASMCoreMethods.hpp"
|
||||||
|
#include <cstring>
|
||||||
|
#include "../WebAssemblyScriptResolver.hpp"
|
||||||
|
#include "WASMHelperFile.hpp"
|
||||||
|
#include "wasm.h"
|
||||||
|
|
||||||
|
wasm_func_t* CreateErrorFunc(WebAssemblyScriptResolver* resolver) {
|
||||||
|
// This is probably the most horrific function we need to expose. As we do not want the scripting library to be
|
||||||
|
// responsible for string formatting for size reasons, we pass a lot of data separately. This includes several
|
||||||
|
// strings.
|
||||||
|
return WasmHelpers::CreateFunc<wasm_trap_t*, i32, i32, i32, i32, i32, i32>(
|
||||||
|
resolver, {[](WebAssemblyScriptResolver* resolver, i32 msg, i32 msg_len, i32 file, i32 file_len, i32 line,
|
||||||
|
i32 position) -> wasm_trap_t* {
|
||||||
|
auto* msgPointer = wasm_memory_data(resolver->GetMemory()) + msg;
|
||||||
|
auto* filePointer = wasm_memory_data(resolver->GetMemory()) + file;
|
||||||
|
|
||||||
|
auto msgString = std::string_view(msgPointer, msg_len);
|
||||||
|
auto fileString = std::string_view(filePointer, file_len);
|
||||||
|
|
||||||
|
std::stringstream fullMessage;
|
||||||
|
fullMessage << "WASM Error with message: " << msgString << std::endl
|
||||||
|
<< "in file: " << fileString << ". Line: " << line << ":" << position;
|
||||||
|
|
||||||
|
wasm_message_t message;
|
||||||
|
wasm_name_new_from_string_nt(&message, fullMessage.str().c_str());
|
||||||
|
wasm_trap_t* trap = wasm_trap_new(resolver->GetStore(), &message);
|
||||||
|
wasm_name_delete(&message);
|
||||||
|
return trap;
|
||||||
|
}});
|
||||||
|
}
|
||||||
|
|
||||||
|
wasm_func_t* CreatePrintFunc(WebAssemblyScriptResolver* resolver) {
|
||||||
|
return WasmHelpers::CreateFunc<void, i32, i32>(resolver,
|
||||||
|
{[](WebAssemblyScriptResolver* resolver, i32 msg, i32 msg_len) {
|
||||||
|
auto* msgPointer = wasm_memory_data(resolver->GetMemory()) + msg;
|
||||||
|
auto msgString = std::string_view(msgPointer, msg_len);
|
||||||
|
std::cout << msgString << std::endl;
|
||||||
|
}});
|
||||||
|
}
|
||||||
|
|
||||||
|
void WASMCoreMethods::Register(ArbUt::Dictionary<std::string, wasm_func_t*>& externs,
|
||||||
|
WebAssemblyScriptResolver* resolver) {
|
||||||
|
externs.Insert("_error", CreateErrorFunc(resolver));
|
||||||
|
externs.Insert("_print", CreatePrintFunc(resolver));
|
||||||
|
}
|
|
@ -0,0 +1,13 @@
|
||||||
|
#ifndef PKMNLIB_WASMCOREMETHODS_HPP
|
||||||
|
#define PKMNLIB_WASMCOREMETHODS_HPP
|
||||||
|
|
||||||
|
#include <Arbutils/Collections/Dictionary.hpp>
|
||||||
|
#include <wasm.h>
|
||||||
|
|
||||||
|
class WebAssemblyScriptResolver;
|
||||||
|
class WASMCoreMethods {
|
||||||
|
public:
|
||||||
|
static void Register(ArbUt::Dictionary<std::string, wasm_func_t*>& externs, WebAssemblyScriptResolver* resolver);
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif // PKMNLIB_WASMCOREMETHODS_HPP
|
|
@ -39,10 +39,10 @@ public:
|
||||||
}
|
}
|
||||||
|
|
||||||
template <typename T, typename R, R (T::*Method)() const>
|
template <typename T, typename R, R (T::*Method)() const>
|
||||||
static wasm_func_t* RegisterGetter(wasm_store_t* store, WebAssemblyScriptResolver* resolver) {
|
static wasm_func_t* RegisterGetter(WebAssemblyScriptResolver* resolver) {
|
||||||
wasm_functype_t* type = wasm_functype_new_1_1(wasm_valtype_new_i64(), GetValType<R>());
|
wasm_functype_t* type = wasm_functype_new_1_1(wasm_valtype_new_i64(), GetValType<R>());
|
||||||
auto* f = wasm_func_new_with_env(
|
auto* f = wasm_func_new_with_env(
|
||||||
store, type,
|
resolver->GetStore(), type,
|
||||||
[](void* env, const wasm_val_vec_t* args, wasm_val_vec_t* returns) -> wasm_trap_t* {
|
[](void* env, const wasm_val_vec_t* args, wasm_val_vec_t* returns) -> wasm_trap_t* {
|
||||||
try {
|
try {
|
||||||
auto obj = (const T*)args->data[0].of.i64;
|
auto obj = (const T*)args->data[0].of.i64;
|
||||||
|
@ -59,26 +59,17 @@ public:
|
||||||
return f;
|
return f;
|
||||||
}
|
}
|
||||||
|
|
||||||
template <class R, class... Args>
|
|
||||||
static wasm_func_t* CreateFunc(wasm_store_t* store, WebAssemblyScriptResolver* resolver,
|
|
||||||
wasm_func_callback_with_env_t func) {
|
|
||||||
auto funcType = GetFuncType<R, Args...>();
|
|
||||||
auto* f = wasm_func_new_with_env(store, funcType, func, resolver, nullptr);
|
|
||||||
wasm_functype_delete(funcType);
|
|
||||||
return f;
|
|
||||||
}
|
|
||||||
|
|
||||||
template <typename T> inline static T ConvertAllArguments(const wasm_val_vec_t* t, std::size_t& index) {
|
template <typename T> inline static T ConvertAllArguments(const wasm_val_vec_t* t, std::size_t& index) {
|
||||||
return FromVal<T>(t->data[index++]);
|
return FromVal<T>(t->data[index++]);
|
||||||
}
|
}
|
||||||
|
|
||||||
template <class R, class... Args>
|
template <class R, class... Args>
|
||||||
static wasm_func_t* CreateFunc2(wasm_store_t* store, WebAssemblyScriptResolver* resolver,
|
static wasm_func_t* CreateFunc(WebAssemblyScriptResolver* resolver,
|
||||||
std::function<R(WebAssemblyScriptResolver*, Args...)> func) {
|
R (*func)(WebAssemblyScriptResolver*, Args...)) {
|
||||||
auto funcType = GetFuncType<R, Args...>();
|
auto funcType = GetFuncType<R, Args...>();
|
||||||
struct Env {
|
struct Env {
|
||||||
WebAssemblyScriptResolver* Resolver;
|
WebAssemblyScriptResolver* Resolver;
|
||||||
std::function<R(WebAssemblyScriptResolver*, Args...)> Func;
|
R (*Func)(WebAssemblyScriptResolver*, Args...);
|
||||||
~Env() {}
|
~Env() {}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -86,13 +77,19 @@ public:
|
||||||
new (env) Env{.Resolver = resolver, .Func = func};
|
new (env) Env{.Resolver = resolver, .Func = func};
|
||||||
resolver->Temp_WasmerBug2_2_1_Bypass.Append(env);
|
resolver->Temp_WasmerBug2_2_1_Bypass.Append(env);
|
||||||
auto* f = wasm_func_new_with_env(
|
auto* f = wasm_func_new_with_env(
|
||||||
store, funcType,
|
resolver->GetStore(), funcType,
|
||||||
[](void* env, const wasm_val_vec_t* parameters, wasm_val_vec_t* results) -> wasm_trap_t* {
|
[](void* env, const wasm_val_vec_t* parameters, wasm_val_vec_t* results) -> wasm_trap_t* {
|
||||||
auto e = *(Env*)env;
|
auto e = *(Env*)env;
|
||||||
size_t index = 0;
|
size_t index = 0;
|
||||||
try {
|
try {
|
||||||
R result = e.Func(e.Resolver, ConvertAllArguments<Args>(parameters, index)...);
|
if constexpr (std::is_void<R>()) {
|
||||||
results->data[0] = ToVal<R>(result);
|
e.Func(e.Resolver, ConvertAllArguments<Args>(parameters, index)...);
|
||||||
|
} else if constexpr (std::is_same<R, wasm_trap_t*>()) {
|
||||||
|
return e.Func(e.Resolver, ConvertAllArguments<Args>(parameters, index)...);
|
||||||
|
} else {
|
||||||
|
R result = e.Func(e.Resolver, ConvertAllArguments<Args>(parameters, index)...);
|
||||||
|
results->data[0] = ToVal<R>(result);
|
||||||
|
}
|
||||||
} catch (ArbUt::Exception& exception) {
|
} catch (ArbUt::Exception& exception) {
|
||||||
return CreateTrapFromException(exception, e.Resolver);
|
return CreateTrapFromException(exception, e.Resolver);
|
||||||
} catch (std::exception& exception) {
|
} catch (std::exception& exception) {
|
||||||
|
@ -117,10 +114,16 @@ private:
|
||||||
} else {
|
} else {
|
||||||
return wasm_valtype_new_i32();
|
return wasm_valtype_new_i32();
|
||||||
}
|
}
|
||||||
|
} else if constexpr (std::is_floating_point<T>()) {
|
||||||
|
if constexpr (sizeof(T) > 4) {
|
||||||
|
return wasm_valtype_new_f64();
|
||||||
|
} else {
|
||||||
|
return wasm_valtype_new_f32();
|
||||||
|
}
|
||||||
} else if constexpr (std::is_same<T, const ArbUt::StringView&>()) {
|
} else if constexpr (std::is_same<T, const ArbUt::StringView&>()) {
|
||||||
return wasm_valtype_new_i64();
|
return wasm_valtype_new_i64();
|
||||||
}
|
}
|
||||||
THROW("Unhandled value type: ", typeid(T).name());
|
THROW("Unhandled value type: ", std::string(typeid(T).name()));
|
||||||
}
|
}
|
||||||
|
|
||||||
template <typename T> inline static wasm_val_t ToVal(const T& val) {
|
template <typename T> inline static wasm_val_t ToVal(const T& val) {
|
||||||
|
@ -138,6 +141,12 @@ private:
|
||||||
} else {
|
} else {
|
||||||
return WASM_I32_VAL((i32)val);
|
return WASM_I32_VAL((i32)val);
|
||||||
}
|
}
|
||||||
|
} else if constexpr (std::is_floating_point<T>()) {
|
||||||
|
if constexpr (sizeof(T) > 4) {
|
||||||
|
return WASM_F64_VAL((f64)val);
|
||||||
|
} else {
|
||||||
|
return WASM_F32_VAL((f32)val);
|
||||||
|
}
|
||||||
} else if constexpr (std::is_same<T, const ArbUt::StringView&>()) {
|
} else if constexpr (std::is_same<T, const ArbUt::StringView&>()) {
|
||||||
auto v = &val;
|
auto v = &val;
|
||||||
return WASM_I64_VAL(reinterpret_cast<i64>(v));
|
return WASM_I64_VAL(reinterpret_cast<i64>(v));
|
||||||
|
@ -156,9 +165,15 @@ private:
|
||||||
return dynamic_cast<T>(reinterpret_cast<void*>(val.of.i64));
|
return dynamic_cast<T>(reinterpret_cast<void*>(val.of.i64));
|
||||||
} else if constexpr (std::is_enum<T>() || std::is_integral<T>()) {
|
} else if constexpr (std::is_enum<T>() || std::is_integral<T>()) {
|
||||||
if constexpr (sizeof(T) > 4) {
|
if constexpr (sizeof(T) > 4) {
|
||||||
return reinterpret_cast<T>(val.of.i64);
|
return static_cast<T>(val.of.i64);
|
||||||
} else {
|
} else {
|
||||||
return reinterpret_cast<T>(val.of.i32);
|
return static_cast<T>(val.of.i32);
|
||||||
|
}
|
||||||
|
} else if constexpr (std::is_floating_point<T>()) {
|
||||||
|
if constexpr (sizeof(T) > 4) {
|
||||||
|
return static_cast<T>(val.of.f64);
|
||||||
|
} else {
|
||||||
|
return static_cast<T>(val.of.f32);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
THROW("Unhandled value type: ", typeid(T).name());
|
THROW("Unhandled value type: ", typeid(T).name());
|
||||||
|
@ -177,7 +192,7 @@ private:
|
||||||
AppendArgument<0, Args...>(ps);
|
AppendArgument<0, Args...>(ps);
|
||||||
|
|
||||||
wasm_valtype_vec_t params, results;
|
wasm_valtype_vec_t params, results;
|
||||||
if constexpr (std::is_void<R>()) {
|
if constexpr (std::is_void<R>() || std::is_same<R, wasm_trap_t*>()) {
|
||||||
results = WASM_EMPTY_VEC;
|
results = WASM_EMPTY_VEC;
|
||||||
} else {
|
} else {
|
||||||
wasm_valtype_t* rs[1] = {GetValType<R>()};
|
wasm_valtype_t* rs[1] = {GetValType<R>()};
|
||||||
|
@ -188,10 +203,10 @@ private:
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
#define REGISTER_GETTER(name, cType, cFunc, store, resolver) \
|
#define REGISTER_GETTER(name, cType, cFunc, resolver) \
|
||||||
externs.Insert( \
|
externs.Insert( \
|
||||||
name, \
|
name, \
|
||||||
WasmHelpers::RegisterGetter<cType, std::result_of<decltype (&cType::cFunc)(cType)>::type, &cType::cFunc>( \
|
WasmHelpers::RegisterGetter<cType, std::result_of<decltype (&cType::cFunc)(cType)>::type, &cType::cFunc>( \
|
||||||
store, resolver));
|
resolver));
|
||||||
|
|
||||||
#endif // PKMNLIB_HELPERFILE_H
|
#endif // PKMNLIB_HELPERFILE_H
|
|
@ -0,0 +1,28 @@
|
||||||
|
#include "WASMStringView.hpp"
|
||||||
|
#include "WASMHelperFile.hpp"
|
||||||
|
|
||||||
|
wasm_func_t* ConstString_GetHash(WebAssemblyScriptResolver* resolver) {
|
||||||
|
return WasmHelpers::CreateFunc<u32, const ArbUt::StringView*>(
|
||||||
|
resolver, {[](WebAssemblyScriptResolver*, const ArbUt::StringView* sv) -> u32 { return sv->GetHash(); }});
|
||||||
|
}
|
||||||
|
|
||||||
|
wasm_func_t* ConstString_GetStr(WebAssemblyScriptResolver* resolver) {
|
||||||
|
return WasmHelpers::CreateFunc<i32, const ArbUt::StringView*>(
|
||||||
|
resolver, {[](WebAssemblyScriptResolver* resolver, const ArbUt::StringView* constString) -> i32 {
|
||||||
|
// To allow webassembly to access the C String, we need to allocate it inside it's memory.
|
||||||
|
// Length + 1 to make room for the '\0'
|
||||||
|
auto stringPointer = resolver->AllocateMemory(constString->Length() + 1, std::alignment_of<const char>());
|
||||||
|
|
||||||
|
// After we have the pointer to the memory allocated for the string, copy the string with specified length
|
||||||
|
// to it, then suffix it with the null byte to end it.
|
||||||
|
strncpy(reinterpret_cast<char*>(stringPointer.first), constString->c_str(), constString->Length());
|
||||||
|
stringPointer.first[constString->Length()] = '\0';
|
||||||
|
return stringPointer.second;
|
||||||
|
}});
|
||||||
|
}
|
||||||
|
|
||||||
|
void WASMStringView::Register(ArbUt::Dictionary<std::string, wasm_func_t*>& externs,
|
||||||
|
WebAssemblyScriptResolver* resolver) {
|
||||||
|
externs.Insert("arbutils_const_string_get_hash", ConstString_GetHash(resolver));
|
||||||
|
externs.Insert("arbutils_const_string_get_str", ConstString_GetStr(resolver));
|
||||||
|
}
|
|
@ -0,0 +1,10 @@
|
||||||
|
#ifndef PKMNLIB_WASMSTRINGVIEW_HPP
|
||||||
|
#define PKMNLIB_WASMSTRINGVIEW_HPP
|
||||||
|
#include "../WebAssemblyScriptResolver.hpp"
|
||||||
|
|
||||||
|
class WASMStringView {
|
||||||
|
public:
|
||||||
|
static void Register(ArbUt::Dictionary<std::string, wasm_func_t*>& externs, WebAssemblyScriptResolver* resolver);
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif // PKMNLIB_WASMSTRINGVIEW_HPP
|
Binary file not shown.
|
@ -0,0 +1,111 @@
|
||||||
|
// This file documents the entire interface API currently used by the WebAssembly script resolver.
|
||||||
|
// Currently, we only define a bunch of functions, but in the future when interface types are actually implemented,
|
||||||
|
// we'd like to implement those as well.
|
||||||
|
|
||||||
|
// Core functions
|
||||||
|
// These are the core utility functions for use.
|
||||||
|
// _error can be used for crash handling in the script handler. It takes a message string, file name string, line and position.
|
||||||
|
_error: function(i32 message_pointer, s32 message_length, i32 file_pointer, i32 file_length, i32 line, i32 position)
|
||||||
|
// _print can be used to print a message to the hosts stdout
|
||||||
|
_print: function(i32 message_pointer, s32 message_length)
|
||||||
|
|
||||||
|
// StringView class
|
||||||
|
type const_string = u64;
|
||||||
|
arbutils_const_string_get_hash: function(const_string ptr) -> u32
|
||||||
|
// Returns a pointer to the WASM memory where the string can be found.
|
||||||
|
// NOTE: This requires us to copy the string into WASM memory.
|
||||||
|
arbutils_const_string_get_str: function(const_string ptr) -> s32
|
||||||
|
|
||||||
|
// Library types
|
||||||
|
type pokemon_library = u64
|
||||||
|
type library_settings = u64
|
||||||
|
type species_library = u64
|
||||||
|
type move_library = u64
|
||||||
|
type item_library = u64
|
||||||
|
type growth_rate_library = u64
|
||||||
|
type type_library = u64
|
||||||
|
type talent_library = u64
|
||||||
|
type nature_library = u64
|
||||||
|
|
||||||
|
type level_int = u8
|
||||||
|
|
||||||
|
type species = u64
|
||||||
|
type move = u64
|
||||||
|
type item = u64
|
||||||
|
type nature = u64
|
||||||
|
|
||||||
|
enum Statistic {
|
||||||
|
Health,
|
||||||
|
Attack,
|
||||||
|
Defense
|
||||||
|
SpecialAttack,
|
||||||
|
SpecialDefense,
|
||||||
|
Speed,
|
||||||
|
}
|
||||||
|
|
||||||
|
// PokemonLibrary class
|
||||||
|
data_library_get_settings: function(pokemon_library ptr) -> library_settings
|
||||||
|
data_library_get_species_library: function(pokemon_library ptr) -> species_library
|
||||||
|
data_library_get_move_library: function(pokemon_library ptr) -> move_library
|
||||||
|
data_library_get_item_library: function(pokemon_library ptr) -> item_library
|
||||||
|
data_library_get_growth_rates: function(pokemon_library ptr) -> growth_rate_library
|
||||||
|
data_library_get_type_library: function(pokemon_library ptr) -> type_library
|
||||||
|
data_library_get_talent_library: function(pokemon_library ptr) -> talent_library
|
||||||
|
data_library_get_nature_library: function(pokemon_library ptr) -> nature_library
|
||||||
|
|
||||||
|
// LibrarySettings class
|
||||||
|
library_settings_get_max_level: function(library_settings ptr) -> level_int
|
||||||
|
library_settings_get_max_moves: function(library_settings ptr) -> u8
|
||||||
|
library_settings_get_shiny_rate: function(library_settings ptr) -> u16
|
||||||
|
|
||||||
|
// SpeciesLibrary class
|
||||||
|
species_library_get_species_by_hash: function(species_library library, u32 hash) -> species
|
||||||
|
|
||||||
|
// MoveLibrary class
|
||||||
|
move_library_get_move_by_hash: function(move_library library, u32 hash) -> move
|
||||||
|
|
||||||
|
// ItemLibrary class
|
||||||
|
item_library_get_item_by_hash: function(item_library library, u32 hash) -> item
|
||||||
|
|
||||||
|
// GrowthRateLibrary class
|
||||||
|
growthrate_library_calculate_level_by_hash: function(growth_rate_library library, u32 hash, u32 experience) -> level_int
|
||||||
|
growthrate_library_calculate_experience_by_hash: function(growth_rate_library library, u32 hash, level_int level) -> u32
|
||||||
|
|
||||||
|
// TypeLibrary class
|
||||||
|
type_library_get_type_id_by_hash: function(type_library, u32 hash) -> u8
|
||||||
|
type_library_get_single_effectiveness: function(type_library, u8 attacking, u8 offensive) -> f32
|
||||||
|
type_library_get_type_name: function(type_library, u8 type) -> const_string
|
||||||
|
|
||||||
|
// NatureLibrary class
|
||||||
|
nature_library_get_nature_by_hash: function(nature_library, u32 hash) -> nature
|
||||||
|
nature_library_get_nature_name: function(nature_library, nature) -> const_string
|
||||||
|
|
||||||
|
// Nature class
|
||||||
|
nature_get_increased_modifier: function(nature) -> f32
|
||||||
|
nature_get_decreased_modifier: function(nature) -> f32
|
||||||
|
nature_get_increased_stat: function(nature) -> Statistic
|
||||||
|
nature_get_decreased_stat: function(nature) -> Statistic
|
||||||
|
|
||||||
|
// MoveData class
|
||||||
|
enum MoveCategory {
|
||||||
|
Physical, Special, Status,
|
||||||
|
}
|
||||||
|
enum MoveTarget {
|
||||||
|
Adjacent, AdjacentAlly, AdjacentAllySelf, AdjacentOpponent,
|
||||||
|
All, AllAdjacent, AllAdjacentOpponent, AllAlly, AllOpponent,
|
||||||
|
Any,
|
||||||
|
RandomOpponent, Self
|
||||||
|
}
|
||||||
|
|
||||||
|
move_data_get_name: function(move) -> const_string
|
||||||
|
move_data_get_type: function(move) -> u8
|
||||||
|
move_data_get_category: function(move) -> MoveCategory
|
||||||
|
move_data_get_base_power: function(move) -> u8
|
||||||
|
move_data_get_accuracy: function(move) -> u8
|
||||||
|
move_data_get_base_usages: function(move) -> u8
|
||||||
|
move_data_get_target: function(move) -> MoveTarget
|
||||||
|
move_data_get_priority: function(move) -> s8
|
||||||
|
move_data_has_secondary_effect: function(move) -> bool
|
||||||
|
move_data_has_flag_by_hash: function(move, u32 hash) -> bool
|
||||||
|
|
||||||
|
|
|
@ -2,8 +2,7 @@
|
||||||
#include <iostream>
|
#include <iostream>
|
||||||
#include <unordered_map>
|
#include <unordered_map>
|
||||||
#include <wasmer.h>
|
#include <wasmer.h>
|
||||||
#include "InterfaceMethods/CoreMethods.hpp"
|
#include "InterfaceMethods/TypeRegistry.hpp"
|
||||||
#include "InterfaceMethods/Library/LibraryMethods.hpp"
|
|
||||||
#include "WebAssemblyBattleScript.hpp"
|
#include "WebAssemblyBattleScript.hpp"
|
||||||
#include "WebAssemblyFunctionCall.hpp"
|
#include "WebAssemblyFunctionCall.hpp"
|
||||||
#include "wasm.h"
|
#include "wasm.h"
|
||||||
|
@ -80,10 +79,7 @@ u8 WebAssemblyScriptResolver::LoadWatFromString(const std::string& data) {
|
||||||
|
|
||||||
void WebAssemblyScriptResolver::RegisterFunction() {}
|
void WebAssemblyScriptResolver::RegisterFunction() {}
|
||||||
|
|
||||||
void WebAssemblyScriptResolver::RegisterDefaultMethods() {
|
void WebAssemblyScriptResolver::RegisterDefaultMethods() { TypeRegistry::Register(_imports, this); }
|
||||||
WebAssemblyCoreMethods::Register(_store, _imports, this);
|
|
||||||
LibraryMethods::Register(_store, _imports, this);
|
|
||||||
}
|
|
||||||
|
|
||||||
void WebAssemblyScriptResolver::Finalize() {
|
void WebAssemblyScriptResolver::Finalize() {
|
||||||
RegisterDefaultMethods();
|
RegisterDefaultMethods();
|
||||||
|
|
Binary file not shown.
|
@ -4,7 +4,7 @@
|
||||||
PkmnLib::Battling::BattleLibrary* TestLibrary::_library = nullptr;
|
PkmnLib::Battling::BattleLibrary* TestLibrary::_library = nullptr;
|
||||||
PkmnLib::Library::SpeciesLibrary* TestLibrary::BuildSpeciesLibrary(CreatureLib::Library::TalentLibrary* talentLibrary) {
|
PkmnLib::Library::SpeciesLibrary* TestLibrary::BuildSpeciesLibrary(CreatureLib::Library::TalentLibrary* talentLibrary) {
|
||||||
auto lib = new PkmnLib::Library::SpeciesLibrary();
|
auto lib = new PkmnLib::Library::SpeciesLibrary();
|
||||||
lib->Insert("testSpecies"_cnc.GetHash(),
|
lib->Insert("testSpecies"_cnc,
|
||||||
new PkmnLib::Library::PokemonSpecies(
|
new PkmnLib::Library::PokemonSpecies(
|
||||||
1, "testSpecies"_cnc,
|
1, "testSpecies"_cnc,
|
||||||
new PkmnLib::Library::PokemonForme(
|
new PkmnLib::Library::PokemonForme(
|
||||||
|
@ -13,7 +13,7 @@ PkmnLib::Library::SpeciesLibrary* TestLibrary::BuildSpeciesLibrary(CreatureLib::
|
||||||
{talentLibrary->Get("testAbility"_cnc)}, {talentLibrary->Get("testHiddenAbility"_cnc)},
|
{talentLibrary->Get("testAbility"_cnc)}, {talentLibrary->Get("testHiddenAbility"_cnc)},
|
||||||
new PkmnLib::Library::LearnableMoves(100)),
|
new PkmnLib::Library::LearnableMoves(100)),
|
||||||
0.5f, "testGrowthRate"_cnc, 100, 100, {"testEggGroup"_cnc}));
|
0.5f, "testGrowthRate"_cnc, 100, 100, {"testEggGroup"_cnc}));
|
||||||
lib->Insert("testSpecies2"_cnc.GetHash(),
|
lib->Insert("testSpecies2"_cnc,
|
||||||
new PkmnLib::Library::PokemonSpecies(
|
new PkmnLib::Library::PokemonSpecies(
|
||||||
2, "testSpecies2"_cnc,
|
2, "testSpecies2"_cnc,
|
||||||
new PkmnLib::Library::PokemonForme(
|
new PkmnLib::Library::PokemonForme(
|
||||||
|
@ -22,7 +22,7 @@ PkmnLib::Library::SpeciesLibrary* TestLibrary::BuildSpeciesLibrary(CreatureLib::
|
||||||
{talentLibrary->Get("testAbility"_cnc)}, {talentLibrary->Get("testHiddenAbility"_cnc)},
|
{talentLibrary->Get("testAbility"_cnc)}, {talentLibrary->Get("testHiddenAbility"_cnc)},
|
||||||
new PkmnLib::Library::LearnableMoves(100)),
|
new PkmnLib::Library::LearnableMoves(100)),
|
||||||
0.5f, "testGrowthRate"_cnc, 100, 100, {"testEggGroup"_cnc}));
|
0.5f, "testGrowthRate"_cnc, 100, 100, {"testEggGroup"_cnc}));
|
||||||
lib->Insert("statTestSpecies1"_cnc.GetHash(),
|
lib->Insert("statTestSpecies1"_cnc,
|
||||||
new PkmnLib::Library::PokemonSpecies(
|
new PkmnLib::Library::PokemonSpecies(
|
||||||
3, "statTestSpecies1"_cnc,
|
3, "statTestSpecies1"_cnc,
|
||||||
new PkmnLib::Library::PokemonForme(
|
new PkmnLib::Library::PokemonForme(
|
||||||
|
@ -31,7 +31,7 @@ PkmnLib::Library::SpeciesLibrary* TestLibrary::BuildSpeciesLibrary(CreatureLib::
|
||||||
{talentLibrary->Get("testAbility"_cnc)}, {talentLibrary->Get("testHiddenAbility"_cnc)},
|
{talentLibrary->Get("testAbility"_cnc)}, {talentLibrary->Get("testHiddenAbility"_cnc)},
|
||||||
new PkmnLib::Library::LearnableMoves(100)),
|
new PkmnLib::Library::LearnableMoves(100)),
|
||||||
0.5f, "testGrowthRate"_cnc, 100, 100, {"testEggGroup"_cnc}));
|
0.5f, "testGrowthRate"_cnc, 100, 100, {"testEggGroup"_cnc}));
|
||||||
lib->Insert("testSpecies3"_cnc.GetHash(),
|
lib->Insert("testSpecies3"_cnc,
|
||||||
new PkmnLib::Library::PokemonSpecies(
|
new PkmnLib::Library::PokemonSpecies(
|
||||||
4, "testSpecies3"_cnc,
|
4, "testSpecies3"_cnc,
|
||||||
new PkmnLib::Library::PokemonForme(
|
new PkmnLib::Library::PokemonForme(
|
||||||
|
@ -41,7 +41,7 @@ PkmnLib::Library::SpeciesLibrary* TestLibrary::BuildSpeciesLibrary(CreatureLib::
|
||||||
new PkmnLib::Library::LearnableMoves(100)),
|
new PkmnLib::Library::LearnableMoves(100)),
|
||||||
0.5f, "testGrowthRate"_cnc, 100, 100, {"testEggGroup"_cnc}));
|
0.5f, "testGrowthRate"_cnc, 100, 100, {"testEggGroup"_cnc}));
|
||||||
|
|
||||||
lib->Insert("testCharizard"_cnc.GetHash(),
|
lib->Insert("testCharizard"_cnc,
|
||||||
new PkmnLib::Library::PokemonSpecies(
|
new PkmnLib::Library::PokemonSpecies(
|
||||||
5, "testCharizard"_cnc,
|
5, "testCharizard"_cnc,
|
||||||
new PkmnLib::Library::PokemonForme(
|
new PkmnLib::Library::PokemonForme(
|
||||||
|
@ -50,7 +50,7 @@ PkmnLib::Library::SpeciesLibrary* TestLibrary::BuildSpeciesLibrary(CreatureLib::
|
||||||
{talentLibrary->Get("testAbility"_cnc)}, {talentLibrary->Get("testHiddenAbility"_cnc)},
|
{talentLibrary->Get("testAbility"_cnc)}, {talentLibrary->Get("testHiddenAbility"_cnc)},
|
||||||
new PkmnLib::Library::LearnableMoves(100)),
|
new PkmnLib::Library::LearnableMoves(100)),
|
||||||
0.5f, "testGrowthRate"_cnc, 100, 100, {"testEggGroup"_cnc}));
|
0.5f, "testGrowthRate"_cnc, 100, 100, {"testEggGroup"_cnc}));
|
||||||
lib->Insert("testVenusaur"_cnc.GetHash(),
|
lib->Insert("testVenusaur"_cnc,
|
||||||
new PkmnLib::Library::PokemonSpecies(
|
new PkmnLib::Library::PokemonSpecies(
|
||||||
6, "testVenusaur"_cnc,
|
6, "testVenusaur"_cnc,
|
||||||
new PkmnLib::Library::PokemonForme(
|
new PkmnLib::Library::PokemonForme(
|
||||||
|
@ -64,11 +64,11 @@ PkmnLib::Library::SpeciesLibrary* TestLibrary::BuildSpeciesLibrary(CreatureLib::
|
||||||
}
|
}
|
||||||
PkmnLib::Library::MoveLibrary* TestLibrary::BuildMoveLibrary() {
|
PkmnLib::Library::MoveLibrary* TestLibrary::BuildMoveLibrary() {
|
||||||
auto lib = new PkmnLib::Library::MoveLibrary();
|
auto lib = new PkmnLib::Library::MoveLibrary();
|
||||||
lib->Insert("testMove"_cnc.GetHash(),
|
lib->Insert("testMove"_cnc,
|
||||||
new PkmnLib::Library::MoveData("testMove"_cnc, 0, PkmnLib::Library::MoveCategory::Physical, 50, 100, 20,
|
new PkmnLib::Library::MoveData("testMove"_cnc, 0, PkmnLib::Library::MoveCategory::Physical, 50, 100, 20,
|
||||||
CreatureLib::Library::AttackTarget::Adjacent, 0,
|
CreatureLib::Library::AttackTarget::Adjacent, 0,
|
||||||
new CreatureLib::Library::SecondaryEffect(), {}));
|
new CreatureLib::Library::SecondaryEffect(), {}));
|
||||||
lib->Insert("testMove2"_cnc.GetHash(),
|
lib->Insert("testMove2"_cnc,
|
||||||
new PkmnLib::Library::MoveData("testMove2"_cnc, 0, PkmnLib::Library::MoveCategory::Special, 30, 100, 10,
|
new PkmnLib::Library::MoveData("testMove2"_cnc, 0, PkmnLib::Library::MoveCategory::Special, 30, 100, 10,
|
||||||
CreatureLib::Library::AttackTarget::Adjacent, 0,
|
CreatureLib::Library::AttackTarget::Adjacent, 0,
|
||||||
new CreatureLib::Library::SecondaryEffect(), {}));
|
new CreatureLib::Library::SecondaryEffect(), {}));
|
||||||
|
@ -76,7 +76,7 @@ PkmnLib::Library::MoveLibrary* TestLibrary::BuildMoveLibrary() {
|
||||||
}
|
}
|
||||||
PkmnLib::Library::ItemLibrary* TestLibrary::BuildItemLibrary() {
|
PkmnLib::Library::ItemLibrary* TestLibrary::BuildItemLibrary() {
|
||||||
auto lib = new PkmnLib::Library::ItemLibrary();
|
auto lib = new PkmnLib::Library::ItemLibrary();
|
||||||
lib->Insert("testItem"_cnc.GetHash(),
|
lib->Insert("testItem"_cnc,
|
||||||
new PkmnLib::Library::Item("testItem"_cnc, CreatureLib::Library::ItemCategory::MiscItem,
|
new PkmnLib::Library::Item("testItem"_cnc, CreatureLib::Library::ItemCategory::MiscItem,
|
||||||
CreatureLib::Library::BattleItemCategory::None, 0, nullptr, nullptr, {}, 0));
|
CreatureLib::Library::BattleItemCategory::None, 0, nullptr, nullptr, {}, 0));
|
||||||
return lib;
|
return lib;
|
||||||
|
|
Loading…
Reference in New Issue