Skip to content

Commit 7a11626

Browse files
committed
make zero fill configurable
1 parent 21242ac commit 7a11626

File tree

5 files changed

+42
-4
lines changed

5 files changed

+42
-4
lines changed

engine/storage/volume/src/main/java/org/apache/cloudstack/storage/datastore/provider/DefaultHostListener.java

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,7 @@
4343
import com.cloud.storage.StoragePool;
4444
import com.cloud.storage.StoragePoolHostVO;
4545
import com.cloud.storage.StorageService;
46+
import com.cloud.storage.VolumeApiServiceImpl;
4647
import com.cloud.storage.dao.StoragePoolHostDao;
4748
import com.cloud.utils.exception.CloudRuntimeException;
4849

@@ -139,6 +140,15 @@ public boolean hostConnect(long hostId, long poolId) throws StorageConflictExcep
139140
Map<String, String> nfsMountOpts = storageManager.getStoragePoolNFSMountOpts(pool, null).first();
140141

141142
Optional.ofNullable(nfsMountOpts).ifPresent(detailsMap::putAll);
143+
144+
if (pool.getPoolType() == Storage.StoragePoolType.CLVM) {
145+
Boolean clvmSecureZeroFill = VolumeApiServiceImpl.CLVMSecureZeroFill.valueIn(poolId);
146+
if (clvmSecureZeroFill != null) {
147+
detailsMap.put("clvmsecurezerofill", String.valueOf(clvmSecureZeroFill));
148+
logger.debug("Added CLVM secure zero-fill setting: {} for storage pool: {}", clvmSecureZeroFill, pool);
149+
}
150+
}
151+
142152
ModifyStoragePoolCommand cmd = new ModifyStoragePoolCommand(true, pool, detailsMap);
143153
cmd.setWait(modifyStoragePoolCommandWait);
144154
HostVO host = hostDao.findById(hostId);

