diff --git a/src/bindings/mono/eina_mono/eina_hash.cs b/src/bindings/mono/eina_mono/eina_hash.cs index 38522dc0e3..dc5c0fd294 100644 --- a/src/bindings/mono/eina_mono/eina_hash.cs +++ b/src/bindings/mono/eina_mono/eina_hash.cs @@ -278,17 +278,31 @@ public class Hash : IEnumerable>, IDi IntPtr nk = GetNativePtr(gchnk, ForceRefKey()); var r = eina_hash_del_by_key(Handle, nk); FreeNativeIndirection(gchnk, ForceRefKey()); - // NativeFreeRef(nk, OwnKey && r); return r; } + /// Searches this hash for val and deletes it from the hash, also deleting it. + /// true if the value was found and deleted, false if it was null or not found. public bool DelByValue(TValue val) { - IntPtr gchnv = CopyNativeObject(val, false); - IntPtr nv = GetNativePtr(gchnv, false); - var r = eina_hash_del_by_data(Handle, nv); - FreeNativeIndirection(gchnv, false); - return r; + // We don't use the C version of `eina_hash_del_by_data` because it requires the exact pointer + // we passed to add(). As our hashes store the data by pointer, this makes it harder to pass the + // same value. + if (val == null) + { + return false; + } + + foreach (var pair in this) + { + if (pair.Value != null && val.Equals(pair.Value)) + { + return this.DelByKey(pair.Key); + } + } + + return false; + } public void Remove(TKey key) diff --git a/src/tests/efl_mono/Hash.cs b/src/tests/efl_mono/Hash.cs new file mode 100644 index 0000000000..e064e47a13 --- /dev/null +++ b/src/tests/efl_mono/Hash.cs @@ -0,0 +1,55 @@ +using System; + +namespace TestSuite { + +class TestHash +{ + + public static void test_del_value() + { + var hash = new Eina.Hash(); + Test.AssertEquals(hash.Count, 0); + hash.Add(0, 1); + Test.Assert(hash.DelByValue(1)); + Test.AssertEquals(hash.Count, 0); + + hash.Add(0, 1); + hash.Add(1, 100); + hash.Add(2, 101); + + Test.Assert(hash.DelByValue(100)); + Test.AssertEquals(hash.Count, 2); + + Test.Assert(!hash.DelByValue(200)); + } + + public static void test_del_value_string() + { + var hash = new Eina.Hash(); + Test.AssertEquals(hash.Count, 0); + hash.Add(0, "E F L"); + Test.Assert(hash.DelByValue("E F L")); + Test.AssertEquals(hash.Count, 0); + + hash.Add(0, "Eina"); + hash.Add(1, "Eo"); + hash.Add(2, "Ecore"); + + Test.Assert(hash.DelByValue("Ecore")); + Test.AssertEquals(hash.Count, 2); + + Test.Assert(!hash.DelByValue("Elementary")); + } + + public static void test_del_key() + { + var hash = new Eina.Hash(); + hash.Add(0, 1); + hash.Add(1, 100); + hash.Add(2, 101); + + hash.DelByKey(1); + Test.AssertEquals(hash.Count, 2); + } +} +} // namespace TestSuite diff --git a/src/tests/efl_mono/meson.build b/src/tests/efl_mono/meson.build index 445c823caa..8dedc3e543 100644 --- a/src/tests/efl_mono/meson.build +++ b/src/tests/efl_mono/meson.build @@ -81,6 +81,7 @@ efl_mono_src = [ 'Value.cs', 'ValueEolian.cs', 'Inheritance.cs', + 'Hash.cs' ] efl_mono_suite = executable('efl-mono-suite',