-
Notifications
You must be signed in to change notification settings - Fork 134
fix(jdbc): various perf improvements #4114
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
base: main
Are you sure you want to change the base?
Changes from all commits
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 |
|---|---|---|
|
|
@@ -331,11 +331,11 @@ private static boolean isFileExists(String filename) { | |
| } | ||
| } | ||
|
|
||
| private static boolean isJson(String value) { | ||
| private static boolean isJson(byte[] value) { | ||
| try { | ||
| // This is done this way to ensure strict Json parsing | ||
| // https://github.com/google/gson/issues/1208#issuecomment-2120764686 | ||
| InputStream stream = new ByteArrayInputStream(value.getBytes()); | ||
| InputStream stream = new ByteArrayInputStream(value); | ||
| InputStreamReader reader = new InputStreamReader(stream); | ||
| JsonReader jsonReader = new JsonReader(reader); | ||
| jsonReader.setStrictness(Strictness.STRICT); | ||
|
|
@@ -366,16 +366,18 @@ private static GoogleCredentials getGoogleServiceAccountCredentials( | |
| final String keyPath = pvtKeyPath != null ? pvtKeyPath : pvtKey; | ||
| PrivateKey key = null; | ||
| InputStream stream = null; | ||
|
|
||
| byte[] keyBytes = pvtKey != null ? pvtKey.getBytes() : null; | ||
|
|
||
| if (isFileExists(keyPath)) { | ||
| key = privateKeyFromP12File(keyPath, p12Password); | ||
| if (key == null) { | ||
| stream = Files.newInputStream(Paths.get(keyPath)); | ||
| } | ||
| } else if (isJson(pvtKey)) { | ||
| stream = new ByteArrayInputStream(pvtKey.getBytes()); | ||
| keyBytes = Files.readAllBytes(Paths.get(keyPath)); | ||
| } | ||
|
|
||
| if (isJson(keyBytes)) { | ||
| stream = new ByteArrayInputStream(keyBytes); | ||
| } else if (pvtKey != null) { | ||
| key = privateKeyFromPkcs8(pvtKey); | ||
| } else { | ||
| key = privateKeyFromP12Bytes(keyBytes, p12Password); | ||
| } | ||
|
Comment on lines
+375
to
381
Contributor
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 updated logic for parsing private keys has a flaw. It doesn't correctly handle PKCS8 keys provided via a file path (
This breaks authentication for these scenarios. The logic should attempt to parse the loaded Here is a suggested fix that correctly sequences the parsing attempts on the if (isJson(keyBytes)) {
stream = new ByteArrayInputStream(keyBytes);
} else if (keyBytes != null) {
// Try to parse as PKCS8 private key
key = privateKeyFromPkcs8(new String(keyBytes, java.nio.charset.StandardCharsets.UTF_8));
if (key == null) {
// If not PKCS8, try to parse as P12
key = privateKeyFromP12Bytes(keyBytes, p12Password);
}
} |
||
|
|
||
| if (stream != null) { | ||
|
|
@@ -703,9 +705,9 @@ private static GoogleCredentials getServiceAccountImpersonatedCredentials( | |
| impersonationLifetimeInt); | ||
| } | ||
|
|
||
| static PrivateKey privateKeyFromP12File(String privateKeyFile, String password) { | ||
| static PrivateKey privateKeyFromP12Bytes(byte[] privateKey, String password) { | ||
| try { | ||
| InputStream stream = Files.newInputStream(Paths.get(privateKeyFile)); | ||
| InputStream stream = new ByteArrayInputStream(privateKey); | ||
| return SecurityUtils.loadPrivateKeyFromKeyStore( | ||
| SecurityUtils.getPkcs12KeyStore(), stream, "notasecret", "privatekey", password); | ||
| } catch (IOException | GeneralSecurityException e) { | ||
|
|
||
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.
The use of
Files.readAllBytes()to read a key file specified in the connection string can lead to a Denial of Service (DoS) via anOutOfMemoryError. An attacker who can control the connection string (e.g., in applications that allow users to provide their own JDBC URL) can point theOAuthPvtKeyPathorOAuthPvtKeyproperty to a very large file (such as/dev/zeroor a large log file) on the server. This will cause the application to attempt to read the entire file into memory, potentially crashing the JVM. Additionally, on Windows systems, providing a UNC path (e.g.,\\attacker-ip\share\file) could lead to an information disclosure by leaking the Windows user's NetNTLM hash when the driver attempts to access the remote share.