This is an automated email from the ASF dual-hosted git repository.
chaokunyang pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/fury.git
The following commit(s) were added to refs/heads/main by this push:
new fcdbebad feat(java): use sha256 to check disallowed.txt tamper (#2102)
fcdbebad is described below
commit fcdbebad94c7dd76dd66cd1888c06fe29f26fd53
Author: Shawn Yang <[email protected]>
AuthorDate: Tue Mar 18 00:23:32 2025 +0800
feat(java): use sha256 to check disallowed.txt tamper (#2102)
## What does this PR do?
use sha256 to check disallowed.txt tamper
## Related issues
Closes #2100
## Does this PR introduce any user-facing change?
<!--
If any user-facing interface changes, please [open an
issue](https://github.com/apache/fury/issues/new/choose) describing the
need to do so and update the document if necessary.
-->
- [ ] Does this PR introduce any public API change?
- [ ] Does this PR introduce any binary protocol compatibility change?
## Benchmark
<!--
When the PR has an impact on performance (if you don't know whether the
PR will have an impact on performance, you can submit the PR first, and
if it will have impact on performance, the code reviewer will explain
it), be sure to attach a benchmark data here.
-->
---
.../org/apache/fury/resolver/DisallowedList.java | 48 ++++++++++++++++++++--
.../src/main/resources/fury/disallowed.txt | 1 +
2 files changed, 45 insertions(+), 4 deletions(-)
diff --git
a/java/fury-core/src/main/java/org/apache/fury/resolver/DisallowedList.java
b/java/fury-core/src/main/java/org/apache/fury/resolver/DisallowedList.java
index e26402e9..b6ea8840 100644
--- a/java/fury-core/src/main/java/org/apache/fury/resolver/DisallowedList.java
+++ b/java/fury-core/src/main/java/org/apache/fury/resolver/DisallowedList.java
@@ -19,11 +19,13 @@
package org.apache.fury.resolver;
-import java.io.BufferedReader;
+import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
-import java.io.InputStreamReader;
import java.nio.charset.StandardCharsets;
+import java.security.MessageDigest;
+import java.security.NoSuchAlgorithmException;
+import java.util.Arrays;
import java.util.Set;
import java.util.stream.Collectors;
import org.apache.fury.exception.InsecureException;
@@ -31,15 +33,24 @@ import org.apache.fury.exception.InsecureException;
/** A class to record which classes are not allowed for serialization. */
class DisallowedList {
private static final String DISALLOWED_LIST_TXT_PATH = "fury/disallowed.txt";
+ // when disallowed.txt changed, update this hash by result of `sha256sum
disallowed.txt`
+ private static final String SHA256_HASH =
+ "30dc5228f52b02f61aff35a94d29ccd903abbf490d8231810c5e1c0321c56557";
private static final Set<String> DEFAULT_DISALLOWED_LIST_SET;
static {
try (InputStream is =
DisallowedList.class.getClassLoader().getResourceAsStream(DISALLOWED_LIST_TXT_PATH))
{
if (is != null) {
+ byte[] fileBytes = readAllBytes(is);
+ String calculatedHash = calculateSHA256(fileBytes);
+ if (!SHA256_HASH.equals(calculatedHash)) {
+ // add a check to avoid some malicious overwrite disallowed.txt
+ throw new SecurityException("Disallowed list has been tampered");
+ }
DEFAULT_DISALLOWED_LIST_SET =
- new BufferedReader(new InputStreamReader(is,
StandardCharsets.UTF_8))
- .lines()
+ Arrays.stream(
+ new String(fileBytes,
StandardCharsets.UTF_8).split(System.lineSeparator()))
.filter(line -> !line.isEmpty() && !line.startsWith("#"))
.collect(Collectors.toSet());
} else {
@@ -52,6 +63,35 @@ class DisallowedList {
}
}
+ private static byte[] readAllBytes(InputStream inputStream) throws
IOException {
+ ByteArrayOutputStream buffer = new ByteArrayOutputStream();
+ int numbytesRead;
+ byte[] data = new byte[1024];
+ while ((numbytesRead = inputStream.read(data, 0, data.length)) != -1) {
+ buffer.write(data, 0, numbytesRead);
+ }
+ buffer.flush();
+ return buffer.toByteArray();
+ }
+
+ private static String calculateSHA256(byte[] input) {
+ try {
+ MessageDigest digest = MessageDigest.getInstance("SHA-256");
+ byte[] hashBytes = digest.digest(input);
+ StringBuilder hexString = new StringBuilder();
+ for (byte b : hashBytes) {
+ String hex = Integer.toHexString(0xff & b);
+ if (hex.length() == 1) {
+ hexString.append('0');
+ }
+ hexString.append(hex);
+ }
+ return hexString.toString();
+ } catch (NoSuchAlgorithmException e) {
+ throw new RuntimeException("SHA-256 algorithm not available", e);
+ }
+ }
+
/**
* Determine whether the current Class is in the default disallowed list.
*
diff --git a/java/fury-core/src/main/resources/fury/disallowed.txt
b/java/fury-core/src/main/resources/fury/disallowed.txt
index bf7fd8dc..2a6e5b02 100644
--- a/java/fury-core/src/main/resources/fury/disallowed.txt
+++ b/java/fury-core/src/main/resources/fury/disallowed.txt
@@ -15,6 +15,7 @@
# specific language governing permissions and limitations
# under the License.
+# Note: update `DisallowedList#SHA256_HASH` when added new classes.
bsh.Interpreter
bsh.XThis
ch.qos.logback.core.db.DriverManagerConnectionSource
---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]