mirror of
https://github.com/openjdk/jdk.git
synced 2026-01-28 03:58:21 +00:00
8155591: Misleading warning when not overriding close method in interface extending AutoCloseable
Reviewed-by: jlahoda
This commit is contained in:
parent
2d924ad358
commit
a5864582da
@ -1982,7 +1982,7 @@ public class Attr extends JCTree.Visitor {
|
||||
twrResult.check(resource, resource.type);
|
||||
|
||||
//check that resource type cannot throw InterruptedException
|
||||
checkAutoCloseable(resource.pos(), localEnv, resource.type);
|
||||
checkAutoCloseable(localEnv, resource, true);
|
||||
|
||||
VarSymbol var = ((JCVariableDecl) resource).sym;
|
||||
|
||||
@ -2031,7 +2031,9 @@ public class Attr extends JCTree.Visitor {
|
||||
}
|
||||
}
|
||||
|
||||
void checkAutoCloseable(DiagnosticPosition pos, Env<AttrContext> env, Type resource) {
|
||||
void checkAutoCloseable(Env<AttrContext> env, JCTree tree, boolean useSite) {
|
||||
DiagnosticPosition pos = tree.pos();
|
||||
Type resource = tree.type;
|
||||
if (!resource.isErroneous() &&
|
||||
types.asSuper(resource, syms.autoCloseableType.tsym) != null &&
|
||||
!types.isSameType(resource, syms.autoCloseableType)) { // Don't emit warning for AutoCloseable itself
|
||||
@ -2049,9 +2051,15 @@ public class Attr extends JCTree.Visitor {
|
||||
log.popDiagnosticHandler(discardHandler);
|
||||
}
|
||||
if (close.kind == MTH &&
|
||||
close.overrides(syms.autoCloseableClose, resource.tsym, types, true) &&
|
||||
(useSite || close.owner != syms.autoCloseableType.tsym) &&
|
||||
((MethodSymbol)close).binaryOverrides(syms.autoCloseableClose, resource.tsym, types) &&
|
||||
chk.isHandled(syms.interruptedExceptionType, types.memberType(resource, close).getThrownTypes())) {
|
||||
log.warning(pos, LintWarnings.TryResourceThrowsInterruptedExc(resource));
|
||||
if (!useSite && close.owner == resource.tsym) {
|
||||
log.warning(TreeInfo.diagnosticPositionFor(close, tree),
|
||||
LintWarnings.TryResourceCanThrowInterruptedExc(resource));
|
||||
} else {
|
||||
log.warning(pos, LintWarnings.TryResourceThrowsInterruptedExc(resource));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -5649,7 +5657,7 @@ public class Attr extends JCTree.Visitor {
|
||||
chk.checkImplementations(tree);
|
||||
|
||||
//check that a resource implementing AutoCloseable cannot throw InterruptedException
|
||||
checkAutoCloseable(tree.pos(), env, c.type);
|
||||
checkAutoCloseable(env, tree, false);
|
||||
|
||||
for (List<JCTree> l = tree.defs; l.nonEmpty(); l = l.tail) {
|
||||
// Attribute declaration
|
||||
|
||||
@ -2368,6 +2368,11 @@ compiler.warn.try.resource.not.referenced=\
|
||||
compiler.warn.try.resource.throws.interrupted.exc=\
|
||||
auto-closeable resource {0} has a member method close() that could throw InterruptedException
|
||||
|
||||
# 0: type
|
||||
# lint: try
|
||||
compiler.warn.try.resource.can.throw.interrupted.exc=\
|
||||
close() method can throw InterruptedException in auto-closeable class {0}
|
||||
|
||||
# lint: unchecked
|
||||
compiler.warn.unchecked.assign=\
|
||||
unchecked assignment: {0} to {1}
|
||||
|
||||
@ -228,7 +228,8 @@ public class InterruptedExceptionTest {
|
||||
|
||||
public void report(Diagnostic<? extends JavaFileObject> diagnostic) {
|
||||
if (diagnostic.getKind() == Diagnostic.Kind.WARNING &&
|
||||
diagnostic.getCode().contains("try.resource.throws.interrupted.exc")) {
|
||||
(diagnostic.getCode().contains("try.resource.throws.interrupted.exc") ||
|
||||
diagnostic.getCode().contains("try.resource.can.throw.interrupted.exc"))) {
|
||||
tryWarnFound++;
|
||||
}
|
||||
}
|
||||
|
||||
@ -0,0 +1,256 @@
|
||||
/*
|
||||
* @test /nodynamiccopyright/
|
||||
* @bug 8155591
|
||||
* @summary Verify cases where no AutoCloseable InterruptedException warning should be generated
|
||||
* @compile/ref=InterruptedExceptionTest2.out -XDrawDiagnostics -Xlint:try InterruptedExceptionTest2.java
|
||||
*/
|
||||
|
||||
import java.util.function.Supplier;
|
||||
|
||||
// Here's an interface and a class that we can inherit declaring offending close() methods
|
||||
|
||||
interface HasClose {
|
||||
void close() throws Exception;
|
||||
}
|
||||
|
||||
class WithConcreteClose {
|
||||
public void close() throws Exception { }
|
||||
}
|
||||
|
||||
abstract class WithAbstractClose {
|
||||
public abstract void close() throws Exception;
|
||||
}
|
||||
|
||||
// Interface declaration tests
|
||||
|
||||
interface InterruptedExceptionTest_I1 extends AutoCloseable {
|
||||
}
|
||||
|
||||
interface InterruptedExceptionTest_I2 extends AutoCloseable {
|
||||
@Override void close();
|
||||
}
|
||||
|
||||
interface InterruptedExceptionTest_I3 extends AutoCloseable {
|
||||
@Override void close() throws InterruptedException; // warning here
|
||||
}
|
||||
|
||||
interface InterruptedExceptionTest_I4 extends AutoCloseable {
|
||||
@Override void close() throws Exception; // warning here
|
||||
}
|
||||
|
||||
interface InterruptedExceptionTest_I5 extends AutoCloseable {
|
||||
@Override default void close() { }
|
||||
}
|
||||
|
||||
interface InterruptedExceptionTest_I6 extends AutoCloseable {
|
||||
@Override default void close() throws InterruptedException { } // warning here
|
||||
}
|
||||
|
||||
interface InterruptedExceptionTest_I7 extends AutoCloseable {
|
||||
@Override default void close() throws Exception { } // warning here
|
||||
}
|
||||
|
||||
interface InterruptedExceptionTest_I8 extends HasClose, AutoCloseable {
|
||||
}
|
||||
|
||||
interface InterruptedExceptionTest_I9 extends HasClose, AutoCloseable {
|
||||
@Override void close();
|
||||
}
|
||||
|
||||
// Abstract class declaration tests
|
||||
|
||||
abstract class InterruptedExceptionTest_C1 implements AutoCloseable {
|
||||
}
|
||||
|
||||
abstract class InterruptedExceptionTest_C2 implements AutoCloseable {
|
||||
@Override public abstract void close();
|
||||
}
|
||||
|
||||
abstract class InterruptedExceptionTest_C3 implements AutoCloseable {
|
||||
@Override public abstract void close() throws InterruptedException; // warning here
|
||||
}
|
||||
|
||||
abstract class InterruptedExceptionTest_C4 implements AutoCloseable {
|
||||
@Override public abstract void close() throws Exception; // warning here
|
||||
}
|
||||
|
||||
abstract class InterruptedExceptionTest_C5 implements AutoCloseable {
|
||||
@Override public void close() { }
|
||||
}
|
||||
|
||||
abstract class InterruptedExceptionTest_C6 implements AutoCloseable {
|
||||
@Override public void close() throws InterruptedException { } // warning here
|
||||
}
|
||||
|
||||
abstract class InterruptedExceptionTest_C7 implements AutoCloseable {
|
||||
@Override public void close() throws Exception { } // warning here
|
||||
}
|
||||
|
||||
abstract class InterruptedExceptionTest_C8 implements HasClose, AutoCloseable {
|
||||
}
|
||||
|
||||
abstract class InterruptedExceptionTest_C9 implements HasClose, AutoCloseable {
|
||||
@Override public void close() { }
|
||||
}
|
||||
|
||||
abstract class InterruptedExceptionTest_C10 extends WithConcreteClose implements AutoCloseable { // warning here
|
||||
}
|
||||
|
||||
abstract class InterruptedExceptionTest_C11 extends WithAbstractClose implements AutoCloseable {
|
||||
}
|
||||
|
||||
// Interface use site tests
|
||||
|
||||
class UseSite_I1 {
|
||||
void m(Supplier<InterruptedExceptionTest_I1> s) throws Exception {
|
||||
try (InterruptedExceptionTest_I1 t = s.get()) { // warning here
|
||||
t.hashCode();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
class UseSite_I2 {
|
||||
void m(Supplier<InterruptedExceptionTest_I2> s) throws Exception {
|
||||
try (InterruptedExceptionTest_I2 t = s.get()) {
|
||||
t.hashCode();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
class UseSite_I3 {
|
||||
void m(Supplier<InterruptedExceptionTest_I3> s) throws Exception {
|
||||
try (InterruptedExceptionTest_I3 t = s.get()) { // warning here
|
||||
t.hashCode();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
class UseSite_I4 {
|
||||
void m(Supplier<InterruptedExceptionTest_I4> s) throws Exception {
|
||||
try (InterruptedExceptionTest_I4 t = s.get()) { // warning here
|
||||
t.hashCode();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
class UseSite_I5 {
|
||||
void m(Supplier<InterruptedExceptionTest_I5> s) throws Exception {
|
||||
try (InterruptedExceptionTest_I5 t = s.get()) {
|
||||
t.hashCode();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
class UseSite_I6 {
|
||||
void m(Supplier<InterruptedExceptionTest_I6> s) throws Exception {
|
||||
try (InterruptedExceptionTest_I6 t = s.get()) { // warning here
|
||||
t.hashCode();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
class UseSite_I7 {
|
||||
void m(Supplier<InterruptedExceptionTest_I7> s) throws Exception {
|
||||
try (InterruptedExceptionTest_I7 t = s.get()) { // warning here
|
||||
t.hashCode();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
class UseSite_I8 {
|
||||
void m(Supplier<InterruptedExceptionTest_I8> s) throws Exception {
|
||||
try (InterruptedExceptionTest_I8 t = s.get()) { // warning here
|
||||
t.hashCode();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
class UseSite_I9 {
|
||||
void m(Supplier<InterruptedExceptionTest_I9> s) throws Exception {
|
||||
try (InterruptedExceptionTest_I9 t = s.get()) {
|
||||
t.hashCode();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Abstract class use site tests
|
||||
|
||||
class UseSite_C1 {
|
||||
void m(Supplier<InterruptedExceptionTest_C1> s) throws Exception {
|
||||
try (InterruptedExceptionTest_C1 t = s.get()) { // warning here
|
||||
t.hashCode();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
class UseSite_C2 {
|
||||
void m(Supplier<InterruptedExceptionTest_C2> s) throws Exception {
|
||||
try (InterruptedExceptionTest_C2 t = s.get()) {
|
||||
t.hashCode();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
class UseSite_C3 {
|
||||
void m(Supplier<InterruptedExceptionTest_C3> s) throws Exception {
|
||||
try (InterruptedExceptionTest_C3 t = s.get()) { // warning here
|
||||
t.hashCode();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
class UseSite_C4 {
|
||||
void m(Supplier<InterruptedExceptionTest_C4> s) throws Exception {
|
||||
try (InterruptedExceptionTest_C4 t = s.get()) { // warning here
|
||||
t.hashCode();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
class UseSite_C5 {
|
||||
void m(Supplier<InterruptedExceptionTest_C5> s) throws Exception {
|
||||
try (InterruptedExceptionTest_C5 t = s.get()) {
|
||||
t.hashCode();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
class UseSite_C6 {
|
||||
void m(Supplier<InterruptedExceptionTest_C6> s) throws Exception {
|
||||
try (InterruptedExceptionTest_C6 t = s.get()) { // warning here
|
||||
t.hashCode();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
class UseSite_C7 {
|
||||
void m(Supplier<InterruptedExceptionTest_C7> s) throws Exception {
|
||||
try (InterruptedExceptionTest_C7 t = s.get()) { // warning here
|
||||
t.hashCode();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
class UseSite_C8 {
|
||||
void m(Supplier<InterruptedExceptionTest_C8> s) throws Exception {
|
||||
try (InterruptedExceptionTest_C8 t = s.get()) { // warning here
|
||||
t.hashCode();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
class UseSite_C9 {
|
||||
void m(Supplier<InterruptedExceptionTest_C9> s) throws Exception {
|
||||
try (InterruptedExceptionTest_C9 t = s.get()) {
|
||||
t.hashCode();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
class UseSite_C10 {
|
||||
void m(Supplier<InterruptedExceptionTest_C10> s) throws Exception {
|
||||
try (InterruptedExceptionTest_C10 t = s.get()) { // warning here
|
||||
t.hashCode();
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,23 @@
|
||||
InterruptedExceptionTest2.java:34:20: compiler.warn.try.resource.can.throw.interrupted.exc: InterruptedExceptionTest_I3
|
||||
InterruptedExceptionTest2.java:38:20: compiler.warn.try.resource.can.throw.interrupted.exc: InterruptedExceptionTest_I4
|
||||
InterruptedExceptionTest2.java:46:28: compiler.warn.try.resource.can.throw.interrupted.exc: InterruptedExceptionTest_I6
|
||||
InterruptedExceptionTest2.java:50:28: compiler.warn.try.resource.can.throw.interrupted.exc: InterruptedExceptionTest_I7
|
||||
InterruptedExceptionTest2.java:70:36: compiler.warn.try.resource.can.throw.interrupted.exc: InterruptedExceptionTest_C3
|
||||
InterruptedExceptionTest2.java:74:36: compiler.warn.try.resource.can.throw.interrupted.exc: InterruptedExceptionTest_C4
|
||||
InterruptedExceptionTest2.java:82:27: compiler.warn.try.resource.can.throw.interrupted.exc: InterruptedExceptionTest_C6
|
||||
InterruptedExceptionTest2.java:86:27: compiler.warn.try.resource.can.throw.interrupted.exc: InterruptedExceptionTest_C7
|
||||
InterruptedExceptionTest2.java:96:10: compiler.warn.try.resource.throws.interrupted.exc: InterruptedExceptionTest_C10
|
||||
InterruptedExceptionTest2.java:106:42: compiler.warn.try.resource.throws.interrupted.exc: InterruptedExceptionTest_I1
|
||||
InterruptedExceptionTest2.java:122:42: compiler.warn.try.resource.throws.interrupted.exc: InterruptedExceptionTest_I3
|
||||
InterruptedExceptionTest2.java:130:42: compiler.warn.try.resource.throws.interrupted.exc: InterruptedExceptionTest_I4
|
||||
InterruptedExceptionTest2.java:146:42: compiler.warn.try.resource.throws.interrupted.exc: InterruptedExceptionTest_I6
|
||||
InterruptedExceptionTest2.java:154:42: compiler.warn.try.resource.throws.interrupted.exc: InterruptedExceptionTest_I7
|
||||
InterruptedExceptionTest2.java:162:42: compiler.warn.try.resource.throws.interrupted.exc: InterruptedExceptionTest_I8
|
||||
InterruptedExceptionTest2.java:180:42: compiler.warn.try.resource.throws.interrupted.exc: InterruptedExceptionTest_C1
|
||||
InterruptedExceptionTest2.java:196:42: compiler.warn.try.resource.throws.interrupted.exc: InterruptedExceptionTest_C3
|
||||
InterruptedExceptionTest2.java:204:42: compiler.warn.try.resource.throws.interrupted.exc: InterruptedExceptionTest_C4
|
||||
InterruptedExceptionTest2.java:220:42: compiler.warn.try.resource.throws.interrupted.exc: InterruptedExceptionTest_C6
|
||||
InterruptedExceptionTest2.java:228:42: compiler.warn.try.resource.throws.interrupted.exc: InterruptedExceptionTest_C7
|
||||
InterruptedExceptionTest2.java:236:42: compiler.warn.try.resource.throws.interrupted.exc: InterruptedExceptionTest_C8
|
||||
InterruptedExceptionTest2.java:252:43: compiler.warn.try.resource.throws.interrupted.exc: InterruptedExceptionTest_C10
|
||||
22 warnings
|
||||
@ -22,8 +22,15 @@
|
||||
*/
|
||||
|
||||
// key: compiler.warn.try.resource.throws.interrupted.exc
|
||||
// key: compiler.warn.try.resource.can.throw.interrupted.exc
|
||||
// options: -Xlint:try
|
||||
|
||||
class TryResourceThrowsInterruptedException implements AutoCloseable {
|
||||
public void close() throws InterruptedException {}
|
||||
{
|
||||
try (var t = new TryResourceThrowsInterruptedException()) {
|
||||
t.hashCode();
|
||||
} catch (InterruptedException e) {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user