Chu Cheng Li created HDDS-16314:
-----------------------------------

             Summary: S3 MPU complete does not filter out blocks still in use 
before enqueuing overwritten key versions to deletedTable
                 Key: HDDS-16314
                 URL: https://issues.apache.org/jira/browse/HDDS-16314
             Project: Apache Ozone
          Issue Type: Bug
          Components: OM
            Reporter: Chu Cheng Li


{{S3MultipartUploadCompleteRequest#validateAndUpdateCache}} enqueues the 
overwritten old key versions to deletedTable without calling 
{{filterOutBlocksStillInUse}}, unlike {{OMKeyCommitRequest}} (and its FSO 
variant), which have applied the filter since HDDS-9146 with an explicit 
comment that missing it "causes data loss once those shared blocks are added to 
deletedTable and processed by KeyDeletingService for deletion".

If the key being overwritten shares any ContainerBlockID with the newly 
completed MPU key, those shared blocks are enqueued to deletedTable and 
physically deleted by KeyDeletingService while the live key table entry still 
references them.

A concrete route to that state exists through bucket versioning history:
# With bucket versioning enabled, overwriting a key retains the previous 
version groups ({{OMKeyRequest#prepareFileInfo}} -> 
{{OmKeyInfo#addNewVersion(..., keepOldVersions=true)}}), so the key table entry 
accumulates multiple location version groups.
# Bucket versioning is later disabled (supported via 
{{OMBucketSetPropertyRequest}}).
# An S3 MPU complete overwrites the key. 
{{S3MultipartUploadCompleteRequest#getOmKeyInfo}} builds the new key from the 
existing key table entry, and {{updateLocationInfoList(partLocations, true, 
true)}} replaces only the latest version's block list, so the older version 
groups' blocks remain referenced by the new key. At the same time the overwrite 
branch enqueues ALL of keyToDelete's blocks (older version groups included) to 
deletedTable.
# KeyDeletingService deletes blocks that the live key table entry still 
references -> data loss.

Beyond that route, any state that leaves the key table entry sharing blocks 
with the completed MPU key hits the same double-free; the commit path is 
already hardened against this class of overlap, the MPU complete path is not.

Not reachable via retried/replayed completes (a duplicate complete fails with 
NO_SUCH_MULTIPART_UPLOAD_ERROR because the multipartInfoTable entry is removed 
in the same transaction) nor via hsync block overlap (part blocks are freshly 
allocated).

Fix: apply the same {{filterOutBlocksStillInUse}} protection in 
{{S3MultipartUploadCompleteRequest#validateAndUpdateCache}} before adding the 
old key versions to {{allKeyInfoToRemove}}, mirroring {{OMKeyCommitRequest}}. 
The shared base class covers both the OBS/LEGACY and FSO paths.



--
This message was sent by Atlassian Jira
(v8.20.10#820010)

---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]

Reply via email to