diff --git a/pkg/smb/controllerserver.go b/pkg/smb/controllerserver.go index 9f9eb6a9cd5..377b21f8b40 100644 --- a/pkg/smb/controllerserver.go +++ b/pkg/smb/controllerserver.go @@ -28,6 +28,7 @@ import ( "google.golang.org/grpc/codes" "google.golang.org/grpc/status" "k8s.io/klog/v2" + azcache "sigs.k8s.io/cloud-provider-azure/pkg/cache" ) const ( @@ -98,6 +99,11 @@ func (d *Driver) CreateVolume(ctx context.Context, req *csi.CreateVolumeRequest) } } + if acquired := d.volumeLocks.TryAcquire(name); !acquired { + return nil, status.Errorf(codes.Aborted, volumeOperationAlreadyExistsFmt, name) + } + defer d.volumeLocks.Release(name) + if createSubDir { // Mount smb base share so we can create a subdirectory if err := d.internalMount(ctx, smbVol, volCap, secrets); err != nil { @@ -147,6 +153,11 @@ func (d *Driver) DeleteVolume(ctx context.Context, req *csi.DeleteVolumeRequest) return &csi.DeleteVolumeResponse{}, nil } + if acquired := d.volumeLocks.TryAcquire(volumeID); !acquired { + return nil, status.Errorf(codes.Aborted, volumeOperationAlreadyExistsFmt, volumeID) + } + defer d.volumeLocks.Release(volumeID) + var volCap *csi.VolumeCapability secrets := req.GetSecrets() mountOptions := getMountOptions(secrets) @@ -167,6 +178,16 @@ func (d *Driver) DeleteVolume(ctx context.Context, req *csi.DeleteVolumeRequest) if len(req.GetSecrets()) > 0 && !strings.EqualFold(smbVol.onDelete, retain) { klog.V(2).Infof("begin to delete or archive subdirectory since secret is provided") + // check whether volumeID is in the cache + cache, err := d.volDeletionCache.Get(volumeID, azcache.CacheReadTypeDefault) + if err != nil { + return nil, status.Errorf(codes.Internal, err.Error()) + } + if cache != nil { + klog.V(2).Infof("DeleteVolume: volume %s is already deleted", volumeID) + return &csi.DeleteVolumeResponse{}, nil + } + // mount smb base share so we can delete or archive the subdirectory if err = d.internalMount(ctx, smbVol, volCap, secrets); err != nil { return nil, status.Errorf(codes.Internal, "failed to mount smb server: %v", err.Error()) @@ -211,6 +232,7 @@ func (d *Driver) DeleteVolume(ctx context.Context, req *csi.DeleteVolumeRequest) klog.V(2).Infof("DeleteVolume(%s) does not delete subdirectory", volumeID) } + d.volDeletionCache.Set(volumeID, "") return &csi.DeleteVolumeResponse{}, nil } diff --git a/pkg/smb/smb.go b/pkg/smb/smb.go index d98de18dae2..a62a83dedba 100644 --- a/pkg/smb/smb.go +++ b/pkg/smb/smb.go @@ -82,6 +82,8 @@ type Driver struct { enableGetVolumeStats bool // a timed cache storing volume stats volStatsCache azcache.Resource + // a timed cache storing volume deletion records + volDeletionCache azcache.Resource // this only applies to Windows node removeSMBMappingDuringUnmount bool krb5CacheDirectory string @@ -120,6 +122,9 @@ func NewDriver(options *DriverOptions) *Driver { if driver.volStatsCache, err = azcache.NewTimedCache(time.Duration(options.VolStatsCacheExpireInMinutes)*time.Minute, getter, false); err != nil { klog.Fatalf("%v", err) } + if driver.volDeletionCache, err = azcache.NewTimedCache(time.Minute, getter, false); err != nil { + klog.Fatalf("%v", err) + } return &driver }