Ejemplo n.º 1
0
def run(test, params, env):
    """
    Hot-plug virtio-serial-pci and chardev and virtserialport

    1. Boot a guest without any device
    2. Hot plug virtio-serial-bus
    3. Hot add chardev 1
    4. Hot plug serial port on chardev 1
    5. Transfer data from host to guest via port
    6. Transfer data from guest to host via port

    :param test: kvm test object
    :param params: Dictionary with the test parameters
    :param env: Dictionary with test environment
    """

    vm = env.get_vm(params['main_vm'])
    os_type = params["os_type"]
    char_devices = add_chardev(vm, params)
    serials = params.objects('extra_serials')
    buses, serial_devices = get_buses_and_serial_devices(
        vm, params, char_devices, serials)
    vm.devices.simple_hotplug(buses[0], vm.monitor)
    vm.devices.simple_hotplug(char_devices[0], vm.monitor)
    vm.devices.simple_hotplug(serial_devices[0], vm.monitor)
    for device in serial_devices:
        add_virtio_ports_to_vm(vm, params, device)
    if os_type == "windows":
        driver_name = params["driver_name"]
        session = vm.wait_for_login()
        session = utils_test.qemu.windrv_check_running_verifier(
            session, vm, test, driver_name)
    params['file_transfer_serial_port'] = serials[0]
    transfer_data(params, vm, sender='both')
Ejemplo n.º 2
0
def run(test, params, env):
    """
    Hot-plug chardev and virtserialport

    1. Boot a guest with 1 virtconsole attached to pty backend
    2. Hot plug unix_socket backend
    3. Hot add virtserialport, attached on unix chardev
    4. Transfer data between host and guest via virtserialport
    5. Hot-unplug existed virt-serial-pci, this should success without crash

    :param test: kvm test object
    :param params: Dictionary with the test parameters
    :param env: Dictionary with test environment
    """
    vm = env.get_vm(params['main_vm'])
    char_devices = add_chardev(vm, params)
    serials = params.objects('extra_serials')
    serial_devices = get_buses_and_serial_devices(
        vm, params, char_devices, serials)[1]
    vm.devices.simple_hotplug(char_devices[0], vm.monitor)
    vm.devices.simple_hotplug(serial_devices[0], vm.monitor)
    for device in serial_devices:
        add_virtio_ports_to_vm(vm, params, device)
    params['file_transfer_serial_port'] = serials[0]
    transfer_data(params, vm, sender='both')
    if params.get("unplug_pci") == "yes":
        virtio_serial_pci = get_virtio_serial_pci(vm, serial_devices[0])
        vm.devices.simple_unplug(virtio_serial_pci, vm.monitor)
    vm.verify_kernel_crash()
Ejemplo n.º 3
0
def run(test, params, env):
    """
    Boot guest with virtio-serial-device with multiple virtserialport

    1. Boot a guest with 1 virtio-serial-bus with 3 serial ports
    2. Transfer data from host to guest via port2, port3
    3. Transfer data from guest to host via port2, port3

    :param test: kvm test object
    :param params: Dictionary with the test parameters
    :param env: Dictionary with test environment
    """

    os_type = params["os_type"]
    vm = env.get_vm(params["main_vm"])
    driver_name = params["driver_name"]
    session = vm.wait_for_login()
    if os_type == "windows":
        session = utils_test.qemu.windrv_check_running_verifier(
            session, vm, test, driver_name)
    for port in params.objects("serials")[2:]:
        port_params = params.object_params(port)
        if not port_params['serial_type'].startswith('virt'):
            continue
        params['file_transfer_serial_port'] = port
        transfer_data(params, vm, sender='both')
    vm.verify_kernel_crash()
