diff --git a/src/binding/julia/Attributable.cpp b/src/binding/julia/Attributable.cpp index 5ae68f764d..3762f20880 100644 --- a/src/binding/julia/Attributable.cpp +++ b/src/binding/julia/Attributable.cpp @@ -6,15 +6,26 @@ #include "defs.hpp" +namespace +{ +struct UseType +{ + template + static void call(jlcxx::TypeWrapper type) + { + type.method( + "cxx_set_attribute_" + datatypeToString(determineDatatype()) + + "!", + &Attributable::setAttribute); + } +}; +} // namespace + void define_julia_Attributable(jlcxx::Module &mod) { auto type = mod.add_type("CXX_Attributable"); -#define USE_TYPE(NAME, ENUM, TYPE) \ - type.method( \ - "cxx_set_attribute_" NAME "!", &Attributable::setAttribute); - {FORALL_OPENPMD_TYPES(USE_TYPE)} -#undef USE_TYPE + forallJuliaTypes(type); type.method("cxx_get_attribute", &Attributable::getAttribute); type.method("cxx_delete_attribute!", &Attributable::deleteAttribute); diff --git a/src/binding/julia/Attribute.cpp b/src/binding/julia/Attribute.cpp index cacda12faf..6e13b6efe2 100644 --- a/src/binding/julia/Attribute.cpp +++ b/src/binding/julia/Attribute.cpp @@ -6,16 +6,25 @@ #include "defs.hpp" +namespace +{ +struct UseType +{ + template + static void call(jlcxx::TypeWrapper type) + { + type.method( + "cxx_get_" + datatypeToString(determineDatatype()), + &Attribute::get); + } +}; +} // namespace + void define_julia_Attribute(jlcxx::Module &mod) { auto type = mod.add_type("CXX_Attribute"); type.method("cxx_dtype", [](const Attribute &attr) { return attr.dtype; }); -#define USE_TYPE(NAME, ENUM, TYPE) \ - type.method("cxx_get_" NAME, &Attribute::get); - { - FORALL_OPENPMD_TYPES(USE_TYPE) - } -#undef USE_TYPE + forallJuliaTypes(type); } diff --git a/src/binding/julia/BaseRecordComponent.cpp b/src/binding/julia/BaseRecordComponent.cpp index e2ddda708e..4ffd41a277 100644 --- a/src/binding/julia/BaseRecordComponent.cpp +++ b/src/binding/julia/BaseRecordComponent.cpp @@ -12,7 +12,7 @@ namespace jlcxx template <> struct SuperType { - typedef Attributable type; + using type = Attributable; }; } // namespace jlcxx diff --git a/src/binding/julia/ChunkInfo.cpp b/src/binding/julia/ChunkInfo.cpp index 322fb996b0..2b396652c7 100644 --- a/src/binding/julia/ChunkInfo.cpp +++ b/src/binding/julia/ChunkInfo.cpp @@ -12,7 +12,7 @@ namespace jlcxx template <> struct SuperType { - typedef ChunkInfo type; + using type = ChunkInfo; }; } // namespace jlcxx diff --git a/src/binding/julia/Container.hpp b/src/binding/julia/Container.hpp index ba973bafc0..70db8749b4 100644 --- a/src/binding/julia/Container.hpp +++ b/src/binding/julia/Container.hpp @@ -20,14 +20,13 @@ namespace jlcxx template struct SuperType> { - typedef Attributable type; + using type = Attributable; }; } // namespace jlcxx +using julia_Container_type_t = + jlcxx::TypeWrapper, jlcxx::TypeVar<2>>>; // TODO: use std::optional instead of std::unique_ptr -typedef jlcxx::TypeWrapper< - jlcxx::Parametric, jlcxx::TypeVar<2>>> - julia_Container_type_t; extern std::unique_ptr julia_Container_type; template @@ -43,7 +42,6 @@ void define_julia_Container(jlcxx::Module &mod) using ContainerT = typename decltype(type)::type; using key_type = typename ContainerT::key_type; using mapped_type = typename ContainerT::mapped_type; - using size_type = typename ContainerT::size_type; static_assert(std::is_same_v); static_assert(std::is_same_v); @@ -69,9 +67,7 @@ void define_julia_Container(jlcxx::Module &mod) type.method("cxx_count", &ContainerT::count); type.method("cxx_contains", &ContainerT::contains); type.method( - "cxx_delete!", - static_cast( - &ContainerT::erase)); + "cxx_delete!", overload_cast(&ContainerT::erase)); type.method("cxx_keys", [](const ContainerT &cont) { std::vector res; res.reserve(cont.size()); diff --git a/src/binding/julia/Datatype.cpp b/src/binding/julia/Datatype.cpp index ce3fe6212f..47dcc21442 100644 --- a/src/binding/julia/Datatype.cpp +++ b/src/binding/julia/Datatype.cpp @@ -6,14 +6,26 @@ #include "defs.hpp" +namespace +{ +struct UseType +{ + template + static void call(jlcxx::Module &mod) + { + Datatype const dt = determineDatatype(); + mod.set_const(datatypeToString(dt), dt); + } +}; +} // namespace + void define_julia_Datatype(jlcxx::Module &mod) { mod.add_bits("Datatype", jlcxx::julia_type("CppEnum")); jlcxx::stl::apply_stl(mod); -#define USE_TYPE(NAME, ENUM, TYPE) mod.set_const(NAME, ENUM); - {FORALL_OPENPMD_TYPES(USE_TYPE)} -#undef USE_TYPE + forallJuliaTypes(mod); + mod.set_const("UNDEFINED", Datatype::UNDEFINED); mod.set_const("openPMD_datatypes", openPMD_Datatypes); diff --git a/src/binding/julia/Iteration.cpp b/src/binding/julia/Iteration.cpp index 952931d41d..28a8d858c3 100644 --- a/src/binding/julia/Iteration.cpp +++ b/src/binding/julia/Iteration.cpp @@ -14,7 +14,7 @@ namespace jlcxx template <> struct SuperType { - typedef Attributable type; + using type = Attributable; }; } // namespace jlcxx @@ -29,9 +29,7 @@ void define_julia_Iteration(jlcxx::Module &mod) type.method("cxx_set_dt!", &Iteration::setDt); type.method("cxx_time_unit_SI", &Iteration::timeUnitSI); type.method("cxx_set_time_unit_SI!", &Iteration::setTimeUnitSI); - type.method( - "cxx_close", - static_cast(&Iteration::close)); + type.method("cxx_close", overload_cast(&Iteration::close)); type.method("cxx_open", &Iteration::open); type.method("cxx_closed", &Iteration::closed); type.method("cxx_meshes", [](Iteration &iter) -> Container & { diff --git a/src/binding/julia/Mesh.cpp b/src/binding/julia/Mesh.cpp index f196b761e4..7fac56776b 100644 --- a/src/binding/julia/Mesh.cpp +++ b/src/binding/julia/Mesh.cpp @@ -12,7 +12,7 @@ namespace jlcxx template <> struct SuperType { - typedef Container type; + using type = Container; }; } // namespace jlcxx @@ -50,8 +50,7 @@ void define_julia_Mesh(jlcxx::Module &mod) type.method("cxx_geometry", &Mesh::geometry); type.method( - "cxx_set_geometry!", - static_cast(&Mesh::setGeometry)); + "cxx_set_geometry!", overload_cast(&Mesh::setGeometry)); type.method("cxx_geometry_parameters", &Mesh::geometryParameters); type.method("cxx_set_geometry_parameters!", &Mesh::setGeometryParameters); type.method("cxx_data_order", &Mesh::dataOrder); diff --git a/src/binding/julia/MeshRecordComponent.cpp b/src/binding/julia/MeshRecordComponent.cpp index 5b000760d6..965af8e269 100644 --- a/src/binding/julia/MeshRecordComponent.cpp +++ b/src/binding/julia/MeshRecordComponent.cpp @@ -12,10 +12,24 @@ namespace jlcxx template <> struct SuperType { - typedef RecordComponent type; + using type = RecordComponent; }; } // namespace jlcxx +namespace +{ +struct UseType +{ + template + static void call(jlcxx::TypeWrapper type) + { + type.method( + "cxx_make_constant_" + datatypeToString(determineDatatype()), + &MeshRecordComponent::makeConstant); + } +}; +} // namespace + void define_julia_MeshRecordComponent(jlcxx::Module &mod) { auto type = mod.add_type( @@ -23,11 +37,5 @@ void define_julia_MeshRecordComponent(jlcxx::Module &mod) type.method("cxx_position", &MeshRecordComponent::position); type.method("cxx_set_position!", &MeshRecordComponent::setPosition); -#define USE_TYPE(NAME, ENUM, TYPE) \ - type.method( \ - "cxx_make_constant_" NAME, &MeshRecordComponent::makeConstant); - { - FORALL_OPENPMD_TYPES(USE_TYPE) - } -#undef USE_TYPE + forallJuliaTypes(type); } diff --git a/src/binding/julia/RecordComponent.cpp b/src/binding/julia/RecordComponent.cpp index a938e1515f..f67fcd5bf0 100644 --- a/src/binding/julia/RecordComponent.cpp +++ b/src/binding/julia/RecordComponent.cpp @@ -17,7 +17,7 @@ namespace jlcxx template <> struct SuperType { - typedef BaseRecordComponent type; + using type = BaseRecordComponent; }; } // namespace jlcxx diff --git a/src/binding/julia/RecordComponent_load_chunk.cpp b/src/binding/julia/RecordComponent_load_chunk.cpp index 12d0c8876e..2c057740c6 100644 --- a/src/binding/julia/RecordComponent_load_chunk.cpp +++ b/src/binding/julia/RecordComponent_load_chunk.cpp @@ -6,17 +6,23 @@ #include "defs.hpp" -void define_julia_RecordComponent_load_chunk( - jlcxx::Module & /*mod*/, jlcxx::TypeWrapper &type) +namespace { -#define USE_TYPE(NAME, ENUM, TYPE) \ - type.method( \ - "cxx_load_chunk_" NAME, \ - static_cast, Offset, Extent)>( \ - &RecordComponent::loadChunk)); +struct UseType +{ + template + static void call(jlcxx::TypeWrapper &type) { - FORALL_SCALAR_OPENPMD_TYPES(USE_TYPE) + type.method( + "cxx_load_" + datatypeToString(determineDatatype()), + overload_cast, Offset, Extent>( + &RecordComponent::loadChunk)); } -#undef USE_TYPE +}; +} // namespace + +void define_julia_RecordComponent_load_chunk( + jlcxx::Module & /*mod*/, jlcxx::TypeWrapper &type) +{ + forallScalarJuliaTypes(type); } diff --git a/src/binding/julia/RecordComponent_make_constant.cpp b/src/binding/julia/RecordComponent_make_constant.cpp index 68f5384cef..89b9f7f371 100644 --- a/src/binding/julia/RecordComponent_make_constant.cpp +++ b/src/binding/julia/RecordComponent_make_constant.cpp @@ -6,14 +6,22 @@ #include "defs.hpp" -void define_julia_RecordComponent_make_constant( - jlcxx::Module & /*mod*/, jlcxx::TypeWrapper &type) +namespace { -#define USE_TYPE(NAME, ENUM, TYPE) \ - type.method( \ - "cxx_make_constant_" NAME, &RecordComponent::makeConstant); +struct UseType +{ + template + static void call(jlcxx::TypeWrapper &type) { - FORALL_SCALAR_OPENPMD_TYPES(USE_TYPE) + type.method( + "cxx_make_constant_" + datatypeToString(determineDatatype()), + &RecordComponent::makeConstant); } -#undef USE_TYPE +}; +} // namespace + +void define_julia_RecordComponent_make_constant( + jlcxx::Module & /*mod*/, jlcxx::TypeWrapper &type) +{ + forallScalarJuliaTypes(type); } diff --git a/src/binding/julia/RecordComponent_store_chunk.cpp b/src/binding/julia/RecordComponent_store_chunk.cpp index 2fc3ecf544..3f46b71499 100644 --- a/src/binding/julia/RecordComponent_store_chunk.cpp +++ b/src/binding/julia/RecordComponent_store_chunk.cpp @@ -6,17 +6,23 @@ #include "defs.hpp" -void define_julia_RecordComponent_store_chunk( - jlcxx::Module & /*mod*/, jlcxx::TypeWrapper &type) +namespace { -#define USE_TYPE(NAME, ENUM, TYPE) \ - type.method( \ - "cxx_store_chunk_" NAME, \ - static_cast, Offset, Extent)>( \ - &RecordComponent::storeChunk)); +struct UseType +{ + template + static void call(jlcxx::TypeWrapper &type) { - FORALL_SCALAR_OPENPMD_TYPES(USE_TYPE) + type.method( + "cxx_store_chunk_" + datatypeToString(determineDatatype()), + overload_cast, Offset, Extent>( + &RecordComponent::storeChunk)); } -#undef USE_TYPE +}; +} // namespace + +void define_julia_RecordComponent_store_chunk( + jlcxx::Module & /*mod*/, jlcxx::TypeWrapper &type) +{ + forallScalarJuliaTypes(type); } diff --git a/src/binding/julia/Series.cpp b/src/binding/julia/Series.cpp index b6fe058523..6d0524f447 100644 --- a/src/binding/julia/Series.cpp +++ b/src/binding/julia/Series.cpp @@ -25,7 +25,7 @@ namespace jlcxx template <> struct SuperType { - typedef Attributable type; + using type = Attributable; }; } // namespace jlcxx @@ -45,7 +45,7 @@ void define_julia_Series(jlcxx::Module &mod) sized_uint_t ucomm, const std::string &options) { MPI_Comm comm; - static_assert(sizeof ucomm == sizeof comm, ""); + static_assert(sizeof ucomm == sizeof comm); memcpy(&comm, &ucomm, sizeof comm); return Series(filepath, at, comm, options); }); @@ -55,7 +55,7 @@ void define_julia_Series(jlcxx::Module &mod) Access at, sized_uint_t ucomm) { MPI_Comm comm; - static_assert(sizeof ucomm == sizeof comm, ""); + static_assert(sizeof ucomm == sizeof comm); memcpy(&comm, &ucomm, sizeof comm); return Series(filepath, at, comm); }); @@ -81,8 +81,7 @@ void define_julia_Series(jlcxx::Module &mod) type.method("cxx_software", &Series::software); type.method( "cxx_set_software!", - static_cast( + overload_cast( &Series::setSoftware)); type.method( "cxx_set_software!", diff --git a/src/binding/julia/WriteIterations.cpp b/src/binding/julia/WriteIterations.cpp index d4f31c51a2..03da048198 100644 --- a/src/binding/julia/WriteIterations.cpp +++ b/src/binding/julia/WriteIterations.cpp @@ -10,8 +10,7 @@ void define_julia_WriteIterations(jlcxx::Module &mod) { - using iterations_t = Container; - using key_type = typename iterations_t::key_type; + using key_type = Series::IterationIndex_t; // using mapped_type = typename iterations_t::mapped_type; auto type = mod.add_type("WriteIterations"); diff --git a/src/binding/julia/defs.hpp b/src/binding/julia/defs.hpp index 97bac41ec2..f4d7d0a3c0 100644 --- a/src/binding/julia/defs.hpp +++ b/src/binding/julia/defs.hpp @@ -22,6 +22,7 @@ #include #include #include +#include #include #include #include @@ -57,213 +58,141 @@ using sized_uint_t = typename sized_uint::type; using array_double_7 = std::array; -/* - * Generate code fo all openPMD types. Use is e.g. as follows: - * #define USE_TYPE(NAME, ENUM, TYPE) \ - * type.method("get_" NAME, &Attribute::get); - * FORALL_OPENPMD_TYPES(USE_TYPE) - * #undef USE_TYPE - */ +// From pybind11, see +// share/openPMD/thirdParty/pybind11/include/pybind11/detail/common.h +// in the source tree +struct non_const_tag +{}; +struct const_tag +{}; -// We disable `long double` since Julia does not support this type -#define FORALL_OPENPMD_TYPES(MACRO) \ - MACRO("CHAR", Datatype::CHAR, char) \ - MACRO("UCHAR", Datatype::UCHAR, unsigned char) \ - MACRO("SHORT", Datatype::SHORT, short) \ - MACRO("INT", Datatype::INT, int) \ - MACRO("LONG", Datatype::LONG, long) \ - MACRO("LONGLONG", Datatype::LONGLONG, long long) \ - MACRO("USHORT", Datatype::USHORT, unsigned short) \ - MACRO("UINT", Datatype::UINT, unsigned int) \ - MACRO("ULONG", Datatype::ULONG, unsigned long) \ - MACRO("ULONGLONG", Datatype::ULONGLONG, unsigned long long) \ - MACRO("FLOAT", Datatype::FLOAT, float) \ - MACRO("DOUBLE", Datatype::DOUBLE, double) \ - /* MACRO("LONG_DOUBLE", Datatype::LONG_DOUBLE, long double) */ \ - MACRO("CFLOAT", Datatype::CFLOAT, std::complex) \ - MACRO("CDOUBLE", Datatype::CDOUBLE, std::complex) \ - /* MACRO("CLONG_DOUBLE", Datatype::CLONG_DOUBLE, std::complex) */ \ - MACRO("STRING", Datatype::STRING, std::string) \ - MACRO("VEC_CHAR", Datatype::VEC_CHAR, std::vector) \ - MACRO("VEC_UCHAR", Datatype::VEC_UCHAR, std::vector) \ - MACRO("VEC_SHORT", Datatype::VEC_SHORT, std::vector) \ - MACRO("VEC_INT", Datatype::VEC_INT, std::vector) \ - MACRO("VEC_LONG", Datatype::VEC_LONG, std::vector) \ - MACRO("VEC_LONGLONG", Datatype::VEC_LONGLONG, std::vector) \ - MACRO("VEC_USHORT", Datatype::VEC_USHORT, std::vector) \ - MACRO("VEC_UINT", Datatype::VEC_UINT, std::vector) \ - MACRO("VEC_ULONG", Datatype::VEC_ULONG, std::vector) \ - MACRO( \ - "VEC_ULONGLONG", \ - Datatype::VEC_ULONGLONG, \ - std::vector) \ - MACRO("VEC_FLOAT", Datatype::VEC_FLOAT, std::vector) \ - MACRO("VEC_DOUBLE", Datatype::VEC_DOUBLE, std::vector) \ - /* MACRO("VEC_LONG_DOUBLE", Datatype::VEC_LONG_DOUBLE, std::vector) */ \ - MACRO( \ - "VEC_CFLOAT", Datatype::VEC_CFLOAT, std::vector>) \ - MACRO( \ - "VEC_CDOUBLE", \ - Datatype::VEC_CDOUBLE, \ - std::vector>) \ - /* MACRO("VEC_CLONG_DOUBLE", Datatype::VEC_CLONG_DOUBLE, \ - * std::vector>) */ \ - MACRO("VEC_STRING", Datatype::VEC_STRING, std::vector) \ - MACRO("ARR_DBL_7", Datatype::ARR_DBL_7, array_double_7) \ - MACRO("BOOL", Datatype::BOOL, bool) +namespace detail +{ +template +struct overload_cast_impl +{ + template + constexpr auto operator()(Return (*pf)(Args...)) const noexcept + -> decltype(pf) + { + return pf; + } -#define FORALL_SCALAR_OPENPMD_TYPES(MACRO) \ - MACRO("CHAR", Datatype::CHAR, char) \ - MACRO("UCHAR", Datatype::UCHAR, unsigned char) \ - MACRO("SHORT", Datatype::SHORT, short) \ - MACRO("INT", Datatype::INT, int) \ - MACRO("LONG", Datatype::LONG, long) \ - MACRO("LONGLONG", Datatype::LONGLONG, long long) \ - MACRO("USHORT", Datatype::USHORT, unsigned short) \ - MACRO("UINT", Datatype::UINT, unsigned int) \ - MACRO("ULONG", Datatype::ULONG, unsigned long) \ - MACRO("ULONGLONG", Datatype::ULONGLONG, unsigned long long) \ - MACRO("FLOAT", Datatype::FLOAT, float) \ - MACRO("DOUBLE", Datatype::DOUBLE, double) \ - /* MACRO("LONG_DOUBLE", Datatype::LONG_DOUBLE, long double) */ \ - MACRO("CFLOAT", Datatype::CFLOAT, std::complex) \ - MACRO("CDOUBLE", Datatype::CDOUBLE, std::complex) \ - /* MACRO("CLONG_DOUBLE", Datatype::CLONG_DOUBLE, std::complex) */ \ - MACRO("STRING", Datatype::STRING, std::string) \ - MACRO("ARR_DBL_7", Datatype::ARR_DBL_7, array_double_7) \ - MACRO("BOOL", Datatype::BOOL, bool) + template + constexpr auto + operator()(Return (Class::*pmf)(Args...), non_const_tag = {}) const noexcept + -> decltype(pmf) + { + return pmf; + } -// This C++ version is a bit more tedious to use than the macro version above -template -T typeval() + template + constexpr auto + operator()(Return (Class::*pmf)(Args...) const, const_tag) const noexcept + -> decltype(pmf) + { + return pmf; + } +}; +} // namespace detail + +template +static constexpr ::detail::overload_cast_impl overload_cast{}; +constexpr const_tag const const_; + +/** + * Generalizes the repeated application of a function template for all + * scalar openPMD datatypes. + * + * Will call the function template found at Action::template call(), + * instantiating T with every scalar openPMD datatype as found + * in the Datatype enum. + * + * @tparam Action The struct containing the function template. + * @tparam Args The function template's argument types. + * @param args The function template's arguments. + */ +template +void forallScalarJuliaTypes(Args &&...args) { - return T{}; + // Do NOT call std::forward(args)... here + // Move semantics must be avoided due to repeated application + Action::template call(args...); + Action::template call(args...); + Action::template call(args...); + Action::template call(args...); + Action::template call(args...); + Action::template call(args...); + Action::template call(args...); + Action::template call(args...); + Action::template call(args...); + Action::template call(args...); + Action::template call(args...); + Action::template call(args...); + Action::template call(args...); + // We disable `long double` since Julia does not support this type + // Action::template call(args...); + Action::template call>(args...); + Action::template call>(args...); + // Action::template call>(args...); + Action::template call(args...); + Action::template call(args...); } -template -void forall_openPMD_types(const F &f, Args &&...args) +/** + * Generalizes the repeated application of a function template for all + * openPMD datatypes. + * + * Will call the function template found at Action::template call(), + * instantiating T with every scalar datatype as found in the Datatype enum. + * + * @tparam Action The struct containing the function template. + * @tparam Args The function template's argument types. + * @param args The function template's arguments. + */ +template +void forallJuliaTypes(Args &&...args) { - f("CHAR", Datatype::CHAR, typeval(), std::forward(args)...); - f("UCHAR", - Datatype::UCHAR, - typeval(), - std::forward(args)...); - f("SHORT", Datatype::SHORT, typeval(), std::forward(args)...); - f("INT", Datatype::INT, typeval(), std::forward(args)...); - f("LONG", Datatype::LONG, typeval(), std::forward(args)...); - f("LONGLONG", - Datatype::LONGLONG, - typeval(), - std::forward(args)...); - f("USHORT", - Datatype::USHORT, - typeval(), - std::forward(args)...); - f("UINT", - Datatype::UINT, - typeval(), - std::forward(args)...); - f("ULONG", - Datatype::ULONG, - typeval(), - std::forward(args)...); - f("ULONGLONG", - Datatype::ULONGLONG, - typeval(), - std::forward(args)...); - f("FLOAT", Datatype::FLOAT, typeval(), std::forward(args)...); - f("DOUBLE", - Datatype::DOUBLE, - typeval(), - std::forward(args)...); - // f("LONG_DOUBLE", Datatype::LONG_DOUBLE, typeval(), - // std::forward(args)...); - f("CFLOAT", - Datatype::CFLOAT, - typeval>(), - std::forward(args)...); - f("CDOUBLE", - Datatype::CDOUBLE, - typeval>(), - std::forward(args)...); - // f("CLONG_DOUBLE", Datatype::CLONG_DOUBLE, typeval>(), std::forward(args)...); - f("STRING", - Datatype::STRING, - typeval(), - std::forward(args)...); - f("VEC_CHAR", - Datatype::VEC_CHAR, - typeval>(), - std::forward(args)...); - f("VEC_UCHAR", - Datatype::VEC_UCHAR, - typeval>(), - std::forward(args)...); - f("VEC_SHORT", - Datatype::VEC_SHORT, - typeval>(), - std::forward(args)...); - f("VEC_INT", - Datatype::VEC_INT, - typeval>(), - std::forward(args)...); - f("VEC_LONG", - Datatype::VEC_LONG, - typeval>(), - std::forward(args)...); - f("VEC_LONGLONG", - Datatype::VEC_LONGLONG, - typeval>(), - std::forward(args)...); - f("VEC_USHORT", - Datatype::VEC_USHORT, - typeval>(), - std::forward(args)...); - f("VEC_UINT", - Datatype::VEC_UINT, - typeval>(), - std::forward(args)...); - f("VEC_ULONG", - Datatype::VEC_ULONG, - typeval>(), - std::forward(args)...); - f("VEC_ULONGLONG", - Datatype::VEC_ULONGLONG, - typeval>(), - std::forward(args)...); - f("VEC_FLOAT", - Datatype::VEC_FLOAT, - typeval>(), - std::forward(args)...); - f("VEC_DOUBLE", - Datatype::VEC_DOUBLE, - typeval>(), - std::forward(args)...); - // f("VEC_LONG_DOUBLE", Datatype::VEC_LONG_DOUBLE, typeval>(), std::forward(args)...); - f("VEC_CFLOAT", - Datatype::VEC_CFLOAT, - typeval>>(), - std::forward(args)...); - f("VEC_CDOUBLE", - Datatype::VEC_CDOUBLE, - typeval>>(), - std::forward(args)...); - // f("VEC_CLONG_DOUBLE", Datatype::VEC_CLONG_DOUBLE, - // typeval>>(), - // std::forward(args)...); - f("VEC_STRING", - Datatype::VEC_STRING, - typeval>(), - std::forward(args)...); - f("ARR_DBL_7", - Datatype::ARR_DBL_7, - typeval(), - std::forward(args)...); - f("BOOL", Datatype::BOOL, typeval(), std::forward(args)...); + // Do NOT call std::forward(args)... here + // Move semantics must be avoided due to repeated application + Action::template call(args...); + Action::template call(args...); + Action::template call(args...); + Action::template call(args...); + Action::template call(args...); + Action::template call(args...); + Action::template call(args...); + Action::template call(args...); + Action::template call(args...); + Action::template call(args...); + Action::template call(args...); + Action::template call(args...); + Action::template call(args...); + // We disable `long double` since Julia does not support this type + // Action::template call(args...); + Action::template call>(args...); + Action::template call>(args...); + // Action::template call>(args...); + Action::template call(args...); + Action::template call>(args...); + Action::template call>(args...); + Action::template call>(args...); + Action::template call>(args...); + Action::template call>(args...); + Action::template call>(args...); + Action::template call>(args...); + Action::template call>(args...); + Action::template call>(args...); + Action::template call>(args...); + Action::template call>(args...); + Action::template call>(args...); + Action::template call>(args...); + // Action::template call>(args...); + Action::template call>>(args...); + Action::template call>>(args...); + // Action::template call>>(args...); + Action::template call>(args...); + Action::template call>(args...); + Action::template call(args...); } namespace diff --git a/src/binding/julia/shared_ptr.cpp b/src/binding/julia/shared_ptr.cpp index 69c8808fbc..d0fffd69f9 100644 --- a/src/binding/julia/shared_ptr.cpp +++ b/src/binding/julia/shared_ptr.cpp @@ -5,15 +5,25 @@ */ #include "defs.hpp" +#include "openPMD/Datatype.hpp" +#include -void define_julia_shared_ptr(jlcxx::Module &mod) +namespace +{ +struct UseType { -#define USE_TYPE(NAME, ENUM, TYPE) \ - mod.method( \ - "create_aliasing_shared_ptr_" NAME, \ - &create_aliasing_shared_ptr); + template + static void call(jlcxx::Module &mod) { - FORALL_SCALAR_OPENPMD_TYPES(USE_TYPE) + mod.method( + "create_aliasing_shared_ptr_" + + datatypeToString(determineDatatype()), + &create_aliasing_shared_ptr); } -#undef USE_TYPE +}; +} // namespace + +void define_julia_shared_ptr(jlcxx::Module &mod) +{ + forallScalarJuliaTypes(mod); }