boolean annotationApplicable(JCAnnotation a, Symbol s) {
        Attribute.Compound atTarget =
            a.annotationType.type.tsym.attribute(syms.annotationTargetType.tsym);
        if (atTarget == null) return true;
        Attribute atValue = atTarget.member(names.value);
        if (!(atValue instanceof Attribute.Array)) return true; // error recovery
        Attribute.Array arr = (Attribute.Array) atValue;
        for (Attribute app : arr.values) {
            if (!(app instanceof Attribute.Enum)) return true; // recovery
            Attribute.Enum e = (Attribute.Enum) app;
            if (e.value.name == names.TYPE)
                { if (s.kind == TYP) return true; }
            else if (e.value.name == names.FIELD)
                { if (s.kind == VAR && s.owner.kind != MTH) return true; }
            else if (e.value.name == names.METHOD)
                { if (s.kind == MTH && !s.isConstructor()) return true; }
            else if (e.value.name == names.PARAMETER)
                { if (s.kind == VAR &&
                      s.owner.kind == MTH &&
                      (s.flags() & PARAMETER) != 0)
                    return true;
                }
            else if (e.value.name == names.CONSTRUCTOR)
                { if (s.kind == MTH && s.isConstructor()) return true; }
            else if (e.value.name == names.LOCAL_VARIABLE)
                { if (s.kind == VAR && s.owner.kind == MTH &&
                      (s.flags() & PARAMETER) == 0)
                    return true;
                }
            else if (e.value.name == names.ANNOTATION_TYPE)
                { if (s.kind == TYP && (s.flags() & ANNOTATION) != 0)
                    return true;
                }
            else if (e.value.name == names.PACKAGE)
                { if (s.kind == PCK) return true; }
            else if (e.value.name == names.TYPE_USE)
                { if (s.kind == TYP ||
                      s.kind == VAR ||
                      (s.kind == MTH && !s.isConstructor() &&
                       s.type.getReturnType().tag != VOID))
                    return true;
                }
            else
                return true; // recovery
        }
        return false;
    }