public override void ProcessAnnotation(AnnotatedItem item)
        {
            if (item.ManagedInfo.Type.Name == null)
            {
                return;
            }

            foreach (var a in item.Annotations)
            {
                if (a.Values == null || a.Name != "RequiresPermission")
                {
                    continue;
                }
                for (int i = 0; i < a.Values.Count; i++)
                {
                    var v = a.Values [i];
                    if (v.Name != "value")
                    {
                        continue;
                    }
                    var ext = item.GetExtension <RequiresPermissionExtension> ();
                    if (ext == null)
                    {
                        ext = new RequiresPermissionExtension();
                        item.SetExtension(ext);
                    }
                    // value is quoted by "", so chop them out.
                    string val = v.Val.Substring(1, v.Val.Length - 2);
                    if (!ext.Values.Contains(val))
                    {
                        ext.Values.Add(val);
                    }
                }
            }
        }
Beispiel #2
0
 public static string FormatMember(this AnnotatedItem a)
 {
     return(string.Format("  [{0}] {1} {2} {3}",
                          a.Arguments == null ? "F" : a.ParameterIndex >= 0 ? ("P" + a.ParameterIndex) : a.MemberName == "#ctor" ? "C" : "M",
                          a.MemberType,
                          a.MemberName,
                          a.Arguments == null ? null : "(" + string.Join(", ", a.Arguments) + ")"));
 }
Beispiel #3
0
 static bool IsProperty(AnnotatedItem item, string propertyName)
 {
     if (item.Arguments == null)
     {
         return(false);
     }
     return(item.ManagedInfo.MemberName == "get_" + propertyName && item.Arguments.Length == 0 ||
            item.ManagedInfo.MemberName == "set_" + propertyName && item.Arguments.Length == 1);
 }
        public override IMethodBase GetMethod(IType iType, AnnotatedItem item)
        {
            var t       = iType.Value();
            var list    = t.GetMethods().Where(m => item.MemberName == "#ctor" ? m is Ctor : m is Method);
            var methods = list.Where(m =>
                                     (item.MemberName == "#ctor" && m is Ctor || m is Method && ((Method)m).JavaName == item.MemberName) &&
                                     m.Parameters.Count == item.Arguments.Length)
                          .ToArray();

            var argTypeLists = methods.Select(m => new { Method = m, Jni = m is Ctor ? ((Ctor)m).JniSignature : ((Method)m).JniSignature })
                               .Select(p => new { Method = p.Method, Arguments = p.Jni == null ? null : ParseJniMethodArgumentsSignature(p.Jni) })
                               .ToArray();

            // this .Replace() is needed so that T[] can match generic arguments
            Func <string, string>       stripParamSuffix = s => s.Replace("...", "").Replace("[]", "");
            Func <string, string>       stripGenParams   = s => s == null ? s : (s.Contains('<') ? s.Substring(0, s.IndexOf('<')) : s).Replace("...", "[]");
            Func <string, string, bool> cmp = (v, w) => stripGenParams(v) == stripGenParams(w);

            for (int i = 0; i < argTypeLists.Length; i++)
            {
                var argTypeListPair = argTypeLists [i];
                var argTypeList     = argTypeListPair.Arguments;
                if (argTypeList == null || item.Arguments.Length != argTypeList.Length)
                {
                    continue;
                }

                bool mismatch = false;
                for (int a = 0; a < argTypeList.Length; a++)
                {
                    if (cmp(argTypeList [a], item.Arguments [a]) ||
                        t.TypeParameters != null && t.TypeParameters.Any(ga => cmp(ga.Name, stripParamSuffix(item.Arguments [a]))) ||
                        argTypeListPair.Method.GenericArguments != null && argTypeListPair.Method.GenericArguments.Any(ga => cmp(ga.Name, stripParamSuffix(item.Arguments [a]))))
                    {
                        continue;
                    }
                    mismatch = true;
                    break;
                }
                if (mismatch)
                {
                    continue;
                }
                return(methods [i].Wrap());
            }
            Errors.Add("warning: method overload not found: " + t.FullName + " member: " + item.FormatMember());
            return(null);
        }
        protected string GetTargetManagedTypeName(AnnotatedItem item)
        {
            var contextType  = _.GetContextManagedType(item.TypeName);
            var contextField = item.Arguments == null?_.GetAnnotatedField(contextType, item.MemberName) : null;

            if (item.Arguments == null)
            {
                return(contextField == null ? null :_.GetFieldManagedTypeName(contextField));
            }
            var contextMethod = item.Arguments == null ? null : _.GetMethod(contextType, item);

            if (contextMethod != null)
            {
                return(item.ParameterIndex < 0 ?
                       _.GetMethodReturnManagedTypeName(contextMethod) :
                       _.GetParameterManagedTypeName(contextMethod, item.ParameterIndex));
            }
            return(null);
        }
