errorMsg = "Failed to detach volume";
}
try {
// Look up the VDI
VDI vdi = mount(conn, cmd.getPooltype(), cmd.getVolumeFolder(),cmd.getVolumePath());
// Look up the VM
VM vm = getVM(conn, vmName);
/* For HVM guest, if no pv driver installed, no attach/detach */
boolean isHVM;
if (vm.getPVBootloader(conn).equalsIgnoreCase("")) {
isHVM = true;
} else {
isHVM = false;
}
VMGuestMetrics vgm = vm.getGuestMetrics(conn);
boolean pvDrvInstalled = false;
if (!isRefNull(vgm) && vgm.getPVDriversUpToDate(conn)) {
pvDrvInstalled = true;
}
if (isHVM && !pvDrvInstalled) {
s_logger.warn(errorMsg + ": You attempted an operation on a VM which requires PV drivers to be installed but the drivers were not detected");
return new AttachVolumeAnswer(cmd, "You attempted an operation that requires PV drivers to be installed on the VM. Please install them by inserting xen-pv-drv.iso.");
}
if (attach) {
// Figure out the disk number to attach the VM to
String diskNumber = null;
if( deviceId != null ) {
if( deviceId.longValue() == 3 ) {
String msg = "Device 3 is reserved for CD-ROM, choose other device";
return new AttachVolumeAnswer(cmd,msg);
}
if(isDeviceUsed(conn, vm, deviceId)) {
String msg = "Device " + deviceId + " is used in VM " + vmName;
return new AttachVolumeAnswer(cmd,msg);
}
diskNumber = deviceId.toString();
} else {
diskNumber = getUnusedDeviceNum(conn, vm);
}
// Create a new VBD
VBD.Record vbdr = new VBD.Record();
vbdr.VM = vm;
vbdr.VDI = vdi;
vbdr.bootable = false;
vbdr.userdevice = diskNumber;
vbdr.mode = Types.VbdMode.RW;
vbdr.type = Types.VbdType.DISK;
vbdr.unpluggable = true;
VBD vbd = VBD.create(conn, vbdr);
// Attach the VBD to the VM
vbd.plug(conn);
// Update the VDI's label to include the VM name
vdi.setNameLabel(conn, vmName + "-DATA");
return new AttachVolumeAnswer(cmd, Long.parseLong(diskNumber));
} else {
// Look up all VBDs for this VDI
Set<VBD> vbds = vdi.getVBDs(conn);
// Detach each VBD from its VM, and then destroy it
for (VBD vbd : vbds) {
VBD.Record vbdr = vbd.getRecord(conn);
if (vbdr.currentlyAttached) {
vbd.unplug(conn);
}
vbd.destroy(conn);
}
// Update the VDI's label to be "detached"
vdi.setNameLabel(conn, "detached");
umount(conn, vdi);
return new AttachVolumeAnswer(cmd);
}