Ejemplo n.º 4
0
def run(test, params, env):
    """
    Hot-plug virtio-serial-pci and virtserialport

    1. Boot a guest with 2 chardev, no serial port & no pci
    2. Hot plug virtio-serial-bus
    3. Hot add virtserialport, attached on chardev 1
    4. Hot plug another serial port on chardev 2 with "nr=1", should fail
    5. Hot plug the serial port again with "nr=2"
    6. Transfer data from host to guest via port1
    7. Transfer data from guest to host via port2

    :param test: kvm test object
    :param params: Dictionary with the test parameters
    :param env: Dictionary with test environment
    """

    params['serials'] = params.objects('serials')[0]
    vm = env.get_vm(params['main_vm'])
    char_devices = add_chardev(vm, params)
    for device in char_devices:
        extra_params = ' ' + device.cmdline()
        params['extra_params'] = params.get('extra_params', '') + extra_params
    params['start_vm'] = "yes"
    env_process.preprocess(test, params, env)
    vm = env.get_vm(params['main_vm'])
    vm.devices.insert(char_devices)
    serials = params.objects('extra_serials')
    buses = []
    serial_devices = []
    for index, serial_id in enumerate(serials):
        chardev_id = char_devices[index].get_qid()
        params['serial_name_%s' % serial_id] = serial_id
        devices = add_virtserial_device(vm, params, serial_id, chardev_id)
        for device in devices:
            if device.child_bus:
                buses.append(device)
            else:
                serial_devices.append(device)
    vm.devices.simple_hotplug(buses[0], vm.monitor)
    vm.devices.simple_hotplug(serial_devices[0], vm.monitor)
    pre_nr = serial_devices[0].get_param('nr')
    # Try hotplug different device with same 'nr'
    serial_devices[1].set_param('bus', serial_devices[0].get_param('bus'))
    serial_devices[1].set_param('nr', pre_nr)
    try:
        serial_devices[1].hotplug(vm.monitor)
    except QMPCmdError as e:
        if 'A port already exists at id %d' % pre_nr not in str(e.data):
            test.fail('Hotplug fail for %s, not as expected' % str(e.data))
    else:
        test.fail('Hotplug with same "nr" option success while should fail')
    serial_devices[1].set_param('nr', int(pre_nr) + 1)
    vm.devices.simple_hotplug(serial_devices[1], vm.monitor)
    for device in serial_devices:
        add_virtio_ports_to_vm(vm, params, device)
    params['file_transfer_serial_port'] = serials[0]
    transfer_data(params, vm, sender='host')
    params['file_transfer_serial_port'] = serials[1]
    transfer_data(params, vm, sender='guest')
    def run_serial_data_transfer():
        """
        Transfer data between two ports.
        """

        params['file_transfer_serial_port'] = serials[0]
        transfer_data(params, vm, sender='host')
        params['file_transfer_serial_port'] = serials[1]
        transfer_data(params, vm, sender='guest')
def run(test, params, env):
    """
    Test long time virtio serial guest file transfer.

    Steps:
    1) Boot up a VM with virtio serial device.
    2) Create a large file in guest or host(sender).
    3) In 'repeat_time',  repeatedly transfer the file between guest and host
    4) Kill the data transfer process
    5) Check guest running well, no crash

    :param test: QEMU test object.
    :param params: Dictionary with the test parameters.
    :param env: Dictionary with test environment.
    """

    os_type = params["os_type"]
    sender = params['file_sender']
    file_size = int(params.get("filesize", 100))
    continue_time = int(params.get("continue_transfer_time", 600))
    vm = env.get_vm(params["main_vm"])
    session = vm.wait_for_login()
    host_dir = data_dir.get_tmp_dir()
    guest_dir = params.get("tmp_dir", '/var/tmp/')
    host_file_size, guest_file_size, _, _ =\
        get_command_options(sender, file_size)
    host_file_name = generate_data_file(host_dir, host_file_size)
    guest_file_name = generate_data_file(
        guest_dir, guest_file_size, session)

    check_pid_cmd = 'ps aux | grep "%s"| grep -v "grep"'
    host_script = params['host_script']
    guest_script = params["guest_script"]
    logging.info('Transfer data from %s', sender)
    try:
        test_time = time.time() + continue_time
        while time.time() < test_time:
            transfer_data(
                params, vm, host_file_name, guest_file_name, sender, False)
        host_proc = process.getoutput(check_pid_cmd % host_script, shell=True)
        guest_proc = session.cmd_output(check_pid_cmd % guest_script)
        if host_proc:
            host_pid = host_proc.split()[1]
            logging.info("Kill serial process on host")
            os.kill(int(host_pid), signal.SIGINT)
        if guest_proc:
            guest_pid = guest_proc.split()[1]
            logging.info("Kill serial process on guest")
            session.cmd('kill -9 %s' % guest_pid)
    finally:
        clean_cmd = params['clean_cmd']
        session.cmd('%s %s' % (clean_cmd, guest_file_name))
        os.remove(host_file_name)
        session.close()
        vm.verify_kernel_crash()
        vm.destroy()
 def run_serial_data_transfer():
     """
     Transfer data via every virtserialport.
     """
     for serial_port in serials:
         port_params = params.object_params(serial_port)
         if not port_params['serial_type'].startswith('virtserial'):
             continue
         logging.info("transfer data with port %s", serial_port)
         params['file_transfer_serial_port'] = serial_port
         transfer_data(params, vm, sender='both')
    def run_serial_data_transfer():
        """
        Transfer data between two ports.
        """

        for port in params.objects("serials"):
            port_params = params.object_params(port)
            if not port_params['serial_type'].startswith('virt'):
                continue
            params['file_transfer_serial_port'] = port
            transfer_data(params, vm)