Beispiel #6
0
        public override void ProcessAnnotation(AnnotatedItem item)
        {
            if (item.ManagedInfo.Type.Name == null)
            {
                return;
            }

            foreach (var a in item.Annotations)
            {
                if (a.Values == null || a.Name.Contains('.') || !a.Name.EndsWith("Def", StringComparison.Ordinal))
                {
                    continue;
                }
                for (int i = 0; i < a.Values.Count; i++)
                {
                    var v = a.Values [i];
                    if (v.Name != "value")
                    {
                        continue;
                    }
                    ProcessAnnotationValue(item, a, v);
                }
            }
        }
Beispiel #7
0
 public abstract IMethodBase GetMethod(IType t, AnnotatedItem item);
Beispiel #8
0
        void ProcessAnnotationValue(AnnotatedItem item, AnnotationData a, AnnotationValue v)
        {
            var x = new ConstantDefinitionExtension();

            x.ConstantKind =
                a.Name == "IntDef" ? ConstantKind.IntDef :
                a.Name == "StringDef" ? ConstantKind.StringDef :
                ConstantKind.Other;
            x.TargetManagedTypeName = GetTargetManagedTypeName(item);
            x.Flag = a.Values.Any(_ => _.Name == "flag");
            a.SetExtension(x);

            x.ManagedConstants = v.ValueAsArray.Select(s => new ManagedMemberInfo()).ToArray();

            if (v.ArrayItemCommonPrefix != null)
            {
                // Most of the *Def values share the same type as the const fields' declaring type.
                var vManagedType = _.GetContextManagedType(v.ArrayItemCommonPrefix);
                if (vManagedType == null)
                {
                    _.Errors.Add(string.Format("Managed type for '{0}' specified in the annotation '{1}' on '{2}' was not found",
                                               v.ArrayItemCommonPrefix, a.Name, item.Name));
                }
                else
                {
                    var missingConsts = new List <string> ();
                    for (int c = 0; c < x.ManagedConstants.Count; c++)
                    {
                        var m  = x.ManagedConstants [c];
                        var mf = _.GetDefinitionField(vManagedType, v.ValueAsArray [c]);
                        if (mf == null)
                        {
                            // it is most likely removed constants due to enumification.
                            missingConsts.Add(v.ValueAsArray [c]);
                        }
                        else
                        {
                            _.SetName(m, vManagedType);
                            m.MemberName = _.GetDefinitionName(mf);
                        }
                    }
                    if (missingConsts.Count != 0 && /*x.ManagedConstants.Count != missingConsts.Count*/ !x.IsTargetAlreadyEnumified)
                    {
                        _.Errors.Add(string.Format("Warning: For '{0}', managed constants are partially missing in {1}: {2}",
                                                   item.Name, v.ArrayItemCommonPrefix, string.Join(", ", missingConsts)));
                    }
                }
            }
            else
            {
                // Sometimes (namely "PendingIntent flags") have different declaring types and
                // in that case this lookup is somewhat complicated - we find the "type name . field name" matches.
                // As of XA 5.3, nothing should matter - the only pattern that falls here is about
                // wherever PendingIntentFlags apply.
                for (int c = 0; c < v.ValueAsArray.Count; c++)
                {
                    var javaConst = v.ValueAsArray [c];
                    var candidate = _.ContextTypes.Keys.Where(j => !string.IsNullOrEmpty(j) && (javaConst.StartsWith(j, StringComparison.Ordinal)))
                                    .Select(j => _.GetContextManagedType(j))
                                    .Select(mn => new { Type = mn, Field = _.GetFields(mn).FirstOrDefault(f => javaConst.EndsWith("." + _.GetJavaName(f), StringComparison.Ordinal)) })
                                    .FirstOrDefault(z => z.Field != null);
                    if (candidate == null)
                    {
                        continue;
                    }
                    var m = x.ManagedConstants [c];
                    _.SetName(m, candidate.Type);
                    m.MemberName = _.GetDefinitionName(candidate.Field);
                    break;
                }
            }
        }
 public abstract void ProcessAnnotation(AnnotatedItem item);
