vitorsousa pushed a commit to branch master.

http://git.enlightenment.org/core/efl.git/commit/?id=29d24aa409371bd0252b34eb54b1adcb256ca2a1

commit 29d24aa409371bd0252b34eb54b1adcb256ca2a1
Author: Lauro Moura <[email protected]>
Date:   Tue Jul 30 11:05:26 2019 -0300

    csharp: Add marshal support for Eina.ValueType
    
    Summary:
    It uses a custom marshaler and a helper boxing class to convert between
    the managed enum values and the native Eina_Value_Type pointers.
    
    To be used by future MVVM machinery.
    
    Reviewers: vitor.sousa, felipealmeida
    
    Reviewed By: vitor.sousa
    
    Subscribers: cedric, #reviewers, #committers
    
    Tags: #efl
    
    Differential Revision: https://phab.enlightenment.org/D9443
---
 .../eolian_mono/eolian/mono/marshall_annotation.hh |  6 ++
 .../eolian_mono/eolian/mono/marshall_type_impl.hh  |  7 ++
 src/bindings/mono/eina_mono/eina_value.cs          | 85 ++++++++++++++++++++++
 src/lib/efl_mono/efl_custom_exports_mono.c         |  3 +
 src/tests/efl_mono/ValueEolian.cs                  | 11 +++
 src/tests/efl_mono/dummy_test_object.c             |  5 ++
 src/tests/efl_mono/dummy_test_object.eo            |  7 ++
 7 files changed, 124 insertions(+)

diff --git a/src/bin/eolian_mono/eolian/mono/marshall_annotation.hh 
b/src/bin/eolian_mono/eolian/mono/marshall_annotation.hh
index 632696d6a7..6d56b2493c 100644
--- a/src/bin/eolian_mono/eolian/mono/marshall_annotation.hh
+++ b/src/bin/eolian_mono/eolian/mono/marshall_annotation.hh
@@ -82,6 +82,9 @@ struct marshall_annotation_visitor_generate
           {"strbuf", false, [&] {
                 return "[MarshalAs(UnmanagedType.CustomMarshaler, 
MarshalTypeRef=typeof(Efl.Eo.StrbufKeepOwnershipMarshaler))]";
           }},
+          {"Value_Type", false, [&] {
+                return "[MarshalAs(UnmanagedType.CustomMarshaler, 
MarshalTypeRef=typeof(Eina.ValueTypeMarshaler))]";
+          }},
         };
       match const return_match_table[] =
         {
@@ -117,6 +120,9 @@ struct marshall_annotation_visitor_generate
           {"strbuf", false, [&] {
                 return "[return: MarshalAs(UnmanagedType.CustomMarshaler, 
MarshalTypeRef=typeof(Efl.Eo.StrbufKeepOwnershipMarshaler))]";
           }},
+          {"Value_Type", false, [&] {
+                return "[return: MarshalAs(UnmanagedType.CustomMarshaler, 
MarshalTypeRef=typeof(Eina.ValueTypeMarshaler))]";
+          }},
         };
 
         if(eina::optional<bool> b = call_annotation_match
diff --git a/src/bin/eolian_mono/eolian/mono/marshall_type_impl.hh 
b/src/bin/eolian_mono/eolian/mono/marshall_type_impl.hh
index 8de109e88b..588e8c2465 100644
--- a/src/bin/eolian_mono/eolian/mono/marshall_type_impl.hh
+++ b/src/bin/eolian_mono/eolian/mono/marshall_type_impl.hh
@@ -161,6 +161,13 @@ struct marshall_type_visitor_generate
                     r.base_type = "void";
                 return r;
                }}
+           , {"Value_Type", nullptr, [&]
+               {
+                regular_type_def r = regular;
+                r.namespaces.clear();
+                r.base_type = "Eina.ValueTypeBox";
+                return r;
+               }}
         };
 
         if (regular.is_struct() && !blacklist::is_struct_blacklisted(regular) 
&& !(bool)(regular.base_qualifier & qualifier_info::is_own))
diff --git a/src/bindings/mono/eina_mono/eina_value.cs 
b/src/bindings/mono/eina_mono/eina_value.cs
index cedf5001c2..57a615772b 100644
--- a/src/bindings/mono/eina_mono/eina_value.cs
+++ b/src/bindings/mono/eina_mono/eina_value.cs
@@ -3,6 +3,7 @@
 #define CODE_ANALYSIS
 
 using System;
