@Override
                public Boolean visitDeclared(DeclaredType a, EqualVisitorParam p) {
                    if (p.type.getKind().equals(DECLARED)) {
                        DeclaredType b = (DeclaredType) p.type;
                        Element aElement = a.asElement();
                        Element bElement = b.asElement();
                        Set<ComparedElements> newVisiting = visitingSetPlus(
                                p.visiting, aElement, a.getTypeArguments(), bElement, b.getTypeArguments());
                        if (newVisiting.equals(p.visiting)) {
                            // We're already visiting this pair of elements.
                            // This can happen for example with Enum in Enum<E extends Enum<E>>. Return a
                            // provisional true value since if the Elements are not in fact equal the original
                            // visitor of Enum will discover that. We have to check both Elements being compared
                            // though to avoid missing the fact that one of the types being compared
                            // differs at exactly this point.
                            return true;
                        }
                        return aElement.equals(bElement)
                                && equal(a.getEnclosingType(), a.getEnclosingType(), newVisiting)
                                && equalLists(a.getTypeArguments(), b.getTypeArguments(), newVisiting);

                    }
                    return false;
                }
Utilities related to {@link TypeMirror} instances.

@author Gregory Kick
@since 2.0
android/annotation_processors/xposed_hook_compiler/src/main/java/github/tornaco/permission/compiler/common/MoreTypes.java