from ganeti import constants
from ganeti import cli
from ganeti import utils
+from ganeti import errors
from ganeti import serializer
from ganeti import objects
from ganeti import locking
# Won't return
parser.error("Invalid mode: %s" % mode)
+ # Normalize and check parameters
+ if options.host is not None:
+ try:
+ options.host = utils.HostInfo.NormalizeName(options.host)
+ except errors.OpPrereqError, err:
+ parser.error("Invalid hostname '%s': %s" % (options.host, err))
+
+ if options.port is not None:
+ options.port = utils.ValidateServiceName(options.port)
+
if (options.exp_size is not None and
options.exp_size != constants.IE_CUSTOM_SIZE):
try:
_CheckNodeNotDrained(self, self.dst_node.name)
self._cds = None
+ self.dest_disk_info = None
self.dest_x509_ca = None
elif self.export_mode == constants.EXPORT_MODE_REMOTE:
self.dest_x509_ca = cert
# Verify target information
+ disk_info = []
for idx, disk_data in enumerate(self.op.target_node):
try:
- masterd.instance.CheckRemoteExportDiskInfo(cds, idx, disk_data)
+ (host, port) = masterd.instance.CheckRemoteExportDiskInfo(cds, idx,
+ disk_data)
except errors.GenericError, err:
raise errors.OpPrereqError("Target info for disk %s: %s" % (idx, err),
errors.ECODE_INVAL)
+ disk_info.append((host, port))
+
+ assert len(disk_info) == len(self.op.target_node)
+ self.dest_disk_info = disk_info
+
else:
raise errors.ProgrammerError("Unhandled export mode %r" %
self.export_mode)
opts = objects.ImportExportOptions(key_name=key_name,
ca_pem=dest_ca_pem)
- (fin_resu, dresults) = helper.RemoteExport(opts, self.op.target_node,
+ (fin_resu, dresults) = helper.RemoteExport(opts, self.dest_disk_info,
timeouts)
finally:
helper.Cleanup()
ieloop = ImportExportLoop(self._lu)
try:
- for idx, (dev, (host, port, _, _)) in enumerate(zip(instance.disks,
- disk_info)):
+ for idx, (dev, (host, port)) in enumerate(zip(instance.disks,
+ disk_info)):
self._feedback_fn("Sending disk %s to %s:%s" % (idx, host, port))
finished_fn = compat.partial(self._TransferFinished, idx)
ieloop.Add(DiskExport(self._lu, instance.primary_node,
if not utils.VerifySha1Hmac(cds, msg, hmac_digest, salt=hmac_salt):
raise errors.GenericError("HMAC is wrong")
- return (host, port)
+ return (utils.HostInfo.NormalizeName(host),
+ utils.ValidateServiceName(port))
def ComputeRemoteImportDiskInfo(cds, salt, disk_index, host, port):
self.assertRaises(errors.GenericError, CheckRemoteExportDiskInfo,
cds, i, di)
+ def testInvalidHostPort(self):
+ cds = "3ZoJY8KtGJ"
+ salt = "drK5oYiHWD"
+
+ for host in [",", "...", "Hello World", "`", "!", "#", "\\"]:
+ di = ComputeRemoteImportDiskInfo(cds, salt, 0, host, 1234)
+ self.assertRaises(errors.OpPrereqError,
+ CheckRemoteExportDiskInfo, cds, 0, di)
+
+ for port in [-1, 792825908, "HelloWorld!", "`#", "\\\"", "_?_"]:
+ di = ComputeRemoteImportDiskInfo(cds, salt, 0, "localhost", port)
+ self.assertRaises(errors.OpPrereqError,
+ CheckRemoteExportDiskInfo, cds, 0, di)
+
def testCheckErrors(self):
cds = "0776450535a"
self.assertRaises(errors.GenericError, CheckRemoteExportDiskInfo,
$impexpd $src_statusfile invalidmode >/dev/null 2>&1 &&
err "daemon-util succeeded with invalid mode"
-$impexpd $src_statusfile import --compression=rot13 >/dev/null 2>&1 &&
- err "daemon-util succeeded with invalid compression"
+for mode in import export; do
+ $impexpd $src_statusfile $mode --compression=rot13 >/dev/null 2>&1 &&
+ err "daemon-util succeeded with invalid compression"
+
+ for host in '' ' ' ' s p a c e' ... , foo.example.net... \
+ 'some"evil"name' 'x\ny\tmoo'; do
+ $impexpd $src_statusfile $mode --host="$host" >/dev/null 2>&1 &&
+ err "daemon-util succeeded with invalid host '$host'"
+ done
+
+ for port in '' ' ' -1234 'some ` port " here'; do
+ $impexpd $src_statusfile $mode --port="$port" >/dev/null 2>&1 &&
+ err "daemon-util succeeded with invalid port '$port'"
+ done
+done
upto 'Generate test data'
cat $(get_testfile proc_drbd8.txt) $(get_testfile cert1.pem) > $testdata