xftp: limit description replicas, no YAML aliases

This commit is contained in:
Evgeny @ SimpleX Chat committed 2026-10-21 14:11:23 +00:00
1 parent 69d55c387a
commit 3441adaa52
2 files changed
+27 -1

No files matched your search

+12 -1
View File
@@ -217,17 +217,28 @@ instance FilePartyI p => StrEncoding (FileDescription p) where
instance StrEncoding AFileDescription where
strEncode (AFD fd) = strEncode fd
strDecode = decodeFileDescription <=< first show . Y.decodeEither'
strDecode s
| B.elem '*' s = Left "YAML aliases are not allowed"
| otherwise = decodeFileDescription =<< first show (Y.decodeEither' s)
strP = strDecode <$?> A.takeByteString
validateFileDescription :: FileDescription p -> Either String (ValidFileDescription p)
validateFileDescription fd@FileDescription {size, chunks}
| chunkNos /= [1 .. length chunks] = Left "chunk numbers are not sequential"
| chunksSize chunks /= unFileSize size = Left "chunks total size is different than file size"
| any (> maxChunkReplicas) replicaCounts = Left "too many chunk replicas"
| sum replicaCounts > maxFileReplicas = Left "too many file replicas"
| otherwise = Right $ ValidFD fd
where
chunkNos = map (\FileChunk {chunkNo} -> chunkNo) chunks
chunksSize = foldl' (\(s :: Int64) FileChunk {chunkSize} -> s + fromIntegral (unFileSize chunkSize)) 0
replicaCounts = map (\FileChunk {replicas} -> length replicas) chunks
maxChunkReplicas :: Int
maxChunkReplicas = 16
maxFileReplicas :: Int
maxFileReplicas = 4096
sharedDescriptionHash :: FileDescription p -> ByteString
sharedDescriptionHash FileDescription {size, digest, key, nonce, chunkSize, chunks} =
+15
View File
@@ -25,6 +25,8 @@ fileDescriptionTests = do
it "parse YAML file description" testParseYAMLFileDescription
it "serialize YAML file description" testSerializeYAMLFileDescription
it "parse file description" testParseFileDescription
it "reject file description with YAML aliases" testRejectYAMLAliases
it "reject file description with too many replicas" testRejectTooManyReplicas
it "serialize file description" testSerializeFileDescription
describe "file description URIs" $ do
it "round trip file description URI" testFileDescriptionURI
@@ -158,6 +160,19 @@ testParseFileDescription = do
Left e -> expectationFailure $ show e
Right fd -> fd `shouldBe` fileDesc
testRejectYAMLAliases :: IO ()
testRejectYAMLAliases = do
(yaml, sizeLine) <- B.breakSubstring "size: " <$> B.readFile fileDescPath
let (header, groups) = B.breakSubstring "- chunks:" yaml
aliased = header <> "- &g\n " <> B.drop 2 groups <> "- *g\n" <> sizeLine
(strDecode aliased :: Either String (FileDescription 'FRecipient)) `shouldBe` Left "YAML aliases are not allowed"
testRejectTooManyReplicas :: IO ()
testRejectTooManyReplicas = do
let FileDescription {chunks} = fileDesc
repeatReplicas c@FileChunk {replicas} = (c :: FileChunk) {replicas = concat $ replicate 9 replicas}
validateFileDescription ((fileDesc :: FileDescription 'FRecipient) {chunks = map repeatReplicas chunks}) `shouldBe` Left "too many chunk replicas"
testSerializeFileDescription :: HasTestEnv => IO ()
testSerializeFileDescription = withRemoveTmpFile $ do
B.writeFile tmpFileDescPath $ strEncode fileDesc