From 2d4fc9dc97047f07bfcb57b112306105e1ad9340 Mon Sep 17 00:00:00 2001 From: Patrick Pelissier Date: Sat, 1 Jun 2024 10:16:39 +0200 Subject: [PATCH] Allow generation of EMPLACE_TYPE for variant if all oplists defined a FIELD operator. --- README.md | 1 + m-core.h | 3 +++ m-variant.h | 18 +++++++++++++++--- 3 files changed, 19 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index a2273c92..8a841a99 100644 --- a/README.md +++ b/README.md @@ -624,6 +624,7 @@ The following classic operators are usually expected for an object: Other documented operators are: * `NAME()` --> `prefix`: Return the base name `prefix` used to construct the container. +* `FIELD()` --> `field name`: Return the name of the field used when constructing the container. * `TYPE()` --> `type`: Return the base type associated to this oplist. * `SUBTYPE()` --> `type`: Return the type of the element stored in the container (used to iterate over the container). * `GENTYPE()` --> `type`: Return the type representing TYPE suitable for a _Generic statement. diff --git a/m-core.h b/m-core.h index ab78636a..6f72dd8f 100644 --- a/m-core.h +++ b/m-core.h @@ -3386,6 +3386,7 @@ M_INLINE size_t m_core_cstr_hash(const char str[]) #define M_GENTYPE_GENTYPE(a) ,a, #define M_SUBTYPE_PTR_SUBTYPE_PTR(a) ,a, #define M_NAME_NAME(a) ,a, +#define M_FIELD_FIELD(a) ,a, #define M_OPLIST_OPLIST(a) ,a, #define M_SORT_SORT(a) ,a, #define M_SPLICE_BACK_SPLICE_BACK(a) ,a, @@ -3477,6 +3478,7 @@ M_INLINE size_t m_core_cstr_hash(const char str[]) #define M_GET_SUBTYPE_PTR(...) M_GET_METHOD(SUBTYPE_PTR, M_NO_DEF_SUBTYPE_PTR, __VA_ARGS__) #define M_GET_GENTYPE(...) M_GET_METHOD(GENTYPE, M_NO_DEF_GENTYPE, __VA_ARGS__) #define M_GET_NAME(...) M_GET_METHOD(NAME, M_NO_DEF_NAME, __VA_ARGS__) +#define M_GET_FIELD(...) M_GET_METHOD(FIELD, M_NO_DEF_FIELD, __VA_ARGS__) #define M_GET_OPLIST(...) M_GET_METHOD(OPLIST, (), __VA_ARGS__) #define M_GET_SORT(...) M_GET_METHOD(SORT, M_NO_DEF_SORT, __VA_ARGS__) #define M_GET_SPLICE_BACK(...) M_GET_METHOD(SPLICE_BACK, M_NO_DEF_SPLICE_BACK, __VA_ARGS__) @@ -3558,6 +3560,7 @@ M_INLINE size_t m_core_cstr_hash(const char str[]) //#define M_CALL_SUBTYPE_PTR(oplist, ...) M_APPLY_API(M_GET_SUBTYPE_PTR oplist, oplist, __VA_ARGS__) //#define M_CALL_GENTYPE(oplist, ...) M_APPLY_API(M_GET_GENTYPE oplist, oplist, __VA_ARGS__) //#define M_CALL_NAME(oplist, ...) M_APPLY_API(M_GET_NAME oplist, oplist, __VA_ARGS__) +//#define M_CALL_FIELD(oplist, ...) M_APPLY_API(M_GET_FIELD oplist, oplist, __VA_ARGS__) //#define M_CALL_OPLIST(oplist, ...) M_APPLY_API(M_GET_OPLIST oplist, oplist, __VA_ARGS__) #define M_CALL_SORT(oplist, ...) M_APPLY_API(M_GET_SORT oplist, oplist, __VA_ARGS__) #define M_CALL_SPLICE_BACK(oplist, ...) M_APPLY_API(M_GET_SPLICE_BACK oplist, oplist, __VA_ARGS__) diff --git a/m-variant.h b/m-variant.h index bf25634d..e90132ac 100644 --- a/m-variant.h +++ b/m-variant.h @@ -194,9 +194,10 @@ typedef \ M_IF_METHOD(GENTYPE, M_VAR1ANT_GET_OPLIST a)( M_GET_GENTYPE M_VAR1ANT_GET_OPLIST a, M_VAR1ANT_GET_TYPE a) \ M_C4(m_var1ant_, name, _gentype_, num); \ - typedef const \ - M_IF_METHOD(GENTYPE, M_VAR1ANT_GET_OPLIST a)( M_GET_GENTYPE M_VAR1ANT_GET_OPLIST a, M_VAR1ANT_GET_TYPE a) \ - M_C4(m_var1ant_, name, _const_gentype_, num); + typedef \ + M_IF_METHOD(GENTYPE, M_VAR1ANT_GET_OPLIST a)( const M_GET_GENTYPE M_VAR1ANT_GET_OPLIST a, M_VAR1ANT_GET_TYPE a const) \ + M_C4(m_var1ant_, name, _const_gentype_, num); \ + typedef M_VAR1ANT_GET_TYPE a M_C4(m_var1ant_, name, _type_, M_VAR1ANT_GET_FIELD a); #define M_VAR1ANT_DEFINE_UNION_ELE(name, a) \ , M_C4(name, _, M_VAR1ANT_GET_FIELD a, _value) @@ -793,8 +794,19 @@ M_INLINE void \ M_IF_METHOD_ALL(INIT_MOVE, __VA_ARGS__)(INIT_MOVE(M_F(name, _init_move)),), \ M_IF_METHOD_ALL(INIT_MOVE, __VA_ARGS__)(MOVE(M_F(name, _move)),), \ M_IF_METHOD_ALL(SWAP, __VA_ARGS__)(SWAP(M_F(name, _swap)),), \ + M_IF_METHOD_ALL(FIELD, __VA_ARGS__)(M_VAR1ANT_OPLIST_EMPLACE_TYPE(name, __VA_ARGS__),), \ ) +/* Expand to an EMPLACE_TYPE compatible with OPLIST definition + (Use M_REDUCE2 which is already used by M_IF_METHOD_ALL) + */ +#define M_VAR1ANT_OPLIST_EMPLACE_TYPE(name, ...) EMPLACE_TYPE( LIST( \ + M_REDUCE2(M_VAR1ANT_OPLIST_EMPLACE_TYPE_EXPAND, M_ID, name, __VA_ARGS__) \ + )) +#define M_VAR1ANT_OPLIST_EMPLACE_TYPE_EXPAND(name, oplist) \ + ( M_C(_, M_GET_FIELD oplist), M_C4(name, _init_set_, M_GET_FIELD oplist), \ + M_C4(m_var1ant_, name, _type_, M_GET_FIELD oplist) ) + /********************************** INTERNAL *********************************/