| Line | Branch | Exec | Source |
|---|---|---|---|
| 1 | // Copyright Contributors to the OpenVDB Project | ||
| 2 | // SPDX-License-Identifier: MPL-2.0 | ||
| 3 | |||
| 4 | /// @file codegen/FunctionRegistry.h | ||
| 5 | /// | ||
| 6 | /// @authors Nick Avramoussis | ||
| 7 | /// | ||
| 8 | /// @brief Contains the global function registration definition which | ||
| 9 | /// described all available user front end functions | ||
| 10 | /// | ||
| 11 | |||
| 12 | #ifndef OPENVDB_AX_CODEGEN_FUNCTION_REGISTRY_HAS_BEEN_INCLUDED | ||
| 13 | #define OPENVDB_AX_CODEGEN_FUNCTION_REGISTRY_HAS_BEEN_INCLUDED | ||
| 14 | |||
| 15 | #include "FunctionTypes.h" | ||
| 16 | |||
| 17 | #include "openvdb_ax/compiler/CompilerOptions.h" | ||
| 18 | |||
| 19 | #include <openvdb/version.h> | ||
| 20 | |||
| 21 | #include <unordered_map> | ||
| 22 | |||
| 23 | namespace openvdb { | ||
| 24 | OPENVDB_USE_VERSION_NAMESPACE | ||
| 25 | namespace OPENVDB_VERSION_NAME { | ||
| 26 | |||
| 27 | namespace ax { | ||
| 28 | namespace codegen { | ||
| 29 | |||
| 30 | /// @brief The function registry which is used for function code generation. | ||
| 31 | /// Each time a function is visited within the AST, its identifier is used as | ||
| 32 | /// a key into this registry for the corresponding function retrieval and | ||
| 33 | /// execution. Functions can be inserted into the registry using insert() with | ||
| 34 | /// a given identifier and pointer. | ||
| 35 | 1488 | class OPENVDB_AX_API FunctionRegistry | |
| 36 | { | ||
| 37 | public: | ||
| 38 | using ConstructorT = FunctionGroup::UniquePtr(*)(const FunctionOptions&); | ||
| 39 | using Ptr = std::shared_ptr<FunctionRegistry>; | ||
| 40 | using UniquePtr = std::unique_ptr<FunctionRegistry>; | ||
| 41 | |||
| 42 | /// @brief An object to represent a registered function, storing its | ||
| 43 | /// constructor, a pointer to the function definition and whether it | ||
| 44 | /// should only be available internally (i.e. to a developer, not a user) | ||
| 45 | /// | ||
| 46 | struct RegisteredFunction | ||
| 47 | { | ||
| 48 | /// @brief Constructor | ||
| 49 | /// @param creator The function definition used to create this function | ||
| 50 | /// @param internal Whether the function should be only internally accessible | ||
| 51 | RegisteredFunction(const ConstructorT& creator, const bool internal = false) | ||
| 52 | 157537 | : mConstructor(creator), mFunction(), mInternal(internal) {} | |
| 53 | |||
| 54 | /// @brief Create a function object using this creator of this function | ||
| 55 | /// @param op The current function options | ||
| 56 | 11418 | inline void create(const FunctionOptions& op) { mFunction = mConstructor(op); } | |
| 57 | |||
| 58 | /// @brief Return a pointer to this function definition | ||
| 59 | inline const FunctionGroup* function() const { return mFunction.get(); } | ||
| 60 | |||
| 61 | /// @brief Check whether this function should be only internally accesible | ||
| 62 |
4/4✓ Branch 0 taken 4 times.
✓ Branch 1 taken 4 times.
✓ Branch 2 taken 5266 times.
✓ Branch 3 taken 5 times.
|
5279 | inline bool isInternal() const { return mInternal; } |
| 63 | |||
| 64 | private: | ||
| 65 | ConstructorT mConstructor; | ||
| 66 | FunctionGroup::Ptr mFunction; | ||
| 67 | bool mInternal; | ||
| 68 | }; | ||
| 69 | |||
| 70 | using RegistryMap = std::unordered_map<std::string, RegisteredFunction>; | ||
| 71 | |||
| 72 | /// @brief Insert and register a function object to a function identifier. | ||
| 73 | /// @note Throws if the identifier is already registered | ||
| 74 | /// | ||
| 75 | /// @param identifier The function identifier to register | ||
| 76 | /// @param creator The function to link to the provided identifier | ||
| 77 | /// @param internal Whether to mark the function as only internally accessible | ||
| 78 | void insert(const std::string& identifier, | ||
| 79 | const ConstructorT creator, | ||
| 80 | const bool internal = false); | ||
| 81 | |||
| 82 | /// @brief Insert and register a function object to a function identifier. | ||
| 83 | /// @note Throws if the identifier is already registered | ||
| 84 | /// | ||
| 85 | /// @param identifier The function identifier to register | ||
| 86 | /// @param creator The function to link to the provided identifier | ||
| 87 | /// @param op FunctionOptions to pass the function constructor | ||
| 88 | /// @param internal Whether to mark the function as only internally accessible | ||
| 89 | void insertAndCreate(const std::string& identifier, | ||
| 90 | const ConstructorT creator, | ||
| 91 | const FunctionOptions& op, | ||
| 92 | const bool internal = false); | ||
| 93 | |||
| 94 | /// @brief Return the corresponding function from a provided function identifier | ||
| 95 | /// @note Returns a nullptr if no such function identifier has been | ||
| 96 | /// registered or if the function is marked as internal | ||
| 97 | /// | ||
| 98 | /// @param identifier The function identifier | ||
| 99 | /// @param op FunctionOptions to pass the function constructor | ||
| 100 | /// @param allowInternalAccess Whether to look in the 'internal' functions | ||
| 101 | const FunctionGroup* getOrInsert(const std::string& identifier, | ||
| 102 | const FunctionOptions& op, | ||
| 103 | const bool allowInternalAccess); | ||
| 104 | |||
| 105 | /// @brief Return the corresponding function from a provided function identifier | ||
| 106 | /// @note Returns a nullptr if no such function identifier has been | ||
| 107 | /// registered or if the function is marked as internal | ||
| 108 | /// | ||
| 109 | /// @param identifier The function identifier | ||
| 110 | /// @param allowInternalAccess Whether to look in the 'internal' functions | ||
| 111 | const FunctionGroup* get(const std::string& identifier, | ||
| 112 | const bool allowInternalAccess) const; | ||
| 113 | |||
| 114 | /// @brief Force the (re)creations of all function objects for all | ||
| 115 | /// registered functions | ||
| 116 | /// @param op The current function options | ||
| 117 | /// @param verify Checks functions are created and have valid identifiers/symbols | ||
| 118 | void createAll(const FunctionOptions& op, const bool verify = false); | ||
| 119 | |||
| 120 | /// @brief Return a const reference to the current registry map | ||
| 121 | inline const RegistryMap& map() const { return mMap; } | ||
| 122 | |||
| 123 | /// @brief Return whether or not the registry is empty | ||
| 124 | inline bool empty() const { return mMap.empty(); } | ||
| 125 | |||
| 126 | /// @brief Clear the underlying function registry | ||
| 127 | inline void clear() { mMap.clear(); } | ||
| 128 | |||
| 129 | private: | ||
| 130 | RegistryMap mMap; | ||
| 131 | }; | ||
| 132 | |||
| 133 | } // namespace codegen | ||
| 134 | } // namespace ax | ||
| 135 | } // namespace OPENVDB_VERSION_NAME | ||
| 136 | } // namespace openvdb | ||
| 137 | |||
| 138 | #endif // OPENVDB_AX_CODEGEN_FUNCTION_REGISTRY_HAS_BEEN_INCLUDED | ||
| 139 | |||
| 140 |