Ejemplo n.º 9
0
def run(test, params, env):
    """
    Driver in use test:
    1) boot guest with serial device.
    2) Transfer data between host and guest via serialport.
    3) run interrupt test during background stress test.

    :param test: QEMU test object
    :param params: Dictionary with the test parameters
    :param env: Dictionary with test environment.
    """

    driver = params["driver_name"]
    sender = params['file_sender']
    timeout = int(params.get("login_timeout", 360))
    suppress_exception = params.get("suppress_exception", "no") == "yes"

    vm = env.get_vm(params["main_vm"])
    session = vm.wait_for_login()
    if params["os_type"] == "windows":
        session = utils_test.qemu.windrv_check_running_verifier(
            session, vm, test, driver, timeout)

    bg_thread = run_bg_test(test, params, vm, sender)
    globals().get(params["interrupt_test"])(test, params, vm, session)
    if bg_thread:
        bg_thread.join(timeout=timeout, suppress_exception=suppress_exception)
    if vm.is_alive():
        kill_host_serial_pid(params, vm)
        if (virtio_serial_file_transfer.transfer_data(params,
                                                      vm,
                                                      sender=sender)
                is not True):
            test.fail("Serial data transfter test failed.")
Ejemplo n.º 10
0
def run(test, params, env):
    """
    Test guest with virtio-serial-device with multiple virtserialports
    Scenario 1:
        1.1. Boot a guest with 1 virtio-serial-bus with 3 serial ports
        1.2. Transfer data via every port
    Scenario 2:
        2.1. Start guest with 2 virtio-serial-pci,
        2.2. Each virtio-serial-pci has 3 virtio-serial-ports
        2.3. Transfer data via every port

    :param test: kvm test object
    :param params: Dictionary with the test parameters
    :param env: Dictionary with test environment
    """
    if params.get("start_vm") == 'no':
        num_bus = params.get_numeric("numberic_bus")
        for i in range(2, num_bus + 1):
            serial_name = 'vs%d' % i
            params['serials'] = '%s %s' % (params.get('serials',
                                                      ''), serial_name)
            params['serial_type_%s' % serial_name] = "virtserialport"
            params['serial_bus_%s' % serial_name] = "<new>"
        params['start_vm'] = "yes"
        env_process.preprocess(test, params, env)

    vm = env.get_vm(params['main_vm'])
    os_type = params["os_type"]
    if os_type == "windows":
        driver_name = params["driver_name"]
        session = vm.wait_for_login()
        session = utils_test.qemu.windrv_check_running_verifier(
            session, vm, test, driver_name)
        session.close()

    for port in params.objects("serials"):
        port_params = params.object_params(port)
        if not port_params['serial_type'].startswith('virtserial'):
            continue
        params['file_transfer_serial_port'] = port
        error_context.context("Transfer data with %s" % port, logging.info)
        transfer_data(params, vm, sender='both')
    vm.verify_alive()
    vm.verify_kernel_crash()