Beispiel #10
0
        public override IMethodBase GetMethod(IType iType, AnnotatedItem item)
        {
            var t = iType.Value();
            Func <ICustomAttributeProvider, string> getRegisterAttName = type => {
                var ca = getRegisterAtt(type);
                return(ca == null ? null : ca.ConstructorArguments [0].Value as string);
            };
            Func <ICustomAttributeProvider, string> getRegisterAttJni = type => {
                var ca = getRegisterAtt(type);
                return(ca == null ? null : ca.ConstructorArguments [1].Value as string);
            };

            var methods = t.GetMethods()
                          .Where(m => (item.MemberName == "#ctor" && m.IsConstructor || getRegisterAttName(m) == item.MemberName) && m.Parameters.Count == item.Arguments.Length)
                          .ToArray();

            // First, try loose match just by checking argument count.

            MethodDefinition candidate  = null;
            bool             overloaded = false;

            foreach (var m in methods)
            {
                if (overloaded)
                {
                    break;
                }
                if (candidate != null)
                {
                    overloaded = true;
                    break;
                }
                else
                {
                    candidate = m;
                }
            }
            if (!overloaded)
            {
                if (candidate == null)
                {
                    Errors.Add("warning: method with matching argument count not found: " + t + " member: " + item.FormatMember());
                }
                return(candidate.Wrap());
            }

            // Second, try strict match.

            Func <ICustomAttributeProvider, string []> getJavaGenTypesValue = td => {
                var a   = getJavaTypesAtt(td);
                var arr = a == null ? new string [0] : ((CustomAttributeArgument [])a.ConstructorArguments [0].Value).Select(ca => ca.Value as string);
                return(arr.Select(s => s.Contains(' ') ? s.Substring(0, s.IndexOf(' ')) : s).ToArray());
            };
            var typeGenArgs = t.GetSelfAndAncestors().SelectMany(getJavaGenTypesValue).ToArray();

            var argTypeLists = methods.Select(m => new { Method = m, Jni = getRegisterAttJni(m) })
                               .Select(p => new { Method = p.Method, Arguments = p.Jni == null ? null : ParseJniMethodArgumentsSignature(p.Jni) })
                               .ToArray();

            for (int i = 0; i < argTypeLists.Length; i++)
            {
                var argTypeListPair = argTypeLists [i];
                var argTypeList     = argTypeListPair.Arguments;
                var methodGenArgs   = getJavaGenTypesValue(argTypeListPair.Method);
                if (!AreArgumentsEqualLax(argTypeList, item.Arguments, typeGenArgs.Concat(methodGenArgs)))
                {
                    continue;
                }
                return(methods [i].Wrap());
            }
            Errors.Add("warning: method overload not found: " + t + " member: " + item.FormatMember());
            return(null);
        }