+using System.ComponentModel;
 using System.Linq;
 using System.Runtime.InteropServices;
 using System.Collections.Generic;
@@ -515,6 +516,8 @@ static internal class UnsafeNativeMethods
     internal static extern IntPtr type_array();
     [DllImport(efl.Libs.CustomExports)]
     internal static extern IntPtr type_list();
+    [DllImport(efl.Libs.CustomExports)]
+    internal static extern IntPtr type_hash();
 
     // Optional
     [DllImport(efl.Libs.CustomExports)]
@@ -716,6 +719,39 @@ static class ValueTypeMethods
     }
 }
 
+/// <summary>Boxing class for custom marshalling of ValueType enums.
+///
+/// <para>As custom marshalling of enums (and other value types) is not 
supported, use
+/// use this boxing class as an intermediate at the Marshalling API level 
(like in
+/// marshall_type_impl.hh in the generator). User-facing API still uses 
Eina.ValueType
+/// normally.</para>
+/// </summary>
+[EditorBrowsable(EditorBrowsableState.Never)]
+public class ValueTypeBox
+{
+    public ValueType _payload;
+
+    public ValueTypeBox(ValueType v)
+    {
+        _payload = v;
+    }
+
+    public static implicit operator ValueTypeBox(ValueType v)
+    {
+        return new ValueTypeBox(v);
+    }
+
+    public static implicit operator ValueType(ValueTypeBox box)
+    {
+        if (box == null)
+        {
+            return Eina.ValueType.Empty;
+        }
+
+        return box._payload;
+    }
+}
+
 static class ValueTypeBridge
 {
     private static Dictionary<ValueType, IntPtr> ManagedToNative = new 
Dictionary<ValueType, IntPtr>();
@@ -860,6 +896,9 @@ static class ValueTypeBridge
         ManagedToNative.Add(ValueType.List, type_list());
         NativeToManaged.Add(type_list(), ValueType.List);
 
+        ManagedToNative.Add(ValueType.Hash, type_hash());
+        NativeToManaged.Add(type_hash(), ValueType.Hash);
+
         ManagedToNative.Add(ValueType.Optional, type_optional());
         NativeToManaged.Add(type_optional(), ValueType.Optional);
 
@@ -2898,6 +2937,7 @@ public class Value : IDisposable, IComparable<Value>, 
IEquatable<Value>
 
 /// <summary> Custom marshaler to convert value pointers to managed values and 
back,
 /// without changing ownership.</summary>
+[EditorBrowsable(EditorBrowsableState.Never)]
 public class ValueMarshaler : ICustomMarshaler
 {
     /// <summary>Creates a managed value from a C pointer, whitout taking 
ownership of it.</summary>
@@ -3000,4 +3040,49 @@ public class ValueMarshalerOwn : ICustomMarshaler
     static private ValueMarshalerOwn marshaler;
 }
 
+/// <summary> Custom marshaler to convert value type pointers to managed boxed 
enum values
+/// and back.</summary>
+public class ValueTypeMarshaler : ICustomMarshaler
+{
+    /// <summary>Creates a boxed ValueType enum value from a C 
pointer.</summary>
+    public object MarshalNativeToManaged(IntPtr pNativeData)
+    {
+        var r = ValueTypeBridge.GetManaged(pNativeData);
+        return new ValueTypeBox(r);
+    }
+    public static Eina.ValueType vtype;
+
+    /// <summary>Retrieves the C pointer from a given boxed enum value 
type.</summary>
+    public IntPtr MarshalManagedToNative(object managedObj)
+    {
+        ValueTypeBox v = (ValueTypeBox)managedObj;
+        return ValueTypeBridge.GetNative(v);
+    }
+
+    public void CleanUpNativeData(IntPtr pNativeData)
+    {
+    }
+
+    public void CleanUpManagedData(object managedObj)
+    {
+    }
+
+    public int GetNativeDataSize()
+    {
+        return -1;
+    }
+
+    public static ICustomMarshaler GetInstance(string cookie)
+    {
+        if (marshaler == null)
+        {
+            marshaler = new ValueTypeMarshaler();
+        }
+
+        return marshaler;
+    }
+
+    static private ValueTypeMarshaler marshaler;
+}
+
 }
diff --git a/src/lib/efl_mono/efl_custom_exports_mono.c 
b/src/lib/efl_mono/efl_custom_exports_mono.c
index aa2572f49d..590bb4e784 100644
--- a/src/lib/efl_mono/efl_custom_exports_mono.c
+++ b/src/lib/efl_mono/efl_custom_exports_mono.c
@@ -421,6 +421,9 @@ EAPI const Eina_Value_Type *type_array() {
 EAPI const Eina_Value_Type *type_list() {
    return EINA_VALUE_TYPE_LIST;
 }
+EAPI const Eina_Value_Type *type_hash() {
+   return EINA_VALUE_TYPE_HASH;
+}
 EAPI const Eina_Value_Type *type_error() {
    return EINA_VALUE_TYPE_ERROR;
 }
diff --git a/src/tests/efl_mono/ValueEolian.cs 
b/src/tests/efl_mono/ValueEolian.cs
index ea178d4ac9..945228a6db 100644
--- a/src/tests/efl_mono/ValueEolian.cs
+++ b/src/tests/efl_mono/ValueEolian.cs
@@ -160,6 +160,17 @@ public static class TestEinaValueEolian {
         Test.AssertEquals(expected, received);
         Test.AssertEquals(Eina.ValueType.Int32, received.GetValueType());
     }
+
+    public static void TestEolianEinaValueTypeMarshalling()
+    {
+        var obj = new Dummy.TestObject();
+
+        var values = Enum.GetValues(typeof(Eina.ValueType));
+        foreach (Eina.ValueType type in values)
+        {
+            Test.AssertEquals(type, obj.MirrorValueType(type));
+        }
+    }
 }
 #pragma warning restore 1591
 }