Ejemplo n.º 11
0
def run(test, params, env):
    """
    Driver in use test:
    1) boot guest with serial device.
    2) Transfer data between host and guest via serialport.
    3) run interrupt test during background stress test.

    :param test: QEMU test object
    :param params: Dictionary with the test parameters
    :param env: Dictionary with test environment.
    """
    def run_bg_test():
        """
        Run serial data transfer backgroud test.

        :return: return the background case thread if it's successful;
                 else raise error.
        """
        error_context.context("Run serial transfer test in background",
                              logging.info)
        stress_thread = utils_misc.InterruptedThread(
            virtio_serial_file_transfer.transfer_data, (params, vm),
            {"sender": sender})
        stress_thread.start()

        check_bg_timeout = float(params.get('check_bg_timeout', 120))
        if not utils_misc.wait_for(
                lambda: driver_in_use.check_bg_running(vm, params),
                check_bg_timeout, 0, 1):
            test.fail("Backgroud test is not alive!")
        return stress_thread

    driver = params["driver_name"]
    sender = params['file_sender']
    timeout = int(params.get("login_timeout", 360))
    suppress_exception = params.get("suppress_exception", "no") == "yes"

    vm = env.get_vm(params["main_vm"])
    session = vm.wait_for_login()
    if params["os_type"] == "windows":
        session = utils_test.qemu.windrv_check_running_verifier(
            session, vm, test, driver, timeout)

    bg_thread = run_bg_test()
    globals().get(params["interrupt_test"])(test, params, vm, session)
    if bg_thread:
        bg_thread.join(timeout=timeout, suppress_exception=suppress_exception)
    if vm.is_alive():
        kill_host_serial_pid(params, vm)
        if (virtio_serial_file_transfer.transfer_data(params,
                                                      vm,
                                                      sender=sender)
                is not True):
            test.fail("Serial data transfter test failed.")
def run(test, params, env):
    """
    Test virtio serial guest file transfer with max ports.

    Steps:
    1) Boot up a VM with 30 virtserialports on one virtio-serial-pci.
    2) Transfer data via these ports one by one.

    :param test: QEMU test object.
    :param params: Dictionary with the test parameters.
    :param env: Dictionary with test environment.
    """
    num_serial_ports = int(params.get("virtio_serial_ports"))
    for i in range(2, num_serial_ports + 1):
        serial_name = 'vs%d' % i
        params['serials'] = '%s %s' % (params.get('serials', ''), serial_name)
        params['serial_type_%s' % serial_name] = "virtserialport"
    params['start_vm'] = "yes"
    env_process.preprocess(test, params, env)
    vm = env.get_vm(params['main_vm'])
    os_type = params["os_type"]

    if os_type == "windows":
        session = vm.wait_for_login()
        driver_name = params["driver_name"]
        session = utils_test.qemu.windrv_check_running_verifier(
            session, vm, test, driver_name)
        session.close()

    serials = params.objects("serials")
    for serial_port in serials:
        port_params = params.object_params(serial_port)
        if not port_params['serial_type'].startswith('virtserial'):
            continue
        test.log.info("transfer data with port %s", serial_port)
        params['file_transfer_serial_port'] = serial_port
        transfer_data(params, vm, sender='both')

    vm.verify_alive()
    vm.destroy()
