/** * Searches the given field node for annotations and returns each one that matches the provided regular expression pattern. * * Only the simple name is checked - the package and any containing class are ignored. */ public static Annotation[] findAnnotations(FieldDeclaration field, Pattern namePattern) { List<Annotation> result = new ArrayList<Annotation>(); if (field.annotations == null) return EMPTY_ANNOTATIONS_ARRAY; for (Annotation annotation : field.annotations) { TypeReference typeRef = annotation.type; if (typeRef != null && typeRef.getTypeName() != null) { char[][] typeName = typeRef.getTypeName(); String suspect = new String(typeName[typeName.length - 1]); if (namePattern.matcher(suspect).matches()) { result.add(annotation); } } } return result.toArray(EMPTY_ANNOTATIONS_ARRAY); }
/** {@inheritDoc} */ @Override protected EclipseNode buildTree(ASTNode node, Kind kind) { switch (kind) { case COMPILATION_UNIT: return buildCompilationUnit((CompilationUnitDeclaration) node); case TYPE: return buildType((TypeDeclaration) node); case FIELD: return buildField((FieldDeclaration) node); case INITIALIZER: return buildInitializer((Initializer) node); case METHOD: return buildMethod((AbstractMethodDeclaration) node); case ARGUMENT: return buildLocal((Argument) node, kind); case LOCAL: return buildLocal((LocalDeclaration) node, kind); case STATEMENT: return buildStatement((Statement) node); case ANNOTATION: return buildAnnotation((Annotation) node, false); default: throw new AssertionError("Did not expect to arrive here: " + kind); } }
public void setFieldDefaultsForField(EclipseNode fieldNode, ASTNode pos, AccessLevel level, boolean makeFinal) { FieldDeclaration field = (FieldDeclaration) fieldNode.get(); if (level != null && level != AccessLevel.NONE) { if ((field.modifiers & (ClassFileConstants.AccPublic | ClassFileConstants.AccPrivate | ClassFileConstants.AccProtected)) == 0) { if (!hasAnnotation(PackagePrivate.class, fieldNode)) { field.modifiers |= EclipseHandlerUtil.toEclipseModifier(level); } } } if (makeFinal && (field.modifiers & ClassFileConstants.AccFinal) == 0) { if (!hasAnnotation(NonFinal.class, fieldNode)) { if ((field.modifiers & ClassFileConstants.AccStatic) == 0 || field.initialization != null) { field.modifiers |= ClassFileConstants.AccFinal; } } } fieldNode.rebuild(); }
/** * Checks if there is a field with the provided name. * * @param fieldName the field name to check for. * @param node Any node that represents the Type (TypeDeclaration) to look in, or any child node thereof. */ public static MemberExistsResult fieldExists(String fieldName, EclipseNode node) { while (node != null && !(node.get() instanceof TypeDeclaration)) { node = node.up(); } if (node != null && node.get() instanceof TypeDeclaration) { TypeDeclaration typeDecl = (TypeDeclaration)node.get(); if (typeDecl.fields != null) for (FieldDeclaration def : typeDecl.fields) { char[] fName = def.name; if (fName == null) continue; if (fieldName.equals(new String(fName))) { return getGeneratedBy(def) == null ? MemberExistsResult.EXISTS_BY_USER : MemberExistsResult.EXISTS_BY_LOMBOK; } } } return MemberExistsResult.NOT_EXISTS; }
/** * Given a list of field names and a node referring to a type, finds each name in the list that does not match a field within the type. */ public static List<Integer> createListOfNonExistentFields(List<String> list, EclipseNode type, boolean excludeStandard, boolean excludeTransient) { boolean[] matched = new boolean[list.size()]; for (EclipseNode child : type.down()) { if (list.isEmpty()) break; if (child.getKind() != Kind.FIELD) continue; if (excludeStandard) { if ((((FieldDeclaration)child.get()).modifiers & ClassFileConstants.AccStatic) != 0) continue; if (child.getName().startsWith("$")) continue; } if (excludeTransient && (((FieldDeclaration)child.get()).modifiers & ClassFileConstants.AccTransient) != 0) continue; int idx = list.indexOf(child.getName()); if (idx > -1) matched[idx] = true; } List<Integer> problematic = new ArrayList<Integer>(); for (int i = 0 ; i < list.size() ; i++) { if (!matched[i]) problematic.add(i); } return problematic; }
private void makeSimpleSetterMethodForBuilder(EclipseNode builderType, EclipseNode fieldNode, EclipseNode sourceNode, boolean fluent, boolean chain) { TypeDeclaration td = (TypeDeclaration) builderType.get(); AbstractMethodDeclaration[] existing = td.methods; if (existing == null) existing = EMPTY; int len = existing.length; FieldDeclaration fd = (FieldDeclaration) fieldNode.get(); char[] name = fd.name; for (int i = 0; i < len; i++) { if (!(existing[i] instanceof MethodDeclaration)) continue; char[] existingName = existing[i].selector; if (Arrays.equals(name, existingName)) return; } String setterName = fluent ? fieldNode.getName() : HandlerUtil.buildAccessorName("set", fieldNode.getName()); MethodDeclaration setter = HandleSetter.createSetter(td, fieldNode, setterName, chain, ClassFileConstants.AccPublic, sourceNode, Collections.<Annotation>emptyList(), Collections.<Annotation>emptyList()); injectMethod(builderType, setter); }
@Override public List<EclipseNode> generateFields(SingularData data, EclipseNode builderType) { if (useGuavaInstead(builderType)) { return guavaListSetSingularizer.generateFields(data, builderType); } TypeReference type = new QualifiedTypeReference(JAVA_UTIL_ARRAYLIST, NULL_POSS); type = addTypeArgs(1, false, builderType, type, data.getTypeArgs()); FieldDeclaration buildField = new FieldDeclaration(data.getPluralName(), 0, -1); buildField.bits |= ECLIPSE_DO_NOT_TOUCH_FLAG; buildField.modifiers = ClassFileConstants.AccPrivate; buildField.declarationSourceEnd = -1; buildField.type = type; data.setGeneratedByRecursive(buildField); return Collections.singletonList(injectFieldAndMarkGenerated(builderType, buildField)); }
public void setFieldDefaultsForField(EclipseNode fieldNode, ASTNode pos, AccessLevel level, boolean makeFinal) { FieldDeclaration field = (FieldDeclaration) fieldNode.get(); if (level != null && level != AccessLevel.NONE) { if ((field.modifiers & (ClassFileConstants.AccPublic | ClassFileConstants.AccPrivate | ClassFileConstants.AccProtected)) == 0) { if (!hasAnnotation(PackagePrivate.class, fieldNode)) { field.modifiers |= EclipseHandlerUtil.toEclipseModifier(level); } } } if (makeFinal && (field.modifiers & ClassFileConstants.AccFinal) == 0) { if (!hasAnnotation(NonFinal.class, fieldNode)) { field.modifiers |= ClassFileConstants.AccFinal; } } fieldNode.rebuild(); }
private QualifiedAllocationExpression convert( IJavaElement localType, FieldDeclaration enumConstant, CompilationResult compilationResult) throws JavaModelException { TypeDeclaration anonymousLocalTypeDeclaration = convert((SourceType) localType, compilationResult); QualifiedAllocationExpression expression = new QualifiedAllocationExpression(anonymousLocalTypeDeclaration); expression.type = anonymousLocalTypeDeclaration.superclass; anonymousLocalTypeDeclaration.superclass = null; anonymousLocalTypeDeclaration.superInterfaces = null; anonymousLocalTypeDeclaration.allocation = expression; if (enumConstant != null) { anonymousLocalTypeDeclaration.modifiers &= ~ClassFileConstants.AccEnum; expression.enumConstant = enumConstant; expression.type = null; } return expression; }
private ASTNode getEnclosingDeclaration() { int i = this.parentsPtr; while (i > -1) { ASTNode parent = this.parents[i]; if (parent instanceof AbstractMethodDeclaration) { return parent; } else if (parent instanceof Initializer) { return parent; } else if (parent instanceof FieldDeclaration) { return parent; } else if (parent instanceof TypeDeclaration) { return parent; } i--; } return null; }
public RecoveredElement add(FieldDeclaration newFieldDeclaration, int bracketBalanceValue) { resetPendingModifiers(); /* local variables inside initializer can only be final and non void */ char[][] fieldTypeName; if ((newFieldDeclaration.modifiers & ~ClassFileConstants.AccFinal) != 0 /* local var can only be final */ || (newFieldDeclaration.type == null) // initializer || ((fieldTypeName = newFieldDeclaration.type.getTypeName()).length == 1 // non void && CharOperation.equals(fieldTypeName[0], TypeBinding.VOID.sourceName()))){ if (this.parent == null) return this; // ignore this.updateSourceEndIfNecessary(previousAvailableLineEnd(newFieldDeclaration.declarationSourceStart - 1)); return this.parent.add(newFieldDeclaration, bracketBalanceValue); } /* default behavior is to delegate recording to parent if any, do not consider elements passed the known end (if set) it must be belonging to an enclosing element */ if (this.fieldDeclaration.declarationSourceEnd > 0 && newFieldDeclaration.declarationSourceStart > this.fieldDeclaration.declarationSourceEnd){ if (this.parent == null) return this; // ignore return this.parent.add(newFieldDeclaration, bracketBalanceValue); } // still inside initializer, treat as local variable return this; // ignore }
public RecoveredElement add(FieldDeclaration addedfieldDeclaration, int bracketBalanceValue) { /* default behavior is to delegate recording to parent if any */ resetPendingModifiers(); if (this.parent == null) return this; // ignore if (this.fieldDeclaration.declarationSourceStart == addedfieldDeclaration.declarationSourceStart) { if (this.fieldDeclaration.initialization != null) { this.updateSourceEndIfNecessary(this.fieldDeclaration.initialization.sourceEnd); } else { this.updateSourceEndIfNecessary(this.fieldDeclaration.sourceEnd); } } else { this.updateSourceEndIfNecessary(previousAvailableLineEnd(addedfieldDeclaration.declarationSourceStart - 1)); } return this.parent.add(addedfieldDeclaration, bracketBalanceValue); }
public RecoveredElement add(FieldDeclaration fieldDeclaration, int bracketBalanceValue) { resetPendingModifiers(); /* local variables inside method can only be final and non void */ char[][] fieldTypeName; if ((fieldDeclaration.modifiers & ~ClassFileConstants.AccFinal) != 0 // local var can only be final || (fieldDeclaration.type == null) // initializer || ((fieldTypeName = fieldDeclaration.type.getTypeName()).length == 1 // non void && CharOperation.equals(fieldTypeName[0], TypeBinding.VOID.sourceName()))){ this.updateSourceEndIfNecessary(previousAvailableLineEnd(fieldDeclaration.declarationSourceStart - 1)); return this.parent.add(fieldDeclaration, bracketBalanceValue); } /* do not consider a local variable starting passed the block end (if set) it must be belonging to an enclosing block */ if (this.blockDeclaration.sourceEnd != 0 && fieldDeclaration.declarationSourceStart > this.blockDeclaration.sourceEnd){ return this.parent.add(fieldDeclaration, bracketBalanceValue); } // ignore the added field, since indicates a local variable behind recovery point // which thus got parsed as a field reference. This can happen if restarting after // having reduced an assistNode to get the following context (see 1GEK7SG) return this; }
public void duplicateModifierForField(ReferenceBinding type, FieldDeclaration fieldDecl) { /* to highlight modifiers use: this.handle( new Problem( DuplicateModifierForField, new String[] {new String(fieldDecl.name)}, fieldDecl.modifiers.sourceStart, fieldDecl.modifiers.sourceEnd)); */ String[] arguments = new String[] {new String(fieldDecl.name)}; this.handle( IProblem.DuplicateModifierForField, arguments, arguments, fieldDecl.sourceStart, fieldDecl.sourceEnd); }
public void enumConstantMustImplementAbstractMethod(AbstractMethodDeclaration method, FieldDeclaration field) { MethodBinding abstractMethod = method.binding; this.handle( IProblem.EnumConstantMustImplementAbstractMethod, new String[] { new String(abstractMethod.selector), typesAsString(abstractMethod, false), new String(field.name), }, new String[] { new String(abstractMethod.selector), typesAsString(abstractMethod, true), new String(field.name), }, field.sourceStart(), field.sourceEnd()); }
public FieldDeclaration sourceField() { SourceTypeBinding sourceType; try { sourceType = (SourceTypeBinding) this.declaringClass; } catch (ClassCastException e) { return null; } FieldDeclaration[] fields = sourceType.scope.referenceContext.fields; if (fields != null) { for (int i = fields.length; --i >= 0;) if (this == fields[i].binding) return fields[i]; } return null; }
public void generateSyntheticBodyForEnumInitializationMethod(SyntheticMethodBinding methodBinding) { // no local used this.maxLocals = 0; // generate all enum constants SourceTypeBinding sourceTypeBinding = (SourceTypeBinding) methodBinding.declaringClass; TypeDeclaration typeDeclaration = sourceTypeBinding.scope.referenceContext; BlockScope staticInitializerScope = typeDeclaration.staticInitializerScope; FieldDeclaration[] fieldDeclarations = typeDeclaration.fields; for (int i = methodBinding.startIndex, max = methodBinding.endIndex; i < max; i++) { FieldDeclaration fieldDecl = fieldDeclarations[i]; if (fieldDecl.isStatic()) { if (fieldDecl.getKind() == AbstractVariableDeclaration.ENUM_CONSTANT) { fieldDecl.generateCode(staticInitializerScope, this); } } } return_(); }
@Override public boolean process(final Set<? extends TypeElement> annotations, final RoundEnvironment roundEnv) { Set<? extends Element> fields = roundEnv.getElementsAnnotatedWith(Multiline.class); for (Element field : fields) { String docComment = elementUtils.getDocComment(field); if (null != docComment) { VariableElementImpl fieldElem = (VariableElementImpl) field; FieldBinding biding = (FieldBinding) fieldElem._binding; FieldDeclaration decl = biding.sourceField(); StringLiteral string = new StringLiteral(docComment.toCharArray(), decl.sourceStart, decl.sourceEnd, decl.sourceStart); decl.initialization = string; } } return true; }
private void removeFields(TypeDeclaration typeDeclaration) { int start = typeDeclaration.declarationSourceStart; int end = typeDeclaration.declarationSourceEnd; FieldDeclaration[] fieldDeclarations = typeDeclaration.fields; if (fieldDeclarations != null) { for (int i = 0; i < fieldDeclarations.length; i++) { int j = indexOfFisrtNameAfter(start); done : while (j != -1) { int nameStart = this.potentialVariableNameStarts[j]; if (start <= nameStart && nameStart <= end) { if (CharOperation.equals(this.potentialVariableNames[j], fieldDeclarations[i].name, false)) { removeNameAt(j); } } if (end < nameStart) break done; j = indexOfNextName(j); } } } }
public FieldDeclaration updatedFieldDeclaration(int depth, Set knownTypes){ if (this.initializerBody != null){ Block block = this.initializerBody.updatedBlock(depth, knownTypes); if (block != null){ Initializer initializer = (Initializer) this.fieldDeclaration; initializer.block = block; if (initializer.declarationSourceEnd == 0) { initializer.declarationSourceEnd = block.sourceEnd; initializer.bodyEnd = block.sourceEnd; } } if (this.localTypeCount > 0) this.fieldDeclaration.bits |= ASTNode.HasLocalType; } if (this.fieldDeclaration.sourceEnd == 0){ this.fieldDeclaration.sourceEnd = this.fieldDeclaration.declarationSourceEnd; } return this.fieldDeclaration; }
public void visitField(EclipseNode node, FieldDeclaration field) { print("<FIELD%s %s %s = %s%s>", isGenerated(field) ? " (GENERATED)" : "", str(field.type), str(field.name), field.initialization, position(node)); indent++; if (printContent) { if (field.initialization != null) print("%s", field.initialization); disablePrinting++; } }
private EclipseNode buildField(FieldDeclaration field) { if (field instanceof Initializer) return buildInitializer((Initializer)field); if (setAndGetAsHandled(field)) return null; List<EclipseNode> childNodes = new ArrayList<EclipseNode>(); addIfNotNull(childNodes, buildStatement(field.initialization)); childNodes.addAll(buildAnnotations(field.annotations, true)); return putInMap(new EclipseNode(this, field, childNodes, Kind.FIELD)); }
private static List<EclipseNode> findFields(EclipseNode typeNode, boolean nullMarked) { List<EclipseNode> fields = new ArrayList<EclipseNode>(); for (EclipseNode child : typeNode.down()) { if (child.getKind() != Kind.FIELD) continue; FieldDeclaration fieldDecl = (FieldDeclaration) child.get(); if (!filterField(fieldDecl)) continue; boolean isFinal = (fieldDecl.modifiers & ClassFileConstants.AccFinal) != 0; boolean isNonNull = nullMarked && findAnnotations(fieldDecl, NON_NULL_PATTERN).length != 0; if ((isFinal || isNonNull) && fieldDecl.initialization == null) fields.add(child); } return fields; }
static List<EclipseNode> findAllFields(EclipseNode typeNode) { List<EclipseNode> fields = new ArrayList<EclipseNode>(); for (EclipseNode child : typeNode.down()) { if (child.getKind() != Kind.FIELD) continue; FieldDeclaration fieldDecl = (FieldDeclaration) child.get(); if (!filterField(fieldDecl)) continue; // Skip initialized final fields. if (((fieldDecl.modifiers & ClassFileConstants.AccFinal) != 0) && fieldDecl.initialization != null) continue; fields.add(child); } return fields; }
public static boolean isFieldDeprecated(EclipseNode fieldNode) { FieldDeclaration field = (FieldDeclaration) fieldNode.get(); if ((field.modifiers & ClassFileConstants.AccDeprecated) != 0) { return true; } if (field.annotations == null) return false; for (Annotation annotation : field.annotations) { if (typeMatches(Deprecated.class, fieldNode, annotation.type)) { return true; } } return false; }
static TypeReference getFieldType(EclipseNode field, FieldAccess fieldAccess) { boolean lookForGetter = lookForGetter(field, fieldAccess); GetterMethod getter = lookForGetter ? findGetter(field) : null; if (getter == null) { return ((FieldDeclaration)field.get()).type; } return getter.type; }
static Expression createFieldAccessor(EclipseNode field, FieldAccess fieldAccess, ASTNode source) { int pS = source == null ? 0 : source.sourceStart, pE = source == null ? 0 : source.sourceEnd; long p = (long)pS << 32 | pE; boolean lookForGetter = lookForGetter(field, fieldAccess); GetterMethod getter = lookForGetter ? findGetter(field) : null; if (getter == null) { FieldDeclaration fieldDecl = (FieldDeclaration)field.get(); FieldReference ref = new FieldReference(fieldDecl.name, p); if ((fieldDecl.modifiers & ClassFileConstants.AccStatic) != 0) { EclipseNode containerNode = field.up(); if (containerNode != null && containerNode.get() instanceof TypeDeclaration) { ref.receiver = new SingleNameReference(((TypeDeclaration)containerNode.get()).name, p); } else { Expression smallRef = new FieldReference(field.getName().toCharArray(), p); if (source != null) setGeneratedBy(smallRef, source); return smallRef; } } else { ref.receiver = new ThisReference(pS, pE); } if (source != null) { setGeneratedBy(ref, source); setGeneratedBy(ref.receiver, source); } return ref; } MessageSend call = new MessageSend(); setGeneratedBy(call, source); call.sourceStart = pS; call.statementEnd = call.sourceEnd = pE; call.receiver = new ThisReference(pS, pE); setGeneratedBy(call.receiver, source); call.selector = getter.name; return call; }
public static boolean filterField(FieldDeclaration declaration, boolean skipStatic) { // Skip the fake fields that represent enum constants. if (declaration.initialization instanceof AllocationExpression && ((AllocationExpression)declaration.initialization).enumConstant != null) return false; if (declaration.type == null) return false; // Skip fields that start with $ if (declaration.name.length > 0 && declaration.name[0] == '$') return false; // Skip static fields. if (skipStatic && (declaration.modifiers & ClassFileConstants.AccStatic) != 0) return false; return true; }
/** * Inserts a field into an existing type. The type must represent a {@code TypeDeclaration}. */ public static EclipseNode injectField(EclipseNode type, FieldDeclaration field) { TypeDeclaration parent = (TypeDeclaration) type.get(); if (parent.fields == null) { parent.fields = new FieldDeclaration[1]; parent.fields[0] = field; } else { int size = parent.fields.length; FieldDeclaration[] newArray = new FieldDeclaration[size + 1]; System.arraycopy(parent.fields, 0, newArray, 0, size); int index = 0; for (; index < size; index++) { FieldDeclaration f = newArray[index]; if (isEnumConstant(f) || isGenerated(f)) continue; break; } System.arraycopy(newArray, index, newArray, index + 1, size - index); newArray[index] = field; parent.fields = newArray; } if (isEnumConstant(field) || (field.modifiers & Modifier.STATIC) != 0) { if (!hasClinit(parent)) { parent.addClinit(); } } return type.add(field, Kind.FIELD); }
public void generateBuilderFields(EclipseNode builderType, List<BuilderFieldData> builderFields, ASTNode source) { List<EclipseNode> existing = new ArrayList<EclipseNode>(); for (EclipseNode child : builderType.down()) { if (child.getKind() == Kind.FIELD) existing.add(child); } top: for (BuilderFieldData bfd : builderFields) { if (bfd.singularData != null && bfd.singularData.getSingularizer() != null) { bfd.createdFields.addAll(bfd.singularData.getSingularizer().generateFields(bfd.singularData, builderType)); } else { for (EclipseNode exists : existing) { char[] n = ((FieldDeclaration) exists.get()).name; if (Arrays.equals(n, bfd.name)) { bfd.createdFields.add(exists); continue top; } } FieldDeclaration fd = new FieldDeclaration(bfd.name, 0, 0); fd.bits |= Eclipse.ECLIPSE_DO_NOT_TOUCH_FLAG; fd.modifiers = ClassFileConstants.AccPrivate; fd.type = copyType(bfd.type); fd.traverse(new SetGeneratedByVisitor(source), (MethodScope) null); bfd.createdFields.add(injectFieldAndMarkGenerated(builderType, fd)); } } }