Bug 577766 - Cannot remove parentheses for instanceof pattern matching

- add support for instanceof pattern matching in
  NecessaryParenthesesChecker and OperatorPrecedence similar to what
  is done for instanceof
- add new test to CleanUpTest16

Change-Id: Ic08a1f78847758b0af587d267ee318b243b1a8bb
Reviewed-on: https://git.eclipse.org/r/c/jdt/eclipse.jdt.ui/+/188857
Tested-by: JDT Bot <jdt-bot@eclipse.org>
Tested-by: Jeff Johnston <jjohnstn@redhat.com>
Reviewed-by: Jeff Johnston <jjohnstn@redhat.com>
diff --git a/org.eclipse.jdt.core.manipulation/core extension/org/eclipse/jdt/internal/core/manipulation/dom/NecessaryParenthesesChecker.java b/org.eclipse.jdt.core.manipulation/core extension/org/eclipse/jdt/internal/core/manipulation/dom/NecessaryParenthesesChecker.java
index 889ad82..4c9c297 100644
--- a/org.eclipse.jdt.core.manipulation/core extension/org/eclipse/jdt/internal/core/manipulation/dom/NecessaryParenthesesChecker.java
+++ b/org.eclipse.jdt.core.manipulation/core extension/org/eclipse/jdt/internal/core/manipulation/dom/NecessaryParenthesesChecker.java
@@ -1,5 +1,5 @@
 /*******************************************************************************
- * Copyright (c) 2011, 2019 IBM Corporation and others.
+ * Copyright (c) 2011, 2021 IBM Corporation and others.
  *
  * This program and the accompanying materials
  * are made available under the terms of the Eclipse Public License 2.0
@@ -60,6 +60,7 @@
 				|| type == ASTNode.POSTFIX_EXPRESSION
 				|| type == ASTNode.CAST_EXPRESSION
 				|| type == ASTNode.INSTANCEOF_EXPRESSION
+				|| type == ASTNode.PATTERN_INSTANCEOF_EXPRESSION
 				|| type == ASTNode.ARRAY_CREATION
 				|| type == ASTNode.ASSIGNMENT;
 	}
diff --git a/org.eclipse.jdt.core.manipulation/core extension/org/eclipse/jdt/internal/core/manipulation/dom/OperatorPrecedence.java b/org.eclipse.jdt.core.manipulation/core extension/org/eclipse/jdt/internal/core/manipulation/dom/OperatorPrecedence.java
index 065da72..d245dd8 100644
--- a/org.eclipse.jdt.core.manipulation/core extension/org/eclipse/jdt/internal/core/manipulation/dom/OperatorPrecedence.java
+++ b/org.eclipse.jdt.core.manipulation/core extension/org/eclipse/jdt/internal/core/manipulation/dom/OperatorPrecedence.java
@@ -1,5 +1,5 @@
 /*******************************************************************************
- * Copyright (c) 2000, 2018 IBM Corporation and others.
+ * Copyright (c) 2000, 2021 IBM Corporation and others.
  *
  * This program and the accompanying materials
  * are made available under the terms of the Eclipse Public License 2.0
@@ -24,6 +24,7 @@
 import org.eclipse.jdt.core.dom.InfixExpression.Operator;
 import org.eclipse.jdt.core.dom.InstanceofExpression;
 import org.eclipse.jdt.core.dom.MethodInvocation;
+import org.eclipse.jdt.core.dom.PatternInstanceofExpression;
 import org.eclipse.jdt.core.dom.PostfixExpression;
 import org.eclipse.jdt.core.dom.PrefixExpression;
 
@@ -73,7 +74,7 @@
 			return ASSIGNMENT;
 		} else if (expression instanceof ConditionalExpression) {
 			return CONDITIONAL;
-		} else if (expression instanceof InstanceofExpression) {
+		} else if (expression instanceof InstanceofExpression || expression instanceof PatternInstanceofExpression) {
 			return RELATIONAL;
 		} else if (expression instanceof CastExpression) {
 			return TYPEGENERATION;
diff --git a/org.eclipse.jdt.ui.tests/ui/org/eclipse/jdt/ui/tests/quickfix/CleanUpTest16.java b/org.eclipse.jdt.ui.tests/ui/org/eclipse/jdt/ui/tests/quickfix/CleanUpTest16.java
index 6f64edb..a887787 100644
--- a/org.eclipse.jdt.ui.tests/ui/org/eclipse/jdt/ui/tests/quickfix/CleanUpTest16.java
+++ b/org.eclipse.jdt.ui.tests/ui/org/eclipse/jdt/ui/tests/quickfix/CleanUpTest16.java
@@ -630,4 +630,32 @@
 		assertRefactoringResultAsExpected(new ICompilationUnit[] { cu0, cu1 }, new String[] { expected0, expected1 }, null);
 	}
 
+	@Test
+	public void testDoNotRemoveParenthesesFromPatternInstanceof() throws Exception {
+		IPackageFragment pack1= fSourceFolder.createPackageFragment("test1", false, null);
+
+		String sample= "" //
+				+ "package test1;\n" //
+				+ "\n" //
+				+ "public class TestParenthesesRemoval {\n" //
+				+ "        public static void doNotChangeParenthesesForInstanceof(Object o) {\n" //
+				+ "            if (!(o instanceof String)) {\n" //
+				+ "                System.out.println(\"not a String\");\n" //
+				+ "            }\n" //
+				+ "        }\n" //
+				+ "        public static void doNotChangeParenthesesForPatternInstanceof(Object o) {\n" //
+				+ "            if (!(o instanceof String s)) {\n" //
+				+ "                System.out.println(\"not a String\");\n" //
+				+ "            } else {\n" //
+				+ "                System.out.println(\"String length is \" + s.length());\n" //
+				+ "        }\n" //
+				+ "    }\n" //
+				+ "}\n";
+		ICompilationUnit cu1= pack1.createCompilationUnit("TestParenthesesRemoval.java", sample, false, null);
+
+		enable(CleanUpConstants.EXPRESSIONS_USE_PARENTHESES_NEVER);
+
+		assertRefactoringHasNoChange(new ICompilationUnit[] { cu1 });
+	}
+
 }