Ejemplo n.º 13
0
def run(test, params, env):
    """
    Test hot unplug virtio serial devices.

     1) Start guest with virtio serial device(s).
     2) Transfer data via serial port.
     3) Hot-unplug serial port
     4) Hot-unplug chardev device
     5) Hot-unplug virtio-serial-pci
     6) Hotplug virtio-serial-pci
     7) Hotplug chardev
     8) Hotplug the port
     9) Transfer data via port from guest to host
     10) Hot-unplug serial the port
     11) Hot-plug serial port to the same chardev.
     12) Transfer data via the port from host to guest

    :param test:   QEMU test object.
    :param params: Dictionary with the test parameters.
    :param env:    Dictionary with test environment.
    """
    vm = env.get_vm(params["main_vm"])
    os_type = params["os_type"]
    sleep_time = float(params.get("sleep_time"))
    if os_type == "windows":
        sleep_time += 10
        driver_name = params["driver_name"]
        session = vm.wait_for_login()
        session = utils_test.qemu.windrv_check_running_verifier(
            session, vm, test, driver_name)
    for port in params.objects("serials"):
        port_params = params.object_params(port)
        if not port_params['serial_type'].startswith('virt'):
            continue
        virtio_port = vm.devices.get(port)
        if not virtio_port:
            test.error("Virtio Port '%s' not found" % port)
        chardev_qid = virtio_port.get_param("chardev")
        try:
            port_chardev = vm.devices.get_by_qid(chardev_qid)[0]
        except IndexError:
            test.error("Failed to get device %s" % chardev_qid)
        params['file_transfer_serial_port'] = port
        virtio_serial_pci = get_virtio_serial_pci(vm, virtio_port)
        logging.info("Transfer data with %s before hot-unplugging", port)
        transfer_data(params, vm, sender='both')
        vm.devices.simple_unplug(virtio_port, vm.monitor)
        vm.devices.simple_unplug(port_chardev, vm.monitor)
        vm.devices.simple_unplug(virtio_serial_pci, vm.monitor)
        time.sleep(sleep_time)
        vm.devices.simple_hotplug(virtio_serial_pci, vm.monitor)
        time.sleep(sleep_time)
        vm.devices.simple_hotplug(port_chardev, vm.monitor)
        vm.devices.simple_hotplug(virtio_port, vm.monitor)
        transfer_data(params, vm, sender='guest')
        vm.devices.simple_unplug(virtio_port, vm.monitor)
        vm.devices.simple_hotplug(virtio_port, vm.monitor)
        transfer_data(params, vm, sender='host')
    vm.verify_alive()
    vm.verify_kernel_crash()
Ejemplo n.º 14
0
def run(test, params, env):
    """
    Test hot unplug virtio serial devices.

     1) Start guest with virtio serial device(s).
     2) Run serial data trainsfer in background
     3) Load module in guest os(linux only).
     4) For each of the virtio serial ports, do following steps one by one:
     4.1) Unload module in guest(linux only)
     4.2) Hot-unplug the virtio serial port
     4.3) Hotplug the devices
     4.4) Reload module in the guest(linux only)
     5) Repeat step2,3,4 100 times
     6) Run serial data transfer after repeated unplug/plug
     7) Reboot VM to make sure the guest kernel not panic.

    :param test:   QEMU test object.
    :param params: Dictionary with the test parameters.
    :param env:    Dictionary with test environment.
    """
    vm = env.get_vm(params["main_vm"])
    vm.verify_alive()
    os_type = params["os_type"]
    timeout = int(params.get("login_timeout", 360))
    module = params.get("modprobe_module")
    check_module = params.get_boolean("check_module", True)
    bg_test = params.get_boolean("bg_test", True)
    session = vm.wait_for_login()
    if os_type == "windows":
        driver_name = params["driver_name"]
        session = utils_test.qemu.windrv_check_running_verifier(
            session, vm, test, driver_name)
    if module and check_module:
        error_context.context("Load module %s" % module, logging.info)
        session.cmd("modprobe %s" % module)
        time.sleep(1)
    session.close()

    for port in params.objects("serials"):
        session = vm.wait_for_login(timeout=timeout)
        port_params = params.object_params(port)
        if not port_params['serial_type'].startswith('virt'):
            continue
        virtio_port = vm.devices.get(port)
        if not virtio_port:
            test.fail("Virtio Port '%s' not found" % port)
        chardev_qid = virtio_port.get_param("chardev")
        try:
            port_chardev = vm.devices.get_by_qid(chardev_qid)[0]
        except IndexError:
            test.error("Failed to get device %s" % chardev_qid)
        if port_params['serial_type'] == 'virtserialport':
            params['file_transfer_serial_port'] = port
            if bg_test:
                run_bg_test(test, params, vm)
        for repeat in range(params.get_numeric("repeat_times", 1)):
            repeat += 1
            if module and check_module:
                error_context.context("Unload module %s" % module,
                                      logging.info)
                session.cmd("modprobe -r %s" % module)
                time.sleep(1)
            error_context.context(
                "Unplug virtio port '%s' in %d tune(s)" % (port, repeat),
                logging.info)
            vm.devices.simple_unplug(virtio_port, vm.monitor)
            if port_params.get("unplug_chardev") == "yes":
                error_context.context(
                    "Unplug chardev '%s' for virtio port '%s'" %
                    (port, chardev_qid), logging.info)
                vm.devices.simple_unplug(port_chardev, vm.monitor)
                time.sleep(0.5)
                vm.devices.simple_hotplug(port_chardev, vm.monitor)
            vm.devices.simple_hotplug(virtio_port, vm.monitor)
            if module and check_module:
                error_context.context("Load  module %s" % module, logging.info)
                session.cmd("modprobe %s" % module)
                time.sleep(1)
        session.close()
        host_script = params['host_script']
        check_pid_cmd = 'pgrep -f %s'
        host_proc_pid = process.getoutput(check_pid_cmd % host_script,
                                          shell=True)
        if host_proc_pid:
            logging.info("Kill the first serial process on host")
            result = process.system('kill -9 %s' % host_proc_pid, shell=True)
            if result != 0:
                logging.error(
                    "Failed to kill the first serial process on host!")
        if transfer_data(params, vm) is not True:
            test.fail("Serial data transfter test failed.")
    vm.reboot()
    vm.verify_kernel_crash()
    session = vm.wait_for_login(timeout=timeout)
    session.close()
