-
Notifications
You must be signed in to change notification settings - Fork 24.9k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Update "ssl-config" to support X-Pack features #74887
Changes from 2 commits
42027ea
093e9e4
d2eb0f6
83c53cc
03420fd
f15b9d9
0e85692
75bcd1b
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,85 @@ | ||
/* | ||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one | ||
* or more contributor license agreements. Licensed under the Elastic License | ||
* 2.0 and the Server Side Public License, v 1; you may not use this file except | ||
* in compliance with, at your election, the Elastic License 2.0 or the Server | ||
* Side Public License, v 1. | ||
*/ | ||
|
||
package org.elasticsearch.common.ssl; | ||
|
||
import javax.net.ssl.TrustManagerFactory; | ||
import javax.net.ssl.X509ExtendedTrustManager; | ||
import java.nio.file.Path; | ||
import java.security.GeneralSecurityException; | ||
import java.security.KeyStore; | ||
import java.security.cert.Certificate; | ||
import java.util.Arrays; | ||
import java.util.Collection; | ||
import java.util.List; | ||
import java.util.Objects; | ||
import java.util.stream.Collectors; | ||
|
||
/** | ||
* A TrustConfiguration that merges trust anchors from a number of other trust configs to produce a single {@link X509ExtendedTrustManager}. | ||
*/ | ||
public class CompositeTrustConfig implements SslTrustConfig { | ||
private final List<SslTrustConfig> configs; | ||
|
||
CompositeTrustConfig(List<SslTrustConfig> configs) { | ||
this.configs = List.copyOf(configs); | ||
} | ||
|
||
@Override | ||
public Collection<Path> getDependentFiles() { | ||
return configs.stream().map(SslTrustConfig::getDependentFiles).flatMap(Collection::stream).collect(Collectors.toUnmodifiableSet()); | ||
} | ||
|
||
@Override | ||
public boolean isSystemDefault() { | ||
return configs.stream().allMatch(SslTrustConfig::isSystemDefault); | ||
} | ||
|
||
@Override | ||
public X509ExtendedTrustManager createTrustManager() { | ||
try { | ||
Collection<Certificate> trustedIssuers = configs.stream() | ||
.map(c -> c.createTrustManager()) | ||
.map(tm -> tm.getAcceptedIssuers()) | ||
.flatMap(Arrays::stream) | ||
.collect(Collectors.toSet()); | ||
final KeyStore store = KeyStoreUtil.buildTrustStore(trustedIssuers); | ||
return KeyStoreUtil.createTrustManager(store, TrustManagerFactory.getDefaultAlgorithm()); | ||
} catch (GeneralSecurityException e) { | ||
throw new SslConfigException("Cannot combine trust configurations [" | ||
+ configs.stream().map(SslTrustConfig::toString).collect(Collectors.joining(",")) | ||
+ "]", | ||
e); | ||
} | ||
} | ||
|
||
@Override | ||
public Collection<? extends StoredCertificate> getConfiguredCertificates() { | ||
return configs.stream().map(SslTrustConfig::getConfiguredCertificates) | ||
.flatMap(Collection::stream) | ||
.collect(Collectors.toUnmodifiableList()); | ||
} | ||
|
||
@Override | ||
public boolean equals(Object o) { | ||
if (this == o) return true; | ||
if (o == null || getClass() != o.getClass()) return false; | ||
CompositeTrustConfig that = (CompositeTrustConfig) o; | ||
return configs.equals(that.configs); | ||
} | ||
|
||
@Override | ||
public int hashCode() { | ||
return Objects.hash(configs); | ||
} | ||
|
||
@Override | ||
public String toString() { | ||
return "Composite-Trust{" + configs.stream().map(SslTrustConfig::toString).collect(Collectors.joining(",")) + '}'; | ||
} | ||
} |
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -18,13 +18,15 @@ | |
import java.security.KeyStore; | ||
import java.util.Arrays; | ||
import java.util.Collection; | ||
import java.util.Collections; | ||
import java.util.List; | ||
import java.util.function.BiFunction; | ||
|
||
/** | ||
* This class represents a trust configuration that corresponds to the default trusted CAs of the JDK | ||
*/ | ||
final class DefaultJdkTrustConfig implements SslTrustConfig { | ||
public final class DefaultJdkTrustConfig implements SslTrustConfig { | ||
|
||
public static final DefaultJdkTrustConfig DEFAULT_INSTANCE = new DefaultJdkTrustConfig(); | ||
|
||
private final BiFunction<String, String, String> systemProperties; | ||
private final char[] trustStorePassword; | ||
|
@@ -51,6 +53,11 @@ final class DefaultJdkTrustConfig implements SslTrustConfig { | |
this.trustStorePassword = trustStorePassword; | ||
} | ||
|
||
@Override | ||
public boolean isSystemDefault() { | ||
return true; | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This method needed for the PKI realm - it will not trust the JDK default issuers. |
||
} | ||
|
||
@Override | ||
public X509ExtendedTrustManager createTrustManager() { | ||
try { | ||
|
@@ -90,7 +97,12 @@ private static char[] getSystemTrustStorePassword(BiFunction<String, String, Str | |
|
||
@Override | ||
public Collection<Path> getDependentFiles() { | ||
return Collections.emptyList(); | ||
return List.of(); | ||
} | ||
|
||
@Override | ||
public Collection<? extends StoredCertificate> getConfiguredCertificates() { | ||
return List.of(); | ||
} | ||
|
||
@Override | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -31,7 +31,7 @@ | |
* Based on https://github.com/groovenauts/jmeter_oauth_plugin/blob/master/jmeter/src/ | ||
* main/java/org/apache/jmeter/protocol/oauth/sampler/PrivateKeyReader.java | ||
*/ | ||
final class DerParser { | ||
public final class DerParser { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The RestrictedTrustConfig in X-Pack needs to be able to use this parser. |
||
// Constructed Flag | ||
private static final int CONSTRUCTED = 0x20; | ||
|
||
|
@@ -55,12 +55,12 @@ final class DerParser { | |
private InputStream derInputStream; | ||
private int maxAsnObjectLength; | ||
|
||
DerParser(byte[] bytes) { | ||
public DerParser(byte[] bytes) { | ||
this.derInputStream = new ByteArrayInputStream(bytes); | ||
this.maxAsnObjectLength = bytes.length; | ||
} | ||
|
||
Asn1Object readAsn1Object() throws IOException { | ||
public Asn1Object readAsn1Object() throws IOException { | ||
int tag = derInputStream.read(); | ||
if (tag == -1) { | ||
throw new IOException("Invalid DER: stream too short, missing tag"); | ||
|
@@ -133,7 +133,7 @@ private int getLength() throws IOException { | |
* | ||
* @author zhang | ||
*/ | ||
static class Asn1Object { | ||
public static class Asn1Object { | ||
|
||
protected final int type; | ||
protected final int length; | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
In X-Pack, specifying a keystore, but no truststore gives you a set of trust anchors that support everything in your JDK trust, and all the trust anchors in your keystore.
This class was added so we can also support that behaviour from ssl-config.