Skip to content

Commit

Permalink
GROOVY-11299: prep work
Browse files Browse the repository at this point in the history
  • Loading branch information
eric-milles committed Jan 28, 2024
1 parent 55d4369 commit 98b2d29
Show file tree
Hide file tree
Showing 10 changed files with 87 additions and 118 deletions.
25 changes: 13 additions & 12 deletions src/main/java/org/codehaus/groovy/ast/ClassNode.java
Original file line number Diff line number Diff line change
Expand Up @@ -867,9 +867,9 @@ public void positionStmtsAfterEnumInitStmts(List<Statement> staticFieldStatement
}

/**
* This method returns a list of all methods of the given name
* defined in the current class
* @return the method list
* Returns a list of all methods with the given name from this class.
*
* @return method list (possibly empty)
* @see #getMethods(String)
*/
public List<MethodNode> getDeclaredMethods(String name) {
Expand All @@ -880,25 +880,26 @@ public List<MethodNode> getDeclaredMethods(String name) {
}

/**
* This method creates a list of all methods with this name of the
* current class and of all super classes
* @return the methods list
* Returns a list of all methods with the given name from this class and its
* super class(es).
*
* @return method list (possibly empty)
* @see #getDeclaredMethods(String)
*/
public List<MethodNode> getMethods(String name) {
List<MethodNode> result = new ArrayList<>();
List<MethodNode> list = new ArrayList<>(4);
ClassNode node = this;
while (node != null) {
result.addAll(node.getDeclaredMethods(name));
list.addAll(node.getDeclaredMethods(name));
node = node.getSuperClass();
}
return result;
return list;
}

/**
* Finds a method matching the given name and parameters in this class.
*
* @return the method matching the given name and parameters or null
* @return method node or null
*/
public MethodNode getDeclaredMethod(String name, Parameter[] parameters) {
for (MethodNode method : getDeclaredMethods(name)) {
Expand All @@ -911,9 +912,9 @@ public MethodNode getDeclaredMethod(String name, Parameter[] parameters) {

/**
* Finds a method matching the given name and parameters in this class
* or any parent class.
* or any super class.
*
* @return the method matching the given name and parameters or null
* @return method node or null
*/
public MethodNode getMethod(String name, Parameter[] parameters) {
for (MethodNode method : getMethods(name)) {
Expand Down
11 changes: 4 additions & 7 deletions src/main/java/org/codehaus/groovy/ast/InnerClassNode.java
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@
import java.util.LinkedList;

/**
* Represents an inner class declaration
* Represents an inner class definition.
*/
public class InnerClassNode extends ClassNode {

Expand All @@ -37,7 +37,7 @@ public class InnerClassNode extends ClassNode {
* @param superClass the base class name - use "java.lang.Object" if no direct base class
*/
public InnerClassNode(ClassNode outerClass, String name, int modifiers, ClassNode superClass) {
this(outerClass, name, modifiers, superClass, ClassHelper.EMPTY_TYPE_ARRAY, MixinNode.EMPTY_ARRAY);
this(outerClass, name, modifiers, superClass, ClassNode.EMPTY_ARRAY, MixinNode.EMPTY_ARRAY);
}

/**
Expand All @@ -50,7 +50,7 @@ public InnerClassNode(ClassNode outerClass, String name, int modifiers, ClassNod
this.outerClass = outerClass;

if (outerClass.innerClasses == null)
outerClass.innerClasses = new LinkedList<InnerClassNode> ();
outerClass.innerClasses = new LinkedList<>();
outerClass.innerClasses.add(this);
}

Expand All @@ -59,17 +59,14 @@ public ClassNode getOuterClass() {
return outerClass;
}

public ClassNode getOuterMostClass() {
public ClassNode getOuterMostClass() {
ClassNode outerClass = getOuterClass();
while (outerClass instanceof InnerClassNode) {
outerClass = outerClass.getOuterClass();
}
return outerClass;
}

/**
* @return the field node on the outer class or null if this is not an inner class
*/
@Override
public FieldNode getOuterField(String name) {
return outerClass.getDeclaredField(name);
Expand Down
20 changes: 10 additions & 10 deletions src/main/java/org/codehaus/groovy/classgen/InnerClassVisitor.java
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,6 @@
import org.codehaus.groovy.ast.stmt.ExpressionStatement;
import org.codehaus.groovy.control.CompilationUnit;
import org.codehaus.groovy.control.SourceUnit;
import org.codehaus.groovy.transform.trait.Traits;

import java.util.ArrayList;
import java.util.Arrays;
Expand All @@ -50,6 +49,7 @@
import static org.codehaus.groovy.ast.tools.GeneralUtils.callX;
import static org.codehaus.groovy.ast.tools.GeneralUtils.constX;
import static org.codehaus.groovy.ast.tools.GeneralUtils.varX;
import static org.codehaus.groovy.transform.trait.Traits.isTrait;
import static org.objectweb.asm.Opcodes.ACC_FINAL;
import static org.objectweb.asm.Opcodes.ACC_PUBLIC;
import static org.objectweb.asm.Opcodes.ACC_STATIC;
Expand Down Expand Up @@ -85,12 +85,12 @@ public void visitClass(ClassNode node) {

super.visitClass(node);

if (node.isEnum() || node.isInterface()) return;
if (innerClass == null) return;

if (node.getSuperClass().isInterface() || Traits.isAnnotatedWithTrait(node.getSuperClass())) {
node.addInterface(node.getUnresolvedSuperClass());
node.setUnresolvedSuperClass(ClassHelper.OBJECT_TYPE);
if (innerClass != null && innerClass.isAnonymous()) {
ClassNode upperClass= node.getUnresolvedSuperClass(false);
if (upperClass.isInterface() || isTrait(upperClass)) {
node.addInterface(upperClass);
node.setUnresolvedSuperClass(ClassHelper.OBJECT_TYPE);
}
}
}

Expand Down Expand Up @@ -150,9 +150,9 @@ public void visitConstructorCallExpression(ConstructorCallExpression call) {

InnerClassNode innerClass = (InnerClassNode) call.getType();
ClassNode outerClass = innerClass.getOuterClass();
ClassNode superClass = innerClass.getSuperClass();
if (!superClass.isInterface() && superClass.getOuterClass() != null
&& !(superClass.isStaticClass() || (superClass.getModifiers() & ACC_STATIC) != 0)) {
ClassNode upperClass = innerClass.getUnresolvedSuperClass(false);
if (upperClass.getOuterClass() != null && !upperClass.isInterface()
&& !(upperClass.isStaticClass() || (upperClass.getModifiers() & ACC_STATIC) != 0)) {
insertThis0ToSuperCall(call, innerClass);
}
if (!innerClass.getDeclaredConstructors().isEmpty()) return;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -61,11 +61,11 @@ public GenericsVisitor(final SourceUnit source) {

@Override
public void visitClass(final ClassNode node) {
ClassNode sn = node.getUnresolvedSuperClass(false);
if (checkWildcard(sn)) return;
ClassNode sc = node.getUnresolvedSuperClass(false);
if (checkWildcard(sc)) return;

boolean isAIC = node instanceof InnerClassNode && ((InnerClassNode) node).isAnonymous();
checkGenericsUsage(sn, node.getSuperClass(), isAIC ? Boolean.TRUE : null);
checkGenericsUsage(sc, sc.redirect(), isAIC ? Boolean.TRUE : null);
for (ClassNode face : node.getInterfaces()) {
checkGenericsUsage(face);
}
Expand Down
13 changes: 6 additions & 7 deletions src/main/java/org/codehaus/groovy/control/ResolveVisitor.java
Original file line number Diff line number Diff line change
Expand Up @@ -948,15 +948,14 @@ private static boolean isVisibleNestedClass(final ClassNode innerType, final Cla

private boolean directlyImplementsTrait(final ClassNode trait) {
ClassNode[] interfaces = currentClass.getInterfaces();
if (interfaces == null) {
return currentClass.getSuperClass().equals(trait);
}
for (ClassNode node : interfaces) {
if (node.equals(trait)) {
return true;
if (interfaces != null) {
for (ClassNode face : interfaces) {
if (face.equals(trait)) {
return true;
}
}
}
return currentClass.getSuperClass().equals(trait);
return currentClass.getUnresolvedSuperClass().equals(trait);
}

private void checkThisAndSuperAsPropertyAccess(final PropertyExpression expression) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -219,7 +219,7 @@ && getSourceUnit().getAST().getClasses().contains(traitType.redirect())) {
traitType.redirect().setNodeMetaData(UNRESOLVED_HELPER_CLASS, helperType);
return helperType;
}
return Traits.findHelper(traitType);
return Traits.findHelper(traitType).getPlainNodeReference();
}

private ClassNode getTraitSuperTarget(final Expression exp) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -133,23 +133,22 @@ public void visit(final ASTNode[] nodes, final SourceUnit source) {

private void checkNoConstructor(final ClassNode cNode) {
if (!cNode.getDeclaredConstructors().isEmpty()) {
addError("Error processing trait '" + cNode.getName() + "'. " + " Constructors are not allowed.", cNode);
addError("Error processing trait '" + cNode.getName() + "'. Constructors are not allowed.", cNode);
}
}

private void checkExtendsClause(final ClassNode cNode) {
ClassNode superClass = cNode.getSuperClass();
ClassNode superClass = cNode.getUnresolvedSuperClass(false);
if (superClass.isInterface() && !Traits.isTrait(superClass)) {
addError("Trait cannot extend an interface. Use 'implements' instead", cNode);
addError("A trait cannot extend an interface. Use 'implements' instead.", cNode);
}
}

private static void replaceExtendsByImplements(final ClassNode cNode) {
ClassNode superClass = cNode.getUnresolvedSuperClass();
ClassNode superClass = cNode.getUnresolvedSuperClass(false);
if (Traits.isTrait(superClass)) {
// move from super class to interface
cNode.setSuperClass(OBJECT_TYPE);
cNode.setUnresolvedSuperClass(OBJECT_TYPE);
cNode.addInterface(superClass);
}
}
Expand Down Expand Up @@ -537,7 +536,7 @@ private void processField(final FieldNode field, final MethodNode initializer, f
FieldNode dummyField = new FieldNode(
dummyFieldName,
ACC_PUBLIC | ACC_STATIC | ACC_FINAL | ACC_SYNTHETIC,
field.getOriginType().getPlainNodeReference(),
field.getOriginType(),
fieldHelper,
null
);
Expand Down
Loading

0 comments on commit 98b2d29

Please sign in to comment.