Ejemplo n.º 15
0
def run(test, params, env):
    """
    Test the related functions of ioeventfd.
    Step:
        Scenario 1:
            1.1 Start guest with ioeventfd=off.
                For windows: Check whether vioscsi.sys verifier enabled in
                the guest.
            1.2 I/O test in the guest.
                For linux: do dd testing.
                For windows: do fio testing.
            1.3 Reboot the guest.
            1.4 Run iozone in the guest.
            1.5 Power off the guest.
            1.6 Repeat the step 1.1-1.5 with ioeventfd=on.
        Scenario 2:
            2.1 Boot guest with ioeventfd=off.
            2.2 Execute info qtree in QMP monitor, info qtree should show the
                ioeventfd = false.
            2.3 Check the ioeventfd=off via /proc/$PID/fd/.
            2.4 Boot guest with ioeventfd=on.
            2.5 Execute info qtree in QMP monitor, info qtree should show the
                ioeventfd = true.
            2.6 Check the ioeventfd=on via /proc/$PID/fd/.
            2.7 Compare the output of 'ls -l /proc/$PID/fd/', the fds with
                "off" should be less than the one with "on".
        Scenario 3:
            3.1 Boot guest with ioeventfd=off and port attched to virtio_serial_pci.
            3.2 Execute info qtree in QMP monitor, info qtree should show the
                ioeventfd = false.
            3.3 Check the ioeventfd=off via /proc/$PID/fd/.
            3.4 Transfer data via the virtserialport.
            3.5 Boot guest with ioeventfd=on attched to one virtio_serial_pci.
            3.6 Execute info qtree in QMP monitor, info qtree should show the
                ioeventfd = true.
            3.7 Check the ioeventfd=on via /proc/$PID/fd/.
            3.8 Compare the output of 'ls -l /proc/$PID/fd/', the fds with
                "off" should be less than the one with "on".
            3.9 Transfer data via the virtserialport.

    :param test: QEMU test object
    :param params: Dictionary with the test parameters
    :param env: Dictionary with test environment.
    """
    def _set_ioeventfd_options():
        """
        Set the ioeventfd options.

        :return: device id with parameter ioeventfd
        """
        dev_type = params.get("dev_type")
        if dev_type == "virtio_serial":
            params['virtio_serial_extra_params_vs1'] = ioeventfd
            dev_id = 'virtio_serial_pci0'
        elif params['drive_format'] == 'virtio':
            params['blk_extra_params_image1'] = ioeventfd
            dev_id = 'image1'
        elif params['drive_format'] == 'scsi-hd':
            params['bus_extra_params_image1'] = ioeventfd
            dev_id = 'virtio_scsi_pci0'
        return dev_id

    def _dd_test(session):
        """ Execute dd testing inside guest. """
        logging.info('Doing dd testing inside guest.')
        logging.debug(session.cmd(params['dd_cmd'], float(params['stress_timeout'])))

    def _fio_test(session):
        """ Execute fio testing inside guest. """
        logging.info('Doing fio testing inside guest.')
        session = utils_test.qemu.windrv_check_running_verifier(
            session, vm, test, params["driver_name"])
        fio = generate_instance(params, vm, 'fio')
        try:
            fio.run(params['fio_options'], float(params['stress_timeout']))
        finally:
            fio.clean()

    def _io_stress_test():
        """ Execute io stress testing inside guest. """
        {'windows': _fio_test, 'linux': _dd_test}[os_type](session)

    def _iozone_test(session):
        """ Execute iozone testing inside guest. """
        logging.info('Doing iozone inside guest.')
        if os_type == 'windows':
            session = utils_test.qemu.windrv_check_running_verifier(
                session, vm, test, params["driver_name"])
        iozone = generate_instance(params, vm, 'iozone')
        try:
            iozone.run(params['iozone_options'], float(params['iozone_timeout']))
        finally:
            iozone.clean()
            return session

    def _check_property(vm, ioeventfd_opt):
        """
        Check the value of ioeventfd by sending "info qtree" in QMP.
        """
        ioevent_qtree_val = 'true' if 'on' in ioeventfd_opt else 'false'
        logging.info('Execute info qtree in QMP monitor.')
        qtree = qemu_qtree.QtreeContainer()
        qtree.parse_info_qtree(vm.monitor.info('qtree'))
        for node in qtree.get_nodes():
            if isinstance(node, qemu_qtree.QtreeDev) and (
                    node.qtree.get('id', None) == dev_id):
                if node.qtree.get('ioeventfd', None) is None:
                    test.fail('The qtree device %s has no property ioeventfd.'
                              % dev_id)
                elif node.qtree['ioeventfd'] == ioevent_qtree_val:
                    logging.info(
                        'The \"%s\" matches with qtree device \"%s\"(%s).' %
                        (ioeventfd_opt, dev_id, ioevent_qtree_val))
                    break
                else:
                    test.fail(
                        'The \"%s\" mismatches with qtree device \"%s\"(%s).' %
                        (ioeventfd_opt, dev_id, ioevent_qtree_val))
        else:
            test.error('No such \"%s\" qtree device.' % dev_id)

    def _get_ioeventfds(ioeventfd_opt):
        """
        Get the number of ioeventfds inside host.
        """
        logging.info('Check the \"%s\" via /proc/$PID/fd/.' % ioeventfd)
        dst_log = 'off' if 'off' in ioeventfd_opt else 'on'
        cmd = 'ls -l /proc/$(pgrep qemu-kvm)/fd > /tmp/{0}; cat /tmp/{0}'.format(dst_log)
        logging.debug('Running \'%s\'' % cmd)
        s, o = process.getstatusoutput(cmd)
        logging.debug(o)
        if s:
            test.error('Failed to get the number of event fd.\n%s' % o)

    def _compare_ioeventfds():
        """
        Compare fd number of ioeventfd=on between ioeventfd=off
        """
        error_context.context(
            'Compare the output of \'ls -l /proc/$PID/fd/\'.', logging.info)
        cmd = 'grep -c eventfd /tmp/off /tmp/on;rm -rf /tmp/off /tmp/on'
        logging.debug('Running \'%s\'' % cmd)
        s, o = process.getstatusoutput(cmd)
        logging.debug(o)
        if s:
            test.error('Failed to compare the outputs.\n%s' % s)
        nums = re.findall(r'\w+:(\d+)', o, re.M)
        if int(nums[0]) > int(nums[1]):
            test.fail('The number of event fds with \"off\" '
                      'should be less than the one with \"on\".')
        logging.info('The number of event fds with \"off\" '
                     'is less than the one with \"on\".')

    params['start_vm'] = 'yes'
    os_type = params['os_type']
    timeout = float(params.get("login_timeout", 240))
    ioeventfds = (params['orig_ioeventfd'], params['new_ioeventfd'])
    for ioeventfd in ioeventfds:
        dev_id = _set_ioeventfd_options()
        error_context.context('Boot a guest with "%s".' % ioeventfd, logging.info)
        env_process.preprocess_vm(test, params, env, params["main_vm"])
        vm = env.get_vm(params["main_vm"])
        vm.verify_alive()
        session = vm.wait_for_login(timeout=timeout)
        if params.get('io_stress', 'no') == 'yes':
            _io_stress_test()
        else:
            _check_property(vm, ioeventfd)
            _get_ioeventfds(ioeventfd)
        if params.get('reboot', 'no') == 'yes':
            error_context.context('Reboot the guest.', logging.info)
            session = _iozone_test(vm.reboot(session, timeout=timeout))
        if params.get('data_transfer', 'no') == 'yes':
            if os_type == 'windows':
                session = utils_test.qemu.windrv_check_running_verifier(
                    session, vm, test, params["driver_name"])
            transfer_data(params, vm)
        session.close()
        vm.destroy(gracefully=True)
    if params.get('compare_fd', 'no') == 'yes':
        _compare_ioeventfds()
