mirror of
https://github.com/minio/minio.git
synced 2025-11-09 21:49:46 -05:00
fix possible crashes on deleteMarker replication (#11308)
Delete marker can have `metaSys` set to nil, that can lead to crashes after the delete marker has been healed. Additionally also fix isObjectDangling check for transitioned objects, that do not have parts should be treated similar to Delete marker.
This commit is contained in:
@@ -25,6 +25,7 @@ import (
|
||||
"time"
|
||||
|
||||
"github.com/minio/minio/cmd/logger"
|
||||
"github.com/minio/minio/pkg/bucket/lifecycle"
|
||||
"github.com/minio/minio/pkg/madmin"
|
||||
"github.com/minio/minio/pkg/sync/errgroup"
|
||||
)
|
||||
@@ -226,8 +227,6 @@ func (er erasureObjects) healObject(ctx context.Context, bucket string, object s
|
||||
dryRun := opts.DryRun
|
||||
scanMode := opts.ScanMode
|
||||
|
||||
dataBlocks := lfi.Erasure.DataBlocks
|
||||
|
||||
storageDisks := er.getDisks()
|
||||
storageEndpoints := er.getEndpoints()
|
||||
|
||||
@@ -244,8 +243,8 @@ func (er erasureObjects) healObject(ctx context.Context, bucket string, object s
|
||||
Bucket: bucket,
|
||||
Object: object,
|
||||
DiskCount: len(storageDisks),
|
||||
ParityBlocks: len(storageDisks) / 2,
|
||||
DataBlocks: len(storageDisks) / 2,
|
||||
ParityBlocks: er.defaultParityCount,
|
||||
DataBlocks: len(storageDisks) - er.defaultParityCount,
|
||||
}
|
||||
|
||||
// Loop to find number of disks with valid data, per-drive
|
||||
@@ -316,7 +315,7 @@ func (er erasureObjects) healObject(ctx context.Context, bucket string, object s
|
||||
|
||||
// If less than read quorum number of disks have all the parts
|
||||
// of the data, we can't reconstruct the erasure-coded data.
|
||||
if numAvailableDisks < dataBlocks {
|
||||
if numAvailableDisks < result.DataBlocks {
|
||||
return er.purgeObjectDangling(ctx, bucket, object, versionID, partsMetadata, errs, dataErrs, opts)
|
||||
}
|
||||
|
||||
@@ -333,7 +332,7 @@ func (er erasureObjects) healObject(ctx context.Context, bucket string, object s
|
||||
|
||||
// Latest FileInfo for reference. If a valid metadata is not
|
||||
// present, it is as good as object not found.
|
||||
latestMeta, err := pickValidFileInfo(ctx, partsMetadata, modTime, dataBlocks)
|
||||
latestMeta, err := pickValidFileInfo(ctx, partsMetadata, modTime, result.DataBlocks)
|
||||
if err != nil {
|
||||
return result, toObjectErr(err, bucket, object, versionID)
|
||||
}
|
||||
@@ -363,7 +362,7 @@ func (er erasureObjects) healObject(ctx context.Context, bucket string, object s
|
||||
dataDir = migrateDataDir
|
||||
}
|
||||
|
||||
if !latestMeta.Deleted {
|
||||
if !latestMeta.Deleted || latestMeta.TransitionStatus != lifecycle.TransitionComplete {
|
||||
result.DataBlocks = latestMeta.Erasure.DataBlocks
|
||||
result.ParityBlocks = latestMeta.Erasure.ParityBlocks
|
||||
|
||||
@@ -775,8 +774,10 @@ func isObjectDangling(metaArr []FileInfo, errs []error, dataErrs []error) (valid
|
||||
break
|
||||
}
|
||||
|
||||
if validMeta.Deleted {
|
||||
// notFoundParts is ignored since a delete marker does not have any parts
|
||||
if validMeta.Deleted || validMeta.TransitionStatus == lifecycle.TransitionComplete {
|
||||
// notFoundParts is ignored since a
|
||||
// - delete marker does not have any parts
|
||||
// - transition status of complete has no parts
|
||||
return validMeta, corruptedErasureMeta+notFoundErasureMeta > len(errs)/2
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user