This is an automated email from the ASF dual-hosted git repository.

jiangtian pushed a commit to branch fix_path_attack_1.3
in repository https://gitbox.apache.org/repos/asf/iotdb.git

commit f601a6535d400e8026af916212478ed46bf683e7
Author: Tian Jiang <[email protected]>
AuthorDate: Tue Aug 5 09:58:09 2025 +0800

    Fix path attack when loading snapshot of IoTConsensus
    
    (cherry picked from commit f907bd3eb07523ec40eb0079c8601d961b07b184)
---
 .../consensus/iot/IoTConsensusServerImpl.java      | 22 +++++++++++++++++++---
 1 file changed, 19 insertions(+), 3 deletions(-)

diff --git 
a/iotdb-core/consensus/src/main/java/org/apache/iotdb/consensus/iot/IoTConsensusServerImpl.java
 
b/iotdb-core/consensus/src/main/java/org/apache/iotdb/consensus/iot/IoTConsensusServerImpl.java
index dab767bc9da..3002b018e3e 100644
--- 
a/iotdb-core/consensus/src/main/java/org/apache/iotdb/consensus/iot/IoTConsensusServerImpl.java
+++ 
b/iotdb-core/consensus/src/main/java/org/apache/iotdb/consensus/iot/IoTConsensusServerImpl.java
@@ -358,7 +358,7 @@ public class IoTConsensusServerImpl {
       throws ConsensusGroupModifyPeerException {
     try {
       String targetFilePath = calculateSnapshotPath(snapshotId, 
originalFilePath);
-      File targetFile = new File(storageDir, targetFilePath);
+      File targetFile = getSnapshotPath(targetFilePath);
       Path parentDir = Paths.get(targetFile.getParent());
       if (!Files.exists(parentDir)) {
         Files.createDirectories(parentDir);
@@ -405,7 +405,23 @@ public class IoTConsensusServerImpl {
 
   public void loadSnapshot(String snapshotId) {
     // TODO: (xingtanzjr) throw exception if the snapshot load failed
-    stateMachine.loadSnapshot(new File(storageDir, snapshotId));
+    stateMachine.loadSnapshot(getSnapshotPath(snapshotId));
+  }
+
+  private File getSnapshotPath(String snapshotRelativePath) {
+    File storageDirFile = new File(storageDir);
+    File snapshotDir = new File(storageDir, snapshotRelativePath);
+    try {
+      if (!snapshotDir
+          .getCanonicalFile()
+          .toPath()
+          .startsWith(storageDirFile.getCanonicalFile().toPath())) {
+        throw new IllegalArgumentException("Invalid snapshotRelativePath: " + 
snapshotRelativePath);
+      }
+    } catch (IOException e) {
+      throw new IllegalArgumentException(e);
+    }
+    return snapshotDir;
   }
 
   @FunctionalInterface
@@ -816,7 +832,7 @@ public class IoTConsensusServerImpl {
   }
 
   public void cleanupSnapshot(String snapshotId) throws 
ConsensusGroupModifyPeerException {
-    File snapshotDir = new File(storageDir, snapshotId);
+    File snapshotDir = getSnapshotPath(snapshotId);
     if (snapshotDir.exists()) {
       try {
         FileUtils.deleteDirectory(snapshotDir);

Reply via email to