plugins/hypervisors/kvm/src/main/java/com/cloud/hypervisor/kvm/resource/wrapper/LibvirtModifyStoragePoolCommandWrapper.java

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -52,9 +52,19 @@ public Answer execute(final ModifyStoragePoolCommand command, final LibvirtCompu
5252

5353
final KVMStoragePool storagepool;
5454
try {
55+
Map<String, String> poolDetails = command.getDetails();
56+
if (poolDetails == null) {
57+
poolDetails = new HashMap<>();
58+
}
59+
60+
// Ensure CLVM secure zero-fill setting has a default value if not provided by MS
61+
if (!poolDetails.containsKey(KVMStoragePool.CLVM_SECURE_ZERO_FILL)) {
62+
poolDetails.put(KVMStoragePool.CLVM_SECURE_ZERO_FILL, "false");
63+
}
64+
5565
storagepool =
5666
storagePoolMgr.createStoragePool(command.getPool().getUuid(), command.getPool().getHost(), command.getPool().getPort(), command.getPool().getPath(), command.getPool()
57-
.getUserInfo(), command.getPool().getType(), command.getDetails());
67+
.getUserInfo(), command.getPool().getType(), poolDetails);
5868
if (storagepool == null) {
5969
return new Answer(command, false, " Failed to create storage pool");
6070
}

plugins/hypervisors/kvm/src/main/java/com/cloud/hypervisor/kvm/storage/KVMStoragePool.java

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,8 @@ public interface KVMStoragePool {
3838
public static final long HeartBeatUpdateMaxTries = AgentPropertiesFileHandler.getPropertyValue(AgentProperties.KVM_HEARTBEAT_UPDATE_MAX_TRIES);
3939
public static final long HeartBeatUpdateRetrySleep = AgentPropertiesFileHandler.getPropertyValue(AgentProperties.KVM_HEARTBEAT_UPDATE_RETRY_SLEEP);
4040
public static final long HeartBeatCheckerTimeout = AgentPropertiesFileHandler.getPropertyValue(AgentProperties.KVM_HEARTBEAT_CHECKER_TIMEOUT);
41+
public static final String CLVM_SECURE_ZERO_FILL = "clvmsecurezerofill";
42+
4143

4244
public default KVMPhysicalDisk createPhysicalDisk(String volumeUuid, PhysicalDiskFormat format, Storage.ProvisioningType provisioningType, long size, Long usableSize, byte[] passphrase) {
4345
return createPhysicalDisk(volumeUuid, format, provisioningType, size, passphrase);

plugins/hypervisors/kvm/src/main/java/com/cloud/hypervisor/kvm/storage/LibvirtStorageAdaptor.java

Lines changed: 14 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1452,6 +1452,12 @@ public boolean deletePhysicalDisk(String uuid, KVMStoragePool pool, Storage.Imag
14521452
}
14531453
}
14541454

1455+
private boolean shouldSecureZeroFill(KVMStoragePool pool) {
1456+
Map<String, String> details = pool.getDetails();
1457+
String secureZeroFillStr = (details != null) ? details.get(KVMStoragePool.CLVM_SECURE_ZERO_FILL) : null;
1458+
return Boolean.parseBoolean(secureZeroFillStr);
1459+
}
1460+
14551461
/**
14561462
* Clean up CLVM volume and its snapshots directly using LVM commands.
14571463
* This is used as a fallback when libvirt cannot find or delete the volume.
@@ -1492,8 +1498,14 @@ private boolean cleanupCLVMVolume(String uuid, KVMStoragePool pool) {
14921498

14931499
logger.info("Volume {} exists, proceeding with cleanup", uuid);
14941500

1495-
logger.info("Step 1: Zero-filling volume {} for security", uuid);
1496-
secureZeroFillVolume(lvPath, uuid);
1501+
boolean secureZeroFillEnabled = shouldSecureZeroFill(pool);
1502+
1503+
if (secureZeroFillEnabled) {
1504+
logger.info("Step 1: Zero-filling volume {} for security", uuid);
1505+
secureZeroFillVolume(lvPath, uuid);
1506+
} else {
1507+
logger.info("Secure zero-fill is disabled, skipping zero-filling for volume {}", uuid);
1508+
}
14971509

14981510
logger.info("Step 2: Removing volume {}", uuid);
14991511
Script removeLv = new Script("lvremove", 10000, logger);

server/src/main/java/com/cloud/storage/VolumeApiServiceImpl.java

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -412,6 +412,9 @@ public class VolumeApiServiceImpl extends ManagerBase implements VolumeApiServic
412412
public static final ConfigKey<Boolean> AllowCheckAndRepairVolume = new ConfigKey<>("Advanced", Boolean.class, "volume.check.and.repair.leaks.before.use", "false",
413413
"To check and repair the volume if it has any leaks before performing volume attach or VM start operations", true, ConfigKey.Scope.StoragePool);
414414

415+
public static final ConfigKey<Boolean> CLVMSecureZeroFill = new ConfigKey<>("Advanced", Boolean.class, "clvm.secure.zero.fill", "false",
416+
"When enabled, CLVM volumes to be zero-filled at the time of deletion to prevent data from being recovered by VMs reusing the space, as thick LVM volumes write data linearly", true, ConfigKey.Scope.StoragePool);
417+
415418
private final StateMachine2<Volume.State, Volume.Event, Volume> _volStateMachine;
416419

417420
private static final Set<Volume.State> STATES_VOLUME_CANNOT_BE_DESTROYED = new HashSet<>(Arrays.asList(Volume.State.Destroy, Volume.State.Expunging, Volume.State.Expunged, Volume.State.Allocated));
@@ -5861,7 +5864,8 @@ public ConfigKey<?>[] getConfigKeys() {
58615864
MatchStoragePoolTagsWithDiskOffering,
58625865
UseHttpsToUpload,
58635866
WaitDetachDevice,
5864-
AllowCheckAndRepairVolume
5867+
AllowCheckAndRepairVolume,
5868+
CLVMSecureZeroFill
58655869
};
58665870
}
58675871
}

0 commit comments

Comments
 (0)