|
| 1 | +/** |
| 2 | + * @name Local variable shadows instance field (except final this-copy) |
| 3 | + * @description Flags local variables that shadow an instance field, unless they are final |
| 4 | + * and initialized directly from that same field (for example `final var name = this.name;`). |
| 5 | + * @id custom-java/local-shadows-instance-field-strict |
| 6 | + * @kind problem |
| 7 | + * @problem.severity warning |
| 8 | + * @precision medium |
| 9 | + * @tags correctness readability maintainability |
| 10 | + */ |
| 11 | +import java |
| 12 | +import semmle.code.java.Member |
| 13 | +import semmle.code.java.Variable |
| 14 | + |
| 15 | +/** |
| 16 | + * True if this local variable is an allowed shadowing of the given instance field: |
| 17 | + * |
| 18 | + * final var name = this.name; |
| 19 | + * final var name = name; // implicit this |
| 20 | + */ |
| 21 | +predicate allowedShadowing(LocalVariableDecl local, Field field) { |
| 22 | + local.isFinal() and |
| 23 | + exists(FieldAccess fa | |
| 24 | + fa = local.getInitializer().getUnderlyingExpr().(FieldAccess) and |
| 25 | + fa.getField() = field and |
| 26 | + fa.isOwnFieldAccess() |
| 27 | + ) |
| 28 | +} |
| 29 | + |
| 30 | +from LocalVariableDecl local, Field field, Callable c |
| 31 | +where |
| 32 | + // same simple name |
| 33 | + local.getName() = field.getName() and |
| 34 | + |
| 35 | + // only consider instance fields |
| 36 | + not field.isStatic() and |
| 37 | + |
| 38 | + // local is inside a callable of a class related to the field's declaring type |
| 39 | + c = local.getCallable() and |
| 40 | + c.getDeclaringType().getASupertype*() = field.getDeclaringType() and |
| 41 | + |
| 42 | + // shadowing is NOT in the allowed final-this-copy form |
| 43 | + not allowedShadowing(local, field) |
| 44 | +select local, |
| 45 | + "Local variable '" + local.getName() + "' shadows instance field '" + |
| 46 | + field.getQualifiedName() + |
| 47 | + "'. Shadowing is only allowed for 'final' locals directly initialized from this field." |
0 commit comments