From efee8786b3fd39b34793565024e3aef5ee5c3687 Mon Sep 17 00:00:00 2001 From: Wouter Born Date: Thu, 17 Mar 2022 13:37:36 +0100 Subject: [PATCH] Stop using ValidationSecurityManager as SecurityManager The Security Manager is deprecated and subject to removal in a future release. There is no replacement for the Security Manager. See also #1579 --- CHANGELOG.md | 1 + .../jsr305/ValidationSecurityManagerTest.java | 106 -------------- .../ba/jsr305/TypeQualifierValue.java | 19 +-- .../ba/jsr305/ValidationSecurityManager.java | 130 ------------------ .../validation/CheckValidatorSandboxing.java | 78 ----------- 5 files changed, 2 insertions(+), 332 deletions(-) delete mode 100644 spotbugs-tests/src/test/java/edu/umd/cs/findbugs/ba/jsr305/ValidationSecurityManagerTest.java delete mode 100644 spotbugs/src/main/java/edu/umd/cs/findbugs/ba/jsr305/ValidationSecurityManager.java delete mode 100644 spotbugsTestCases/src/java/jsr305/validation/CheckValidatorSandboxing.java diff --git a/CHANGELOG.md b/CHANGELOG.md index 60f59413046..22d8cfcbdbb 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -8,6 +8,7 @@ Currently the versioning policy of this project follows [Semantic Versioning v2. ### Fixed - Bumped Saxon-HE from 10.6 to 11.2 ([#1955](https://github.com/spotbugs/spotbugs/pull/1955)) - Fixed traversal of nested archives governed by `-nested:true` ([#1930](https://github.com/spotbugs/spotbugs/pull/1930)) +- Warnings of deprecated System::setSecurityManager calls on Java 17 ([#1983](https://github.com/spotbugs/spotbugs/pull/1983)) ## 4.6.0 - 2022-03-08 ### Fixed diff --git a/spotbugs-tests/src/test/java/edu/umd/cs/findbugs/ba/jsr305/ValidationSecurityManagerTest.java b/spotbugs-tests/src/test/java/edu/umd/cs/findbugs/ba/jsr305/ValidationSecurityManagerTest.java deleted file mode 100644 index 2850c560415..00000000000 --- a/spotbugs-tests/src/test/java/edu/umd/cs/findbugs/ba/jsr305/ValidationSecurityManagerTest.java +++ /dev/null @@ -1,106 +0,0 @@ -/* - * FindBugs - Find Bugs in Java programs - * Copyright (C) 2003-2008 University of Maryland - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation; either - * version 2.1 of the License, or (at your option) any later version. - * - * This library is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public - * License along with this library; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - */ - -package edu.umd.cs.findbugs.ba.jsr305; - -import static org.junit.Assert.assertEquals; -import static org.junit.Assert.fail; - -import java.io.File; -import java.util.concurrent.atomic.AtomicBoolean; - -import javax.annotation.Nonnull; -import javax.annotation.meta.TypeQualifierValidator; -import javax.annotation.meta.When; - -import org.junit.Test; - -import edu.umd.cs.findbugs.internalAnnotations.SlashedClassName; - -/** - * @author pugh - */ -public class ValidationSecurityManagerTest { - - - private static final SlashedClassName ANNOTATION = AnnotationTemplate.class.getAnnotation(SlashedClassName.class); - - static class BadValidator implements TypeQualifierValidator { - - @Override - public @Nonnull When forConstantValue(@Nonnull SlashedClassName annotation, Object value) { - Thread t = new Thread() { - @Override - public void run() { - System.out.println("bang"); - } - }; - t.start(); - return When.NEVER; - } - - } - - public When test(TypeQualifierValidator validator) { - return ValidationSecurityManager.sandboxedValidation(ANNOTATION, validator, "java/lang/String"); - - } - - public void havePermissions() throws InterruptedException { - final AtomicBoolean b = new AtomicBoolean(false); - Thread t = new Thread() { - @Override - public void run() { - b.set(true); - } - }; - t.start(); - t.join(); - assertEquals(true, b.get()); - for (File f : File.listRoots()) { - f.listFiles(); - } - } - - @SlashedClassName - static class AnnotationTemplate { - } - - @Test - public void test() throws InterruptedException { - ValidationSecurityManager sm = ValidationSecurityManager.INSTANCE; - SecurityManager old = System.getSecurityManager(); - System.setSecurityManager(sm); - TypeQualifierValidator goodValidator = new SlashedClassName.Checker(); - havePermissions(); - assertEquals(When.ALWAYS, test(goodValidator)); - try { - test(new BadValidator()); - fail("Should have thrown SecurityException"); - } catch (SecurityException e) { - assert true; - } - havePermissions(); - System.setSecurityManager(old); - havePermissions(); - - - } - -} diff --git a/spotbugs/src/main/java/edu/umd/cs/findbugs/ba/jsr305/TypeQualifierValue.java b/spotbugs/src/main/java/edu/umd/cs/findbugs/ba/jsr305/TypeQualifierValue.java index d9090f6cc76..28f24c76caf 100644 --- a/spotbugs/src/main/java/edu/umd/cs/findbugs/ba/jsr305/TypeQualifierValue.java +++ b/spotbugs/src/main/java/edu/umd/cs/findbugs/ba/jsr305/TypeQualifierValue.java @@ -148,15 +148,6 @@ private TypeQualifierValue(ClassDescriptor typeQualifier, @CheckForNull Object v try { Global.getAnalysisCache().getClassAnalysis(ClassData.class, checkerName); - // found it. - SecurityManager m = System.getSecurityManager(); - if (m == null) { - if (DEBUG_CLASSLOADING) { - System.out.println("Setting ValidationSecurityManager"); - } - System.setSecurityManager(ValidationSecurityManager.INSTANCE); - } - Class c = ValidatorClassLoader.INSTANCE.loadClass(checkerName.getDottedClassName()); if (TypeQualifierValidator.class.isAssignableFrom(c)) { @@ -187,14 +178,6 @@ private TypeQualifierValue(ClassDescriptor typeQualifier, @CheckForNull Object v AnalysisContext.logError("Unable to construct type qualifier checker " + checkerName + " due to " + e.getClass().getSimpleName() + ":" + e.getMessage()); } - } else if (DEBUG_CLASSLOADING) { - SecurityManager m = System.getSecurityManager(); - if (m == null) { - if (DEBUG_CLASSLOADING) { - System.out.println("Setting ValidationSecurityManager"); - } - System.setSecurityManager(ValidationSecurityManager.INSTANCE); - } } } this.validator = validator1; @@ -269,7 +252,7 @@ public When validate(@CheckForNull Object constantValue) { Profiler profiler = analysisCache.getProfiler(); profiler.start(validator.getClass()); try { - return ValidationSecurityManager.sandboxedValidation(proxy, validator, constantValue); + return validator.forConstantValue(proxy, constantValue); } catch (Exception e) { AnalysisContext.logError("Error executing custom validator for " + typeQualifier + " " + constantValue, e); return When.UNKNOWN; diff --git a/spotbugs/src/main/java/edu/umd/cs/findbugs/ba/jsr305/ValidationSecurityManager.java b/spotbugs/src/main/java/edu/umd/cs/findbugs/ba/jsr305/ValidationSecurityManager.java deleted file mode 100644 index fb84f505c43..00000000000 --- a/spotbugs/src/main/java/edu/umd/cs/findbugs/ba/jsr305/ValidationSecurityManager.java +++ /dev/null @@ -1,130 +0,0 @@ -/* - * FindBugs - Find Bugs in Java programs - * Copyright (C) 2003-2008 University of Maryland - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public - * License as published by the Free Software Foundation; either - * version 2.1 of the License, or (at your option) any later version. - * - * This library is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public - * License along with this library; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - */ - -package edu.umd.cs.findbugs.ba.jsr305; - -import java.lang.annotation.Annotation; -import java.security.Permission; - -import javax.annotation.CheckForNull; -import javax.annotation.meta.TypeQualifierValidator; -import javax.annotation.meta.When; - -final class ValidationSecurityManager extends SecurityManager { - - - static final ValidationSecurityManager INSTANCE = new ValidationSecurityManager(); - final static ValidatorClassLoader VALIDATOR_LOADER = ValidatorClassLoader.INSTANCE; - - - static { - if (TypeQualifierValue.DEBUG_CLASSLOADING) { - new RuntimeException("Creating ValidationSecurityManager #").printStackTrace(); - } - - } - - public static When sandboxedValidation(A proxy, TypeQualifierValidator v, @CheckForNull Object constantValue) { - if (performingValidation.get()) { - throw new IllegalStateException("recursive validation"); - } - - try { - performingValidation.set(Boolean.TRUE); - if (TypeQualifierValue.DEBUG_CLASSLOADING) { - System.out.println("Performing validation in thread " + Thread.currentThread().getName()); - } - try { - When result = v.forConstantValue(proxy, constantValue); - if (!performingValidation.get()) { - throw new IllegalStateException("performingValidation not set when validation completes"); - } - return result; - } catch (ClassCastException e) { - Class c = proxy.getClass(); - System.out.println(c.getName() + " extends " + c.getSuperclass().getName()); - for (Class i : c.getInterfaces()) { - System.out.println(" " + i.getName()); - } - throw e; - } - - } finally { - performingValidation.set(Boolean.FALSE); - if (TypeQualifierValue.DEBUG_CLASSLOADING) { - System.out.println("Validation finished in thread " + Thread.currentThread().getName()); - } - - } - } - - - @Override - public void checkPermission(Permission perm) { - if (TypeQualifierValue.DEBUG_CLASSLOADING) { - System.out.println("Checking for " + perm + " permission in thread " + Thread.currentThread().getName()); - } - if (performingValidation.get() && inValidation()) { - SecurityException e = new SecurityException("No permissions granted while performing JSR-305 validation"); - if (TypeQualifierValue.DEBUG_CLASSLOADING) { - e.printStackTrace(System.out); - } - throw e; - } - - } - - @Override - public void checkPermission(Permission perm, Object context) { - if (TypeQualifierValue.DEBUG_CLASSLOADING) { - System.out.println("Checking for " + perm + " permission with content in thread " + Thread.currentThread().getName()); - } - - if (performingValidation.get() && inValidation()) { - SecurityException e = new SecurityException("No permissions granted while performing JSR-305 validation"); - if (TypeQualifierValue.DEBUG_CLASSLOADING) { - e.printStackTrace(System.out); - } - throw e; - } - } - - private ValidationSecurityManager() { - } - - private boolean inValidation() { - for (Class c : getClassContext()) { - if (TypeQualifierValidator.class.isAssignableFrom(c) - || c.getClassLoader() == VALIDATOR_LOADER) { - return true; - } - } - return false; - } - - private static final ThreadLocal performingValidation = new ThreadLocal() { - @Override - protected Boolean initialValue() { - return Boolean.FALSE; - } - - }; - - -} diff --git a/spotbugsTestCases/src/java/jsr305/validation/CheckValidatorSandboxing.java b/spotbugsTestCases/src/java/jsr305/validation/CheckValidatorSandboxing.java deleted file mode 100644 index 7232a9752f2..00000000000 --- a/spotbugsTestCases/src/java/jsr305/validation/CheckValidatorSandboxing.java +++ /dev/null @@ -1,78 +0,0 @@ -package jsr305.validation; - -import java.io.File; -import java.lang.annotation.Documented; -import java.lang.annotation.Retention; -import java.lang.annotation.RetentionPolicy; -import java.util.Arrays; - -import javax.annotation.meta.TypeQualifier; -import javax.annotation.meta.TypeQualifierValidator; -import javax.annotation.meta.When; - -import edu.umd.cs.findbugs.annotations.ExpectWarning; -import edu.umd.cs.findbugs.annotations.NoWarning; - -public class CheckValidatorSandboxing { - - void needsEven(@Even int x) { - } - - void needsEven(@Even long x) { - } - - @NoWarning("TQ") - void testOK(@Even int x) { - needsEven(-2); - needsEven(0); - needsEven(2); - needsEven(2L); - needsEven(x); - } - - @ExpectWarning(value = "TQ", num=5) - void testBad(int x) { - needsEven(-1); - needsEven(1); - needsEven(3); - needsEven(3L); - needsEven(x); - } - - @Documented - @TypeQualifier(applicableTo = Number.class) - @Retention(RetentionPolicy.RUNTIME) - static public @interface Even { - static class Checker implements TypeQualifierValidator { - - @Override - public When forConstantValue(Even annotation, Object value) { - try { - String[] rootList = new File("/").list(); - throw new RuntimeException("Got list of root files " + Arrays.toString(rootList)); - } catch (SecurityException e) { - // e.printStackTrace(); - assert true; - } - try { - Class c = Class.forName("edu.umd.cs.findbugs.FindBugs2"); - throw new RuntimeException("Should not have been able to load " + c); - } catch (ClassNotFoundException e) { - assert true; - } catch (SecurityException e) { - assert true; - } - if (value instanceof Number) { - if (((Number) value).longValue() % 2 == 0) - return When.ALWAYS; - else - return When.NEVER; - } else - return When.UNKNOWN; - } - - } - - } - -}