diff --git a/src/tests/efl_mono/dummy_test_object.c 
b/src/tests/efl_mono/dummy_test_object.c
index 6717b12476..8ba7536720 100644
--- a/src/tests/efl_mono/dummy_test_object.c
+++ b/src/tests/efl_mono/dummy_test_object.c
@@ -4685,6 +4685,11 @@ Efl_Object 
*_dummy_test_object_call_find_provider_for_iface(Eo *obj, EINA_UNUSED
     return efl_provider_find(obj, DUMMY_TEST_IFACE_INTERFACE);
 }
 
+const Eina_Value_Type *_dummy_test_object_mirror_value_type(EINA_UNUSED const 
Eo *obj, EINA_UNUSED Dummy_Test_Object_Data *pd, const Eina_Value_Type *type)
+{
+    return type;
+}
+
 // Inherit
 int _dummy_inherit_helper_receive_dummy_and_call_int_out(Dummy_Test_Object *x)
 {
diff --git a/src/tests/efl_mono/dummy_test_object.eo 
b/src/tests/efl_mono/dummy_test_object.eo
index 2273c23a20..4f26beba0a 100644
--- a/src/tests/efl_mono/dummy_test_object.eo
+++ b/src/tests/efl_mono/dummy_test_object.eo
@@ -1642,6 +1642,13 @@ class Dummy.Test_Object extends Efl.Object implements 
Dummy.Test_Iface {
       call_find_provider_for_iface {
          return: Efl.Object;
       }
+
+      mirror_value_type @beta @const {
+         params {
+            @in type: const(ptr(Eina.Value_Type));
+         }
+         return: const(ptr(Eina.Value_Type));
+      }
    }
    implements {
       Efl.Object.constructor;

-- 


Reply via email to