Skip to content
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.

Commit 63c8eb4

Browse files
committedNov 19, 2021
Fix race condition that was causing dangling loop devices
Apparently it is wrong to assume that `DeleteVolume` gets called only after `UnstageVolume` returns success. This was causing the disk image file to be deleted while the volume was still mounted. This would prevent the loop device from getting detached and in turn disk space from getting reclaimed.
1 parent 9d5ed19 commit 63c8eb4

File tree

3 files changed

+22
-2
lines changed

3 files changed

+22
-2
lines changed
 

‎consts.py

+1
Original file line numberDiff line numberDiff line change
@@ -5,3 +5,4 @@
55
DATA_DIR = "/data"
66
CONFIG = {}
77
RESOURCE_EXHAUSTED_EXIT_CODE = 101
8+
VOLUME_IN_USE_EXIT_CODE = 102

‎rawfile_servicer.py

+13-2
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,12 @@
55
from google.protobuf.wrappers_pb2 import BoolValue
66

77
import rawfile_util
8-
from consts import PROVISIONER_VERSION, PROVISIONER_NAME, RESOURCE_EXHAUSTED_EXIT_CODE
8+
from consts import (
9+
PROVISIONER_VERSION,
10+
PROVISIONER_NAME,
11+
RESOURCE_EXHAUSTED_EXIT_CODE,
12+
VOLUME_IN_USE_EXIT_CODE,
13+
)
914
from csi import csi_pb2, csi_pb2_grpc
1015
from declarative import be_symlink, be_absent
1116
from fs_util import device_stats, mountpoint_to_dev
@@ -208,7 +213,13 @@ def CreateVolume(self, request, context):
208213

209214
@log_grpc_request
210215
def DeleteVolume(self, request, context):
211-
scrub(volume_id=request.volume_id)
216+
try:
217+
scrub(volume_id=request.volume_id)
218+
except CalledProcessError as exc:
219+
if exc.returncode == VOLUME_IN_USE_EXIT_CODE:
220+
context.abort(grpc.StatusCode.FAILED_PRECONDITION, "Volume in use")
221+
else:
222+
raise exc
212223
return csi_pb2.DeleteVolumeResponse()
213224

214225
@log_grpc_request

‎remote.py

+8
Original file line numberDiff line numberDiff line change
@@ -3,12 +3,20 @@
33

44
def scrub(volume_id):
55
import time
6+
from subprocess import CalledProcessError
7+
68
import rawfile_util
9+
from consts import VOLUME_IN_USE_EXIT_CODE
710

811
img_dir = rawfile_util.img_dir(volume_id)
912
if not img_dir.exists():
1013
return
1114

15+
img_file = rawfile_util.img_file(volume_id)
16+
loops = rawfile_util.attached_loops(img_file)
17+
if len(loops) > 0:
18+
raise CalledProcessError(returncode=VOLUME_IN_USE_EXIT_CODE, cmd="")
19+
1220
now = time.time()
1321
deleted_at = now
1422
gc_at = now # TODO: GC sensitive PVCs later

0 commit comments

Comments
 (0)
Please sign in to comment.