siyuan-note/siyuan · error
invalid encrypted asset plaintext chunk size
Error message
invalid encrypted asset plaintext chunk size
What it means
After decrypting a chunk, the code validates that the plaintext length equals the expected chunk size (full encryptedAssetChunkSize, or the remaining bytes for the final chunk). This error means decryption produced plaintext of the wrong length — strong evidence of tampering or AAD/context mismatch, since AES-GCM would normally fail authentication first. The chunk is zeroed before returning.
Source
Thrown at kernel/model/crypto.go:2476
aad := encryptedAssetChunkAAD(aadPrefix, metadata.ContainerID, chunkIndex)
if metadata.Spec == encryptedAssetLegacySpec {
aad = []byte(fmt.Sprintf("%s:content:%d", aadPrefix, chunkIndex))
}
plainChunk, chunkErr := util.DecryptWithAAD(
assetKey,
encryptedChunk,
aad,
)
if chunkErr != nil {
return "", chunkErr
}
expectedSize := int64(encryptedAssetChunkSize)
if remaining := metadata.Size - written; remaining < expectedSize {
expectedSize = remaining
}
if int64(len(plainChunk)) != expectedSize {
zeroAndClear(plainChunk)
return "", errors.New("invalid encrypted asset plaintext chunk size")
}
n, writeErr := writer.Write(plainChunk)
written += int64(n)
zeroAndClear(plainChunk)
if writeErr != nil {
return "", writeErr
}
if n != len(plainChunk) {
return "", io.ErrShortWrite
}
}
var terminator uint32
if err = binary.Read(reader, binary.BigEndian, &terminator); err != nil {
return "", err
}
if terminator != 0 || written != metadata.Size {
return "", errors.New("invalid encrypted asset content length")
}View on GitHub (pinned to 8641553a1f)
Solutions
- Treat the file as tampered or corrupt; restore from a verified backup
- Re-encrypt from the original plaintext if it still exists elsewhere
- Compare metadata.Size and the sum of chunk sizes against the file length to locate the inconsistent region
- Verify the file's integrity via sync history or the device it originated from
Defensive patterns
Strategy: try-catch
Try / catch
plain, err := model.DecryptAsset(box, disk, dek, ct)
if err != nil {
if strings.Contains(err.Error(), "plaintext chunk size") {
// treat file as tampered: quarantine and restore from backup
return restoreFromBackup(disk)
}
return err
} Prevention
- Never modify encrypted blobs or their metadata after creation
- Keep backups taken before any encryption-parameter change
When it happens
Trigger: In DecryptAssetToWriter's chunk loop, a decrypted plainChunk's length does not match metadata.Size - written (clamped to encryptedAssetChunkSize). Happens when the file's chunk boundaries were re-framed after encryption or metadata.Size does not match the actual content.
Common situations: A tool rewrote or re-chunked the encrypted file without updating metadata; corruption shifting bytes between chunks; an intentionally tampered ciphertext where GCM tags were also forged (extremely rare).
Understand the failure class
Background: Checksum mismatch errors: "checksum verification failed", "digest mismatch", "expected vs actual checksum" — what they mean and how to fix them — this error's family across 41 libraries.
Related errors
- encrypted .sy [%s]: base id [%s] != root id [%s]
- invalid encrypted asset content length
- cannot rebuild encrypted indexes: %w
- encrypted document is a symbolic link [%s]
- encrypted document root ID does not match filename [%s]
AI-assisted analysis of siyuan-note/siyuan@8641553a1f (2026-09-11).
Data as JSON: /api/errors/0d70d528de01b619.
Report an issue: GitHub.