mirror of https://github.com/apache/cassandra
Merge branch 'cassandra-4.0' into cassandra-4.1
* cassandra-4.0: Fix JMX security vulnerabilities
This commit is contained in:
commit
fbb3079144
|
|
@ -8,6 +8,7 @@ Merged from 3.11:
|
|||
* Suppress CVE-2022-42003 and CVE-2022-42004 (CASSANDRA-17966)
|
||||
* Make LongBufferPoolTest insensitive to timing (CASSANDRA-16681)
|
||||
Merged from 3.0:
|
||||
* Harden JMX by resolving beanshooter issues (CASSANDRA-17921)
|
||||
* Suppress CVE-2019-2684 (CASSANDRA-17965)
|
||||
* Fix auto-completing "WITH" when creating a materialized view (CASSANDRA-17879)
|
||||
|
||||
|
|
|
|||
|
|
@ -187,7 +187,7 @@
|
|||
<configuration default="false" name="Cassandra" type="Application" factoryName="Application">
|
||||
<extension name="coverage" enabled="false" merge="false" sample_coverage="true" runner="idea" />
|
||||
<option name="MAIN_CLASS_NAME" value="org.apache.cassandra.service.CassandraDaemon" />
|
||||
<option name="VM_PARAMETERS" value="-Dcassandra-foreground=yes -Dcassandra.config=file://$PROJECT_DIR$/conf/cassandra.yaml -Dcassandra.storagedir=$PROJECT_DIR$/data -Dlogback.configurationFile=file://$PROJECT_DIR$/conf/logback.xml -Dcassandra.logdir=$PROJECT_DIR$/data/logs -Djava.library.path=$PROJECT_DIR$/lib/sigar-bin -Dcom.sun.management.jmxremote -Dcom.sun.management.jmxremote.port=7199 -Dcom.sun.management.jmxremote.local.only=false -Dcom.sun.management.jmxremote.authenticate=false -Dcom.sun.management.jmxremote.ssl=false -ea -Xmx1G -Dcassandra.reads.thresholds.coordinator.defensive_checks_enabled=true" />
|
||||
<option name="VM_PARAMETERS" value="-Dcassandra-foreground=yes -Dcassandra.config=file://$PROJECT_DIR$/conf/cassandra.yaml -Dcassandra.storagedir=$PROJECT_DIR$/data -Dlogback.configurationFile=file://$PROJECT_DIR$/conf/logback.xml -Dcassandra.logdir=$PROJECT_DIR$/data/logs -Djava.library.path=$PROJECT_DIR$/lib/sigar-bin -Dcassandra.jmx.local.port=7199 -ea -Xmx1G -Dcassandra.reads.thresholds.coordinator.defensive_checks_enabled=true" />
|
||||
<option name="PROGRAM_PARAMETERS" value="" />
|
||||
<option name="WORKING_DIRECTORY" value="file://$PROJECT_DIR$" />
|
||||
<option name="ALTERNATIVE_JRE_PATH_ENABLED" value="false" />
|
||||
|
|
|
|||
|
|
@ -28,6 +28,7 @@ import java.util.function.BooleanSupplier;
|
|||
import java.util.function.Function;
|
||||
import java.util.function.Predicate;
|
||||
import java.util.stream.Collectors;
|
||||
import javax.management.InstanceNotFoundException;
|
||||
import javax.management.MBeanServer;
|
||||
import javax.management.MalformedObjectNameException;
|
||||
import javax.management.ObjectName;
|
||||
|
|
@ -148,6 +149,10 @@ public class AuthorizationProxy implements InvocationHandler
|
|||
if ("getMBeanServer".equals(methodName))
|
||||
throw new SecurityException("Access denied");
|
||||
|
||||
// Corresponds to MBeanServer.invoke
|
||||
if (methodName.equals("invoke") && args.length == 4)
|
||||
checkVulnerableMethods(args);
|
||||
|
||||
// Retrieve Subject from current AccessControlContext
|
||||
AccessControlContext acc = AccessController.getContext();
|
||||
Subject subject = Subject.getSubject(acc);
|
||||
|
|
@ -478,6 +483,71 @@ public class AuthorizationProxy implements InvocationHandler
|
|||
.collect(Collectors.toSet());
|
||||
}
|
||||
|
||||
private void checkVulnerableMethods(Object args[])
|
||||
{
|
||||
assert args.length == 4;
|
||||
ObjectName name;
|
||||
String operationName;
|
||||
Object[] params;
|
||||
String[] signature;
|
||||
try
|
||||
{
|
||||
name = (ObjectName) args[0];
|
||||
operationName = (String) args[1];
|
||||
params = (Object[]) args[2];
|
||||
signature = (String[]) args[3];
|
||||
}
|
||||
catch (ClassCastException cce)
|
||||
{
|
||||
logger.warn("Could not interpret arguments to check vulnerable MBean invocations; did the MBeanServer interface change?", cce);
|
||||
return;
|
||||
}
|
||||
|
||||
// When adding compiler directives from a file, most JDKs will log the file contents if invalid, which
|
||||
// leads to an arbitrary file read vulnerability
|
||||
checkCompilerDirectiveAddMethods(name, operationName);
|
||||
|
||||
// Loading arbitrary (JVM and native) libraries from remotes
|
||||
checkJvmtiLoad(name, operationName);
|
||||
checkMLetMethods(name, operationName);
|
||||
}
|
||||
|
||||
private void checkCompilerDirectiveAddMethods(ObjectName name, String operation)
|
||||
{
|
||||
if (name.getCanonicalName().equals("com.sun.management:type=DiagnosticCommand")
|
||||
&& operation.equals("compilerDirectivesAdd"))
|
||||
throw new SecurityException("Access is denied!");
|
||||
}
|
||||
|
||||
private void checkJvmtiLoad(ObjectName name, String operation)
|
||||
{
|
||||
if (name.getCanonicalName().equals("com.sun.management:type=DiagnosticCommand")
|
||||
&& operation.equals("jvmtiAgentLoad"))
|
||||
throw new SecurityException("Access is denied!");
|
||||
}
|
||||
|
||||
private void checkMLetMethods(ObjectName name, String operation)
|
||||
{
|
||||
// Inspired by MBeanServerAccessController, but that class ignores check if a SecurityManager is installed,
|
||||
// which we don't want
|
||||
|
||||
if (operation == null)
|
||||
return;
|
||||
|
||||
try
|
||||
{
|
||||
if (!mbs.isInstanceOf(name, "javax.management.loading.MLet"))
|
||||
return;
|
||||
}
|
||||
catch (InstanceNotFoundException infe)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
if (operation.equals("addURL") || operation.equals("getMBeansFromURL"))
|
||||
throw new SecurityException("Access is denied!");
|
||||
}
|
||||
|
||||
public static final class JmxPermissionsCache extends AuthCache<RoleResource, Set<PermissionDetails>>
|
||||
implements JmxPermissionsCacheMBean
|
||||
{
|
||||
|
|
|
|||
Loading…
Reference in New Issue