예제 #1
0
        public override void VisitObjCPropertyDecl(ObjCPropertyDecl decl)
        {
            // don't process methods (or types) that are unavailable for the current platform
            if (!decl.IsAvailable() || !(decl.DeclContext as Decl).IsAvailable())
            {
                return;
            }

            // does not look exposed, but part of the dump
            if (decl.DumpToString().IndexOf("UI_APPEARANCE_SELECTOR", StringComparison.OrdinalIgnoreCase) < 0)
            {
                return;
            }

            var getter = decl.Getter;

            if (getter != null)
            {
                VisitObjCMethodDecl(getter);
            }
            var setter = decl.Setter;

            if (setter != null)
            {
                VisitObjCMethodDecl(setter);
            }
        }
예제 #2
0
        protected PropertyInfo FindProperty(ObjCPropertyDecl prop)
        {
            string getNativeSelector = prop.Getter != null ? prop.Getter.Name : null;
            string setNativeSelector = prop.Setter != null ? prop.Setter.Name : null;

            foreach (PropertyInfo p in currentType.GetProperties())
            {
                string getManagedSelector = GetSelector(p.GetGetMethod());
                string setManagedSelector = GetSelector(p.GetSetMethod());
                if (getNativeSelector == getManagedSelector && setNativeSelector == setManagedSelector)
                {
                    return(p);
                }
            }
            return(null);
        }
예제 #3
0
        public override void VisitObjCPropertyDecl(ObjCPropertyDecl decl)
        {
            // protocol members are checked in ObjCProtocolCheck
            if (decl.DeclContext is ObjCProtocolDecl)
            {
                return;
            }

            // check availability macros to see if the API is available on the OS and not deprecated
            if (!decl.IsAvailable())
            {
                return;
            }

            var framework = Helpers.GetFramework(decl);

            if (framework == null)
            {
                return;
            }

            var nativeArgumentSemantic = decl.Attributes.ToArgumentSemantic();
            var nativeMethodDefinition = decl.QualifiedName;

            if (qualified_properties.TryGetValue(nativeMethodDefinition, out var managedArgumentSemanticList))
            {
                foreach (var entry in managedArgumentSemanticList)
                {
                    var method = entry.Item1;
                    var managedArgumentSemantic = entry.Item2;

                    if (managedArgumentSemantic != nativeArgumentSemantic)
                    {
                        // FIXME: only Copy mistakes are reported now
                        if (managedArgumentSemantic == Helpers.ArgumentSemantic.Copy || nativeArgumentSemantic == Helpers.ArgumentSemantic.Copy)
                        {
                            // FIXME: rule disactivated for now
                            // Log.On (framework).Add ($"!incorrect-argument-semantic! Native '{nativeMethodDefinition}' is declared as ({nativeArgumentSemantic.ToUsableString ().ToLowerInvariant ()}) but mapped to 'ArgumentSemantic.{managedArgumentSemantic.ToUsableString ()}' in '{method}'");
                        }
                    }
                }
            }
        }
예제 #4
0
        public override void VisitObjCPropertyDecl(ObjCPropertyDecl decl)
        {
            if (currentInterfaceDecl == null || currentType == null)
            {
                return;
            }

            PropertyInfo managedProperty = FindProperty(decl);

            if (managedProperty == null)
            {
                return;
            }

            bool nativeHasGetter  = decl.Getter != null;
            bool nativeHasSetter  = decl.Setter != null;
            bool managedHasGetter = managedProperty.CanRead;
            bool managedHasSetter = managedProperty.CanWrite;

            CheckPropertyStatus(nativeHasGetter, managedHasGetter, managedProperty, string.Format("{0} getter on {1}", decl, currentType.Name));
            CheckPropertyStatus(nativeHasSetter, managedHasSetter, managedProperty, string.Format("{0} setter on {1}", decl, currentType.Name));
        }
        public override void VisitObjCPropertyDecl(ObjCPropertyDecl decl)
        {
            if (currentInterfaceDecl == null || currentType == null)
            {
                return;
            }

            PropertyInfo managedProperty = FindProperty(decl);

            if (managedProperty == null)
            {
                return;
            }

            bool nativeHasSetter  = decl.Setter != null;
            bool managedHasSetter = managedProperty.CanWrite;

            if (nativeHasSetter && managedHasSetter)
            {
                ObjCPropertySetterKind nativeSetSemantic = decl.SetterKind;

                // Read as int so we don't have to depend on XM assembly for type
                //	public enum ArgumentSemantic : int {
                //		None = -1,
                //		Assign = 0,
                //		Copy = 1,
                //		Retain = 2,
                //		Weak = 3,
                //		Strong = Retain,
                //		UnsafeUnretained = Assign,
                //	}
                int managedSetSemantic = GetArgumentSemantic(managedProperty.GetSetMethod());

                // If our data type is string or string [], we _better_ be Copy on the native side.
                // Since we copy to/from .NET strings, ignore these to reduce noise
                if (nativeSetSemantic == ObjCPropertySetterKind.Copy &&
                    (managedProperty.PropertyType == typeof(string) || managedProperty.PropertyType == typeof(string [])))
                {
                    return;
                }

                switch (nativeSetSemantic)
                {
                case ObjCPropertySetterKind.Assign:
                    if (managedSetSemantic != 0 && managedSetSemantic != -1)                             // None maps to Assign
                    {
                        ReportError(currentType.Name, managedProperty.Name, managedSetSemantic, nativeSetSemantic);
                    }
                    break;

                case ObjCPropertySetterKind.Retain:
                    if (managedSetSemantic != 2)
                    {
                        ReportError(currentType.Name, managedProperty.Name, managedSetSemantic, nativeSetSemantic);
                    }
                    break;

                case ObjCPropertySetterKind.Copy:
                    if (managedSetSemantic != 1)
                    {
                        ReportError(currentType.Name, managedProperty.Name, managedSetSemantic, nativeSetSemantic);
                    }
                    break;

                case ObjCPropertySetterKind.Weak:
                    if (managedSetSemantic != 3)
                    {
                        ReportError(currentType.Name, managedProperty.Name, managedSetSemantic, nativeSetSemantic);
                    }
                    break;

                default:
                    throw new InvalidOperationException(string.Format("PropertyArgumentSemanticVisitor - Unknown semantic"));
                }
            }
        }