java:S2696 not raised when the static-field write target is wrapped in parentheses

Product: SonarQube Community Build 26.5.0.122743
sonar-java version: sonar-java 8.29 (build 43460)
sonar-java SE version: sonar-java-symbolic-execution 8.16.4 (build 1912)
Java source level: 21 (javac 21, source/target 21)

Rule

java:S2696 — Instance methods should not write to “static” fields

Description

S2696 flags an instance method that writes to a static field. The check inspects the operand of the increment/assignment but does not unwrap a ParenthesizedTree. Per JLS 15.8.5, (ClassName.counter)++ denotes exactly the same variable write as ClassName.counter++; the parentheses are a pure no-op. Wrapping the target in parentheses makes the rule miss the write.

Reproducer

// BEFORE — S2696 raised
public class S2696Before {
  public static int counter;
  void bar() {
    S2696Before.counter++;       // Noncompliant
  }
}

// AFTER — semantically identical, S2696 NOT raised
public class S2696After {
  public static int counter;
  void bar() {
    (S2696After.counter)++;      // no issue (FN)
  }
}

Expected behavior

S2696 should be raised on both forms. The increment writes to the static field counter from an instance method in both cases; parenthesizing the assignment target does not change the variable being written.

Actual behavior

  • BEFORE: java:S2696 (CRITICAL) raised on S2696Before.counter++.
  • AFTER: no issue. The added parentheses around the static-field access defeat the matcher.