Ejemplo n.º 16
0
def run(test, params, env):
    """
    Test hot unplug virtio serial devices.

     1) Start guest with virtio serial device(s).
     2) Run serial data trainsfer in background(windows only)
     3) Load module in guest os(linux only).
     4) For each of the virtio serial ports, do following steps one by one:
     4.1) Unload module in guest(linux only)
     4.2) Hot-unplug the virtio serial port
     4.3) Hotplug the devices
     4.4) Reload module in the guest(linux only)
     5) Repeat step2,3,4 100 times
     6) Run serial data transfer after repeated unplug/plug
     7) Reboot VM to make sure the guest kernel not panic.

    :param test:   QEMU test object.
    :param params: Dictionary with the test parameters.
    :param env:    Dictionary with test environment.
    """

    vm = env.get_vm(params["main_vm"])
    vm.verify_alive()
    timeout = int(params.get("login_timeout", 360))
    if params["os_type"] == "windows":
        run_bg_test(test, params, vm)
    for repeat in range(int(params.get("repeat_times", 1))):
        repeat += 1
        session = vm.wait_for_login(timeout=timeout)
        module = params.get("modprobe_module")
        if module:
            error_context.context("Load module %s" % module, logging.info)
            session.cmd("modprobe %s" % module)
        for port in params.objects("serials"):
            port_params = params.object_params(port)
            if not port_params['serial_type'].startswith('virt'):
                continue
            virtio_port = vm.devices.get(port)
            if not virtio_port:
                test.fail("Virtio Port '%s' not found" % port)
            chardev_qid = virtio_port.get_param("chardev")
            try:
                port_chardev = vm.devices.get_by_qid(chardev_qid)[0]
            except IndexError:
                test.error("Failed to get device %s" % chardev_qid)
            if module:
                error_context.context("Unload module %s" % module,
                                      logging.info)
                session.cmd("modprobe -r %s" % module)
            error_context.context(
                "Unplug virtio port '%s' in %d tune(s)" % (port, repeat),
                logging.info)
            vm.devices.simple_unplug(virtio_port, vm.monitor)
            if port_params.get("unplug_chardev") == "yes":
                error_context.context(
                    "Unplug chardev '%s' for virtio port '%s'" %
                    (port, chardev_qid), logging.info)
                vm.devices.simple_unplug(port_chardev, vm.monitor)
                time.sleep(0.5)
                vm.devices.simple_hotplug(port_chardev, vm.monitor)
            vm.devices.simple_hotplug(virtio_port, vm.monitor)
            if module:
                error_context.context("Load  module %s" % module, logging.info)
                session.cmd("modprobe %s" % module)
        session.close()
    if transfer_data(params, vm) is not True:
        test.fail("Serial data transfter test failed.")
    vm.reboot()
    session = vm.wait_for_login(timeout=timeout)
    session.close()