Ejemplo n.º 1
0
        public unsafe void Combine <T>(T thing) where T : ISwiftHashable
        {
            fixed(byte *thisSwiftDataPtr = StructMarshal.Marshaler.PrepareNominal(this))
            {
                IntPtr       thingIntPtr;
                ISwiftObject thingProxy       = null;
                var          thingIsSwiftable = StructMarshal.Marshaler.IsSwiftRepresentable(typeof(T));

                if (thingIsSwiftable)
                {
                    byte *thingPtr = stackalloc byte [StructMarshal.Marshaler.Strideof(typeof(T))];
                    thingIntPtr = new IntPtr(thingPtr);
                    StructMarshal.Marshaler.ToSwift(thing, thingIntPtr);
                }
                else
                {
                    if (SwiftProtocolTypeAttribute.IsAssociatedTypeProxy(typeof(ISwiftHashable)))
                    {
                        byte *thingPtr0 = stackalloc byte [IntPtr.Size];
                        thingIntPtr = new IntPtr(thingPtr0);
                        Marshal.WriteIntPtr(thingIntPtr, thingProxy.SwiftObject);
                    }
                    else
                    {
                        var   thingExistentialContainer = SwiftObjectRegistry.Registry.ExistentialContainerForProtocols(thing, typeof(ISwiftHashable));
                        byte *thingProtoPtr             = stackalloc byte [thingExistentialContainer.SizeOf];
                        thingIntPtr = new IntPtr(thingProtoPtr);
                        thingExistentialContainer.CopyTo(thingIntPtr);
                    }
                }
                NativeMethodsForSwiftHasher.PI_hasherCombine((IntPtr)thisSwiftDataPtr, thingIntPtr,
                                                             StructMarshal.Marshaler.Metatypeof(typeof(T), new Type [] { typeof(ISwiftHashable) }),
                                                             StructMarshal.Marshaler.ProtocolWitnessof(typeof(ISwiftHashable), typeof(T)));
                if (thingIsSwiftable)
                {
                    StructMarshal.Marshaler.ReleaseSwiftPointer(typeof(T), thingIntPtr);
                }
                else
                {
                    if (thingProxy != null)
                    {
                        StructMarshal.ReleaseSwiftObject(thingProxy);
                    }
                }
            }
        }