1 /* 2 * QTest testcase for migration 3 * 4 * Copyright (c) 2016-2018 Red Hat, Inc. and/or its affiliates 5 * based on the vhost-user-test.c that is: 6 * Copyright (c) 2014 Virtual Open Systems Sarl. 7 * 8 * This work is licensed under the terms of the GNU GPL, version 2 or later. 9 * See the COPYING file in the top-level directory. 10 * 11 */ 12 13 #include "qemu/osdep.h" 14 15 #include "libqtest.h" 16 #include "qapi/qmp/qdict.h" 17 #include "qemu/module.h" 18 #include "qemu/option.h" 19 #include "qemu/range.h" 20 #include "qemu/sockets.h" 21 #include "chardev/char.h" 22 #include "crypto/tlscredspsk.h" 23 #include "qapi/qmp/qlist.h" 24 #include "ppc-util.h" 25 26 #include "migration-helpers.h" 27 #include "tests/migration/migration-test.h" 28 #ifdef CONFIG_GNUTLS 29 # include "tests/unit/crypto-tls-psk-helpers.h" 30 # ifdef CONFIG_TASN1 31 # include "tests/unit/crypto-tls-x509-helpers.h" 32 # endif /* CONFIG_TASN1 */ 33 #endif /* CONFIG_GNUTLS */ 34 35 /* For dirty ring test; so far only x86_64 is supported */ 36 #if defined(__linux__) && defined(HOST_X86_64) 37 #include "linux/kvm.h" 38 #endif 39 40 unsigned start_address; 41 unsigned end_address; 42 static bool uffd_feature_thread_id; 43 static QTestMigrationState src_state; 44 static QTestMigrationState dst_state; 45 46 /* 47 * An initial 3 MB offset is used as that corresponds 48 * to ~1 sec of data transfer with our bandwidth setting. 49 */ 50 #define MAGIC_OFFSET_BASE (3 * 1024 * 1024) 51 /* 52 * A further 1k is added to ensure we're not a multiple 53 * of TEST_MEM_PAGE_SIZE, thus avoid clash with writes 54 * from the migration guest workload. 55 */ 56 #define MAGIC_OFFSET_SHUFFLE 1024 57 #define MAGIC_OFFSET (MAGIC_OFFSET_BASE + MAGIC_OFFSET_SHUFFLE) 58 #define MAGIC_MARKER 0xFEED12345678CAFEULL 59 60 /* 61 * Dirtylimit stop working if dirty page rate error 62 * value less than DIRTYLIMIT_TOLERANCE_RANGE 63 */ 64 #define DIRTYLIMIT_TOLERANCE_RANGE 25 /* MB/s */ 65 66 #define ANALYZE_SCRIPT "scripts/analyze-migration.py" 67 #define VMSTATE_CHECKER_SCRIPT "scripts/vmstate-static-checker.py" 68 69 #define QEMU_VM_FILE_MAGIC 0x5145564d 70 #define FILE_TEST_FILENAME "migfile" 71 #define FILE_TEST_OFFSET 0x1000 72 #define FILE_TEST_MARKER 'X' 73 #define QEMU_ENV_SRC "QTEST_QEMU_BINARY_SRC" 74 #define QEMU_ENV_DST "QTEST_QEMU_BINARY_DST" 75 76 #if defined(__linux__) 77 #include <sys/syscall.h> 78 #include <sys/vfs.h> 79 #endif 80 81 #if defined(__linux__) && defined(__NR_userfaultfd) && defined(CONFIG_EVENTFD) 82 #include <sys/eventfd.h> 83 #include <sys/ioctl.h> 84 #include "qemu/userfaultfd.h" 85 86 static bool ufd_version_check(void) 87 { 88 struct uffdio_api api_struct; 89 uint64_t ioctl_mask; 90 91 int ufd = uffd_open(O_CLOEXEC); 92 93 if (ufd == -1) { 94 g_test_message("Skipping test: userfaultfd not available"); 95 return false; 96 } 97 98 api_struct.api = UFFD_API; 99 api_struct.features = 0; 100 if (ioctl(ufd, UFFDIO_API, &api_struct)) { 101 g_test_message("Skipping test: UFFDIO_API failed"); 102 return false; 103 } 104 uffd_feature_thread_id = api_struct.features & UFFD_FEATURE_THREAD_ID; 105 106 ioctl_mask = 1ULL << _UFFDIO_REGISTER | 107 1ULL << _UFFDIO_UNREGISTER; 108 if ((api_struct.ioctls & ioctl_mask) != ioctl_mask) { 109 g_test_message("Skipping test: Missing userfault feature"); 110 return false; 111 } 112 113 return true; 114 } 115 116 #else 117 static bool ufd_version_check(void) 118 { 119 g_test_message("Skipping test: Userfault not available (builtdtime)"); 120 return false; 121 } 122 123 #endif 124 125 static char *tmpfs; 126 static char *bootpath; 127 128 /* The boot file modifies memory area in [start_address, end_address) 129 * repeatedly. It outputs a 'B' at a fixed rate while it's still running. 130 */ 131 #include "tests/migration/i386/a-b-bootblock.h" 132 #include "tests/migration/aarch64/a-b-kernel.h" 133 #include "tests/migration/ppc64/a-b-kernel.h" 134 #include "tests/migration/s390x/a-b-bios.h" 135 136 static void bootfile_create(char *dir, bool suspend_me) 137 { 138 const char *arch = qtest_get_arch(); 139 unsigned char *content; 140 size_t len; 141 142 bootpath = g_strdup_printf("%s/bootsect", dir); 143 if (strcmp(arch, "i386") == 0 || strcmp(arch, "x86_64") == 0) { 144 /* the assembled x86 boot sector should be exactly one sector large */ 145 g_assert(sizeof(x86_bootsect) == 512); 146 x86_bootsect[SYM_suspend_me - SYM_start] = suspend_me; 147 content = x86_bootsect; 148 len = sizeof(x86_bootsect); 149 } else if (g_str_equal(arch, "s390x")) { 150 content = s390x_elf; 151 len = sizeof(s390x_elf); 152 } else if (strcmp(arch, "ppc64") == 0) { 153 content = ppc64_kernel; 154 len = sizeof(ppc64_kernel); 155 } else if (strcmp(arch, "aarch64") == 0) { 156 content = aarch64_kernel; 157 len = sizeof(aarch64_kernel); 158 g_assert(sizeof(aarch64_kernel) <= ARM_TEST_MAX_KERNEL_SIZE); 159 } else { 160 g_assert_not_reached(); 161 } 162 163 FILE *bootfile = fopen(bootpath, "wb"); 164 165 g_assert_cmpint(fwrite(content, len, 1, bootfile), ==, 1); 166 fclose(bootfile); 167 } 168 169 static void bootfile_delete(void) 170 { 171 unlink(bootpath); 172 g_free(bootpath); 173 bootpath = NULL; 174 } 175 176 /* 177 * Wait for some output in the serial output file, 178 * we get an 'A' followed by an endless string of 'B's 179 * but on the destination we won't have the A (unless we enabled suspend/resume) 180 */ 181 static void wait_for_serial(const char *side) 182 { 183 g_autofree char *serialpath = g_strdup_printf("%s/%s", tmpfs, side); 184 FILE *serialfile = fopen(serialpath, "r"); 185 186 do { 187 int readvalue = fgetc(serialfile); 188 189 switch (readvalue) { 190 case 'A': 191 /* Fine */ 192 break; 193 194 case 'B': 195 /* It's alive! */ 196 fclose(serialfile); 197 return; 198 199 case EOF: 200 fseek(serialfile, 0, SEEK_SET); 201 usleep(1000); 202 break; 203 204 default: 205 fprintf(stderr, "Unexpected %d on %s serial\n", readvalue, side); 206 g_assert_not_reached(); 207 } 208 } while (true); 209 } 210 211 static void wait_for_stop(QTestState *who, QTestMigrationState *state) 212 { 213 if (!state->stop_seen) { 214 qtest_qmp_eventwait(who, "STOP"); 215 } 216 } 217 218 static void wait_for_resume(QTestState *who, QTestMigrationState *state) 219 { 220 if (!state->resume_seen) { 221 qtest_qmp_eventwait(who, "RESUME"); 222 } 223 } 224 225 static void wait_for_suspend(QTestState *who, QTestMigrationState *state) 226 { 227 if (state->suspend_me && !state->suspend_seen) { 228 qtest_qmp_eventwait(who, "SUSPEND"); 229 } 230 } 231 232 /* 233 * It's tricky to use qemu's migration event capability with qtest, 234 * events suddenly appearing confuse the qmp()/hmp() responses. 235 */ 236 237 static int64_t read_ram_property_int(QTestState *who, const char *property) 238 { 239 QDict *rsp_return, *rsp_ram; 240 int64_t result; 241 242 rsp_return = migrate_query_not_failed(who); 243 if (!qdict_haskey(rsp_return, "ram")) { 244 /* Still in setup */ 245 result = 0; 246 } else { 247 rsp_ram = qdict_get_qdict(rsp_return, "ram"); 248 result = qdict_get_try_int(rsp_ram, property, 0); 249 } 250 qobject_unref(rsp_return); 251 return result; 252 } 253 254 static int64_t read_migrate_property_int(QTestState *who, const char *property) 255 { 256 QDict *rsp_return; 257 int64_t result; 258 259 rsp_return = migrate_query_not_failed(who); 260 result = qdict_get_try_int(rsp_return, property, 0); 261 qobject_unref(rsp_return); 262 return result; 263 } 264 265 static uint64_t get_migration_pass(QTestState *who) 266 { 267 return read_ram_property_int(who, "dirty-sync-count"); 268 } 269 270 static void read_blocktime(QTestState *who) 271 { 272 QDict *rsp_return; 273 274 rsp_return = migrate_query_not_failed(who); 275 g_assert(qdict_haskey(rsp_return, "postcopy-blocktime")); 276 qobject_unref(rsp_return); 277 } 278 279 /* 280 * Wait for two changes in the migration pass count, but bail if we stop. 281 */ 282 static void wait_for_migration_pass(QTestState *who) 283 { 284 uint64_t pass, prev_pass = 0, changes = 0; 285 286 while (changes < 2 && !src_state.stop_seen && !src_state.suspend_seen) { 287 usleep(1000); 288 pass = get_migration_pass(who); 289 changes += (pass != prev_pass); 290 prev_pass = pass; 291 } 292 } 293 294 static void check_guests_ram(QTestState *who) 295 { 296 /* Our ASM test will have been incrementing one byte from each page from 297 * start_address to < end_address in order. This gives us a constraint 298 * that any page's byte should be equal or less than the previous pages 299 * byte (mod 256); and they should all be equal except for one transition 300 * at the point where we meet the incrementer. (We're running this with 301 * the guest stopped). 302 */ 303 unsigned address; 304 uint8_t first_byte; 305 uint8_t last_byte; 306 bool hit_edge = false; 307 int bad = 0; 308 309 qtest_memread(who, start_address, &first_byte, 1); 310 last_byte = first_byte; 311 312 for (address = start_address + TEST_MEM_PAGE_SIZE; address < end_address; 313 address += TEST_MEM_PAGE_SIZE) 314 { 315 uint8_t b; 316 qtest_memread(who, address, &b, 1); 317 if (b != last_byte) { 318 if (((b + 1) % 256) == last_byte && !hit_edge) { 319 /* This is OK, the guest stopped at the point of 320 * incrementing the previous page but didn't get 321 * to us yet. 322 */ 323 hit_edge = true; 324 last_byte = b; 325 } else { 326 bad++; 327 if (bad <= 10) { 328 fprintf(stderr, "Memory content inconsistency at %x" 329 " first_byte = %x last_byte = %x current = %x" 330 " hit_edge = %x\n", 331 address, first_byte, last_byte, b, hit_edge); 332 } 333 } 334 } 335 } 336 if (bad >= 10) { 337 fprintf(stderr, "and in another %d pages", bad - 10); 338 } 339 g_assert(bad == 0); 340 } 341 342 static void cleanup(const char *filename) 343 { 344 g_autofree char *path = g_strdup_printf("%s/%s", tmpfs, filename); 345 346 unlink(path); 347 } 348 349 static long long migrate_get_parameter_int(QTestState *who, 350 const char *parameter) 351 { 352 QDict *rsp; 353 long long result; 354 355 rsp = qtest_qmp_assert_success_ref( 356 who, "{ 'execute': 'query-migrate-parameters' }"); 357 result = qdict_get_int(rsp, parameter); 358 qobject_unref(rsp); 359 return result; 360 } 361 362 static void migrate_check_parameter_int(QTestState *who, const char *parameter, 363 long long value) 364 { 365 long long result; 366 367 result = migrate_get_parameter_int(who, parameter); 368 g_assert_cmpint(result, ==, value); 369 } 370 371 static void migrate_set_parameter_int(QTestState *who, const char *parameter, 372 long long value) 373 { 374 qtest_qmp_assert_success(who, 375 "{ 'execute': 'migrate-set-parameters'," 376 "'arguments': { %s: %lld } }", 377 parameter, value); 378 migrate_check_parameter_int(who, parameter, value); 379 } 380 381 static char *migrate_get_parameter_str(QTestState *who, 382 const char *parameter) 383 { 384 QDict *rsp; 385 char *result; 386 387 rsp = qtest_qmp_assert_success_ref( 388 who, "{ 'execute': 'query-migrate-parameters' }"); 389 result = g_strdup(qdict_get_str(rsp, parameter)); 390 qobject_unref(rsp); 391 return result; 392 } 393 394 static void migrate_check_parameter_str(QTestState *who, const char *parameter, 395 const char *value) 396 { 397 g_autofree char *result = migrate_get_parameter_str(who, parameter); 398 g_assert_cmpstr(result, ==, value); 399 } 400 401 static void migrate_set_parameter_str(QTestState *who, const char *parameter, 402 const char *value) 403 { 404 qtest_qmp_assert_success(who, 405 "{ 'execute': 'migrate-set-parameters'," 406 "'arguments': { %s: %s } }", 407 parameter, value); 408 migrate_check_parameter_str(who, parameter, value); 409 } 410 411 static long long migrate_get_parameter_bool(QTestState *who, 412 const char *parameter) 413 { 414 QDict *rsp; 415 int result; 416 417 rsp = qtest_qmp_assert_success_ref( 418 who, "{ 'execute': 'query-migrate-parameters' }"); 419 result = qdict_get_bool(rsp, parameter); 420 qobject_unref(rsp); 421 return !!result; 422 } 423 424 static void migrate_check_parameter_bool(QTestState *who, const char *parameter, 425 int value) 426 { 427 int result; 428 429 result = migrate_get_parameter_bool(who, parameter); 430 g_assert_cmpint(result, ==, value); 431 } 432 433 static void migrate_set_parameter_bool(QTestState *who, const char *parameter, 434 int value) 435 { 436 qtest_qmp_assert_success(who, 437 "{ 'execute': 'migrate-set-parameters'," 438 "'arguments': { %s: %i } }", 439 parameter, value); 440 migrate_check_parameter_bool(who, parameter, value); 441 } 442 443 static void migrate_ensure_non_converge(QTestState *who) 444 { 445 /* Can't converge with 1ms downtime + 3 mbs bandwidth limit */ 446 migrate_set_parameter_int(who, "max-bandwidth", 3 * 1000 * 1000); 447 migrate_set_parameter_int(who, "downtime-limit", 1); 448 } 449 450 static void migrate_ensure_converge(QTestState *who) 451 { 452 /* Should converge with 30s downtime + 1 gbs bandwidth limit */ 453 migrate_set_parameter_int(who, "max-bandwidth", 1 * 1000 * 1000 * 1000); 454 migrate_set_parameter_int(who, "downtime-limit", 30 * 1000); 455 } 456 457 /* 458 * Our goal is to ensure that we run a single full migration 459 * iteration, and also dirty memory, ensuring that at least 460 * one further iteration is required. 461 * 462 * We can't directly synchronize with the start of a migration 463 * so we have to apply some tricks monitoring memory that is 464 * transferred. 465 * 466 * Initially we set the migration bandwidth to an insanely 467 * low value, with tiny max downtime too. This basically 468 * guarantees migration will never complete. 469 * 470 * This will result in a test that is unacceptably slow though, 471 * so we can't let the entire migration pass run at this speed. 472 * Our intent is to let it run just long enough that we can 473 * prove data prior to the marker has been transferred *AND* 474 * also prove this transferred data is dirty again. 475 * 476 * Before migration starts, we write a 64-bit magic marker 477 * into a fixed location in the src VM RAM. 478 * 479 * Then watch dst memory until the marker appears. This is 480 * proof that start_address -> MAGIC_OFFSET_BASE has been 481 * transferred. 482 * 483 * Finally we go back to the source and read a byte just 484 * before the marker until we see it flip in value. This 485 * is proof that start_address -> MAGIC_OFFSET_BASE 486 * is now dirty again. 487 * 488 * IOW, we're guaranteed at least a 2nd migration pass 489 * at this point. 490 * 491 * We can now let migration run at full speed to finish 492 * the test 493 */ 494 static void migrate_prepare_for_dirty_mem(QTestState *from) 495 { 496 /* 497 * The guest workflow iterates from start_address to 498 * end_address, writing 1 byte every TEST_MEM_PAGE_SIZE 499 * bytes. 500 * 501 * IOW, if we write to mem at a point which is NOT 502 * a multiple of TEST_MEM_PAGE_SIZE, our write won't 503 * conflict with the migration workflow. 504 * 505 * We put in a marker here, that we'll use to determine 506 * when the data has been transferred to the dst. 507 */ 508 qtest_writeq(from, start_address + MAGIC_OFFSET, MAGIC_MARKER); 509 } 510 511 static void migrate_wait_for_dirty_mem(QTestState *from, 512 QTestState *to) 513 { 514 uint64_t watch_address = start_address + MAGIC_OFFSET_BASE; 515 uint64_t marker_address = start_address + MAGIC_OFFSET; 516 uint8_t watch_byte; 517 518 /* 519 * Wait for the MAGIC_MARKER to get transferred, as an 520 * indicator that a migration pass has made some known 521 * amount of progress. 522 */ 523 do { 524 usleep(1000 * 10); 525 } while (qtest_readq(to, marker_address) != MAGIC_MARKER); 526 527 528 /* If suspended, src only iterates once, and watch_byte may never change */ 529 if (src_state.suspend_me) { 530 return; 531 } 532 533 /* 534 * Now ensure that already transferred bytes are 535 * dirty again from the guest workload. Note the 536 * guest byte value will wrap around and by chance 537 * match the original watch_byte. This is harmless 538 * as we'll eventually see a different value if we 539 * keep watching 540 */ 541 watch_byte = qtest_readb(from, watch_address); 542 do { 543 usleep(1000 * 10); 544 } while (qtest_readb(from, watch_address) == watch_byte); 545 } 546 547 548 static void migrate_pause(QTestState *who) 549 { 550 qtest_qmp_assert_success(who, "{ 'execute': 'migrate-pause' }"); 551 } 552 553 static void migrate_continue(QTestState *who, const char *state) 554 { 555 qtest_qmp_assert_success(who, 556 "{ 'execute': 'migrate-continue'," 557 " 'arguments': { 'state': %s } }", 558 state); 559 } 560 561 static void migrate_recover(QTestState *who, const char *uri) 562 { 563 qtest_qmp_assert_success(who, 564 "{ 'execute': 'migrate-recover', " 565 " 'id': 'recover-cmd', " 566 " 'arguments': { 'uri': %s } }", 567 uri); 568 } 569 570 static void migrate_cancel(QTestState *who) 571 { 572 qtest_qmp_assert_success(who, "{ 'execute': 'migrate_cancel' }"); 573 } 574 575 static void migrate_postcopy_start(QTestState *from, QTestState *to) 576 { 577 qtest_qmp_assert_success(from, "{ 'execute': 'migrate-start-postcopy' }"); 578 579 wait_for_stop(from, &src_state); 580 qtest_qmp_eventwait(to, "RESUME"); 581 } 582 583 typedef struct { 584 /* 585 * QTEST_LOG=1 may override this. When QTEST_LOG=1, we always dump errors 586 * unconditionally, because it means the user would like to be verbose. 587 */ 588 bool hide_stderr; 589 bool use_shmem; 590 /* only launch the target process */ 591 bool only_target; 592 /* Use dirty ring if true; dirty logging otherwise */ 593 bool use_dirty_ring; 594 const char *opts_source; 595 const char *opts_target; 596 /* suspend the src before migrating to dest. */ 597 bool suspend_me; 598 } MigrateStart; 599 600 /* 601 * A hook that runs after the src and dst QEMUs have been 602 * created, but before the migration is started. This can 603 * be used to set migration parameters and capabilities. 604 * 605 * Returns: NULL, or a pointer to opaque state to be 606 * later passed to the TestMigrateFinishHook 607 */ 608 typedef void * (*TestMigrateStartHook)(QTestState *from, 609 QTestState *to); 610 611 /* 612 * A hook that runs after the migration has finished, 613 * regardless of whether it succeeded or failed, but 614 * before QEMU has terminated (unless it self-terminated 615 * due to migration error) 616 * 617 * @opaque is a pointer to state previously returned 618 * by the TestMigrateStartHook if any, or NULL. 619 */ 620 typedef void (*TestMigrateFinishHook)(QTestState *from, 621 QTestState *to, 622 void *opaque); 623 624 typedef struct { 625 /* Optional: fine tune start parameters */ 626 MigrateStart start; 627 628 /* Required: the URI for the dst QEMU to listen on */ 629 const char *listen_uri; 630 631 /* 632 * Optional: the URI for the src QEMU to connect to 633 * If NULL, then it will query the dst QEMU for its actual 634 * listening address and use that as the connect address. 635 * This allows for dynamically picking a free TCP port. 636 */ 637 const char *connect_uri; 638 639 /* 640 * Optional: JSON-formatted list of src QEMU URIs. If a port is 641 * defined as '0' in any QDict key a value of '0' will be 642 * automatically converted to the correct destination port. 643 */ 644 const char *connect_channels; 645 646 /* Optional: callback to run at start to set migration parameters */ 647 TestMigrateStartHook start_hook; 648 /* Optional: callback to run at finish to cleanup */ 649 TestMigrateFinishHook finish_hook; 650 651 /* 652 * Optional: normally we expect the migration process to complete. 653 * 654 * There can be a variety of reasons and stages in which failure 655 * can happen during tests. 656 * 657 * If a failure is expected to happen at time of establishing 658 * the connection, then MIG_TEST_FAIL will indicate that the dst 659 * QEMU is expected to stay running and accept future migration 660 * connections. 661 * 662 * If a failure is expected to happen while processing the 663 * migration stream, then MIG_TEST_FAIL_DEST_QUIT_ERR will indicate 664 * that the dst QEMU is expected to quit with non-zero exit status 665 */ 666 enum { 667 /* This test should succeed, the default */ 668 MIG_TEST_SUCCEED = 0, 669 /* This test should fail, dest qemu should keep alive */ 670 MIG_TEST_FAIL, 671 /* This test should fail, dest qemu should fail with abnormal status */ 672 MIG_TEST_FAIL_DEST_QUIT_ERR, 673 /* The QMP command for this migration should fail with an error */ 674 MIG_TEST_QMP_ERROR, 675 } result; 676 677 /* 678 * Optional: set number of migration passes to wait for, if live==true. 679 * If zero, then merely wait for a few MB of dirty data 680 */ 681 unsigned int iterations; 682 683 /* 684 * Optional: whether the guest CPUs should be running during a precopy 685 * migration test. We used to always run with live but it took much 686 * longer so we reduced live tests to only the ones that have solid 687 * reason to be tested live-only. For each of the new test cases for 688 * precopy please provide justifications to use live explicitly (please 689 * refer to existing ones with live=true), or use live=off by default. 690 */ 691 bool live; 692 693 /* Postcopy specific fields */ 694 void *postcopy_data; 695 bool postcopy_preempt; 696 bool postcopy_recovery_test_fail; 697 } MigrateCommon; 698 699 static int test_migrate_start(QTestState **from, QTestState **to, 700 const char *uri, MigrateStart *args) 701 { 702 g_autofree gchar *arch_source = NULL; 703 g_autofree gchar *arch_target = NULL; 704 /* options for source and target */ 705 g_autofree gchar *arch_opts = NULL; 706 g_autofree gchar *cmd_source = NULL; 707 g_autofree gchar *cmd_target = NULL; 708 const gchar *ignore_stderr; 709 g_autofree char *shmem_opts = NULL; 710 g_autofree char *shmem_path = NULL; 711 const char *kvm_opts = NULL; 712 const char *arch = qtest_get_arch(); 713 const char *memory_size; 714 const char *machine_alias, *machine_opts = ""; 715 g_autofree char *machine = NULL; 716 717 if (args->use_shmem) { 718 if (!g_file_test("/dev/shm", G_FILE_TEST_IS_DIR)) { 719 g_test_skip("/dev/shm is not supported"); 720 return -1; 721 } 722 } 723 724 dst_state = (QTestMigrationState) { }; 725 src_state = (QTestMigrationState) { }; 726 bootfile_create(tmpfs, args->suspend_me); 727 src_state.suspend_me = args->suspend_me; 728 729 if (strcmp(arch, "i386") == 0 || strcmp(arch, "x86_64") == 0) { 730 memory_size = "150M"; 731 732 if (g_str_equal(arch, "i386")) { 733 machine_alias = "pc"; 734 } else { 735 machine_alias = "q35"; 736 } 737 arch_opts = g_strdup_printf( 738 "-drive if=none,id=d0,file=%s,format=raw " 739 "-device ide-hd,drive=d0,secs=1,cyls=1,heads=1", bootpath); 740 start_address = X86_TEST_MEM_START; 741 end_address = X86_TEST_MEM_END; 742 } else if (g_str_equal(arch, "s390x")) { 743 memory_size = "128M"; 744 machine_alias = "s390-ccw-virtio"; 745 arch_opts = g_strdup_printf("-bios %s", bootpath); 746 start_address = S390_TEST_MEM_START; 747 end_address = S390_TEST_MEM_END; 748 } else if (strcmp(arch, "ppc64") == 0) { 749 memory_size = "256M"; 750 start_address = PPC_TEST_MEM_START; 751 end_address = PPC_TEST_MEM_END; 752 machine_alias = "pseries"; 753 machine_opts = "vsmt=8"; 754 arch_opts = g_strdup_printf( 755 "-nodefaults -machine " PSERIES_DEFAULT_CAPABILITIES " " 756 "-bios %s", bootpath); 757 } else if (strcmp(arch, "aarch64") == 0) { 758 memory_size = "150M"; 759 machine_alias = "virt"; 760 machine_opts = "gic-version=3"; 761 arch_opts = g_strdup_printf("-cpu max -kernel %s", bootpath); 762 start_address = ARM_TEST_MEM_START; 763 end_address = ARM_TEST_MEM_END; 764 } else { 765 g_assert_not_reached(); 766 } 767 768 if (!getenv("QTEST_LOG") && args->hide_stderr) { 769 #ifndef _WIN32 770 ignore_stderr = "2>/dev/null"; 771 #else 772 /* 773 * On Windows the QEMU executable is created via CreateProcess() and 774 * IO redirection does not work, so don't bother adding IO redirection 775 * to the command line. 776 */ 777 ignore_stderr = ""; 778 #endif 779 } else { 780 ignore_stderr = ""; 781 } 782 783 if (args->use_shmem) { 784 shmem_path = g_strdup_printf("/dev/shm/qemu-%d", getpid()); 785 shmem_opts = g_strdup_printf( 786 "-object memory-backend-file,id=mem0,size=%s" 787 ",mem-path=%s,share=on -numa node,memdev=mem0", 788 memory_size, shmem_path); 789 } 790 791 if (args->use_dirty_ring) { 792 kvm_opts = ",dirty-ring-size=4096"; 793 } 794 795 if (!qtest_has_machine(machine_alias)) { 796 g_autofree char *msg = g_strdup_printf("machine %s not supported", machine_alias); 797 g_test_skip(msg); 798 return -1; 799 } 800 801 machine = resolve_machine_version(machine_alias, QEMU_ENV_SRC, 802 QEMU_ENV_DST); 803 804 g_test_message("Using machine type: %s", machine); 805 806 cmd_source = g_strdup_printf("-accel kvm%s -accel tcg " 807 "-machine %s,%s " 808 "-name source,debug-threads=on " 809 "-m %s " 810 "-serial file:%s/src_serial " 811 "%s %s %s %s %s", 812 kvm_opts ? kvm_opts : "", 813 machine, machine_opts, 814 memory_size, tmpfs, 815 arch_opts ? arch_opts : "", 816 arch_source ? arch_source : "", 817 shmem_opts ? shmem_opts : "", 818 args->opts_source ? args->opts_source : "", 819 ignore_stderr); 820 if (!args->only_target) { 821 *from = qtest_init_with_env(QEMU_ENV_SRC, cmd_source); 822 qtest_qmp_set_event_callback(*from, 823 migrate_watch_for_events, 824 &src_state); 825 } 826 827 cmd_target = g_strdup_printf("-accel kvm%s -accel tcg " 828 "-machine %s,%s " 829 "-name target,debug-threads=on " 830 "-m %s " 831 "-serial file:%s/dest_serial " 832 "-incoming %s " 833 "%s %s %s %s %s", 834 kvm_opts ? kvm_opts : "", 835 machine, machine_opts, 836 memory_size, tmpfs, uri, 837 arch_opts ? arch_opts : "", 838 arch_target ? arch_target : "", 839 shmem_opts ? shmem_opts : "", 840 args->opts_target ? args->opts_target : "", 841 ignore_stderr); 842 *to = qtest_init_with_env(QEMU_ENV_DST, cmd_target); 843 qtest_qmp_set_event_callback(*to, 844 migrate_watch_for_events, 845 &dst_state); 846 847 /* 848 * Remove shmem file immediately to avoid memory leak in test failed case. 849 * It's valid because QEMU has already opened this file 850 */ 851 if (args->use_shmem) { 852 unlink(shmem_path); 853 } 854 855 return 0; 856 } 857 858 static void test_migrate_end(QTestState *from, QTestState *to, bool test_dest) 859 { 860 unsigned char dest_byte_a, dest_byte_b, dest_byte_c, dest_byte_d; 861 862 qtest_quit(from); 863 864 if (test_dest) { 865 qtest_memread(to, start_address, &dest_byte_a, 1); 866 867 /* Destination still running, wait for a byte to change */ 868 do { 869 qtest_memread(to, start_address, &dest_byte_b, 1); 870 usleep(1000 * 10); 871 } while (dest_byte_a == dest_byte_b); 872 873 qtest_qmp_assert_success(to, "{ 'execute' : 'stop'}"); 874 875 /* With it stopped, check nothing changes */ 876 qtest_memread(to, start_address, &dest_byte_c, 1); 877 usleep(1000 * 200); 878 qtest_memread(to, start_address, &dest_byte_d, 1); 879 g_assert_cmpint(dest_byte_c, ==, dest_byte_d); 880 881 check_guests_ram(to); 882 } 883 884 qtest_quit(to); 885 886 cleanup("migsocket"); 887 cleanup("src_serial"); 888 cleanup("dest_serial"); 889 cleanup(FILE_TEST_FILENAME); 890 } 891 892 #ifdef CONFIG_GNUTLS 893 struct TestMigrateTLSPSKData { 894 char *workdir; 895 char *workdiralt; 896 char *pskfile; 897 char *pskfilealt; 898 }; 899 900 static void * 901 test_migrate_tls_psk_start_common(QTestState *from, 902 QTestState *to, 903 bool mismatch) 904 { 905 struct TestMigrateTLSPSKData *data = 906 g_new0(struct TestMigrateTLSPSKData, 1); 907 908 data->workdir = g_strdup_printf("%s/tlscredspsk0", tmpfs); 909 data->pskfile = g_strdup_printf("%s/%s", data->workdir, 910 QCRYPTO_TLS_CREDS_PSKFILE); 911 g_mkdir_with_parents(data->workdir, 0700); 912 test_tls_psk_init(data->pskfile); 913 914 if (mismatch) { 915 data->workdiralt = g_strdup_printf("%s/tlscredspskalt0", tmpfs); 916 data->pskfilealt = g_strdup_printf("%s/%s", data->workdiralt, 917 QCRYPTO_TLS_CREDS_PSKFILE); 918 g_mkdir_with_parents(data->workdiralt, 0700); 919 test_tls_psk_init_alt(data->pskfilealt); 920 } 921 922 qtest_qmp_assert_success(from, 923 "{ 'execute': 'object-add'," 924 " 'arguments': { 'qom-type': 'tls-creds-psk'," 925 " 'id': 'tlscredspsk0'," 926 " 'endpoint': 'client'," 927 " 'dir': %s," 928 " 'username': 'qemu'} }", 929 data->workdir); 930 931 qtest_qmp_assert_success(to, 932 "{ 'execute': 'object-add'," 933 " 'arguments': { 'qom-type': 'tls-creds-psk'," 934 " 'id': 'tlscredspsk0'," 935 " 'endpoint': 'server'," 936 " 'dir': %s } }", 937 mismatch ? data->workdiralt : data->workdir); 938 939 migrate_set_parameter_str(from, "tls-creds", "tlscredspsk0"); 940 migrate_set_parameter_str(to, "tls-creds", "tlscredspsk0"); 941 942 return data; 943 } 944 945 static void * 946 test_migrate_tls_psk_start_match(QTestState *from, 947 QTestState *to) 948 { 949 return test_migrate_tls_psk_start_common(from, to, false); 950 } 951 952 static void * 953 test_migrate_tls_psk_start_mismatch(QTestState *from, 954 QTestState *to) 955 { 956 return test_migrate_tls_psk_start_common(from, to, true); 957 } 958 959 static void 960 test_migrate_tls_psk_finish(QTestState *from, 961 QTestState *to, 962 void *opaque) 963 { 964 struct TestMigrateTLSPSKData *data = opaque; 965 966 test_tls_psk_cleanup(data->pskfile); 967 if (data->pskfilealt) { 968 test_tls_psk_cleanup(data->pskfilealt); 969 } 970 rmdir(data->workdir); 971 if (data->workdiralt) { 972 rmdir(data->workdiralt); 973 } 974 975 g_free(data->workdiralt); 976 g_free(data->pskfilealt); 977 g_free(data->workdir); 978 g_free(data->pskfile); 979 g_free(data); 980 } 981 982 #ifdef CONFIG_TASN1 983 typedef struct { 984 char *workdir; 985 char *keyfile; 986 char *cacert; 987 char *servercert; 988 char *serverkey; 989 char *clientcert; 990 char *clientkey; 991 } TestMigrateTLSX509Data; 992 993 typedef struct { 994 bool verifyclient; 995 bool clientcert; 996 bool hostileclient; 997 bool authzclient; 998 const char *certhostname; 999 const char *certipaddr; 1000 } TestMigrateTLSX509; 1001 1002 static void * 1003 test_migrate_tls_x509_start_common(QTestState *from, 1004 QTestState *to, 1005 TestMigrateTLSX509 *args) 1006 { 1007 TestMigrateTLSX509Data *data = g_new0(TestMigrateTLSX509Data, 1); 1008 1009 data->workdir = g_strdup_printf("%s/tlscredsx5090", tmpfs); 1010 data->keyfile = g_strdup_printf("%s/key.pem", data->workdir); 1011 1012 data->cacert = g_strdup_printf("%s/ca-cert.pem", data->workdir); 1013 data->serverkey = g_strdup_printf("%s/server-key.pem", data->workdir); 1014 data->servercert = g_strdup_printf("%s/server-cert.pem", data->workdir); 1015 if (args->clientcert) { 1016 data->clientkey = g_strdup_printf("%s/client-key.pem", data->workdir); 1017 data->clientcert = g_strdup_printf("%s/client-cert.pem", data->workdir); 1018 } 1019 1020 g_mkdir_with_parents(data->workdir, 0700); 1021 1022 test_tls_init(data->keyfile); 1023 #ifndef _WIN32 1024 g_assert(link(data->keyfile, data->serverkey) == 0); 1025 #else 1026 g_assert(CreateHardLink(data->serverkey, data->keyfile, NULL) != 0); 1027 #endif 1028 if (args->clientcert) { 1029 #ifndef _WIN32 1030 g_assert(link(data->keyfile, data->clientkey) == 0); 1031 #else 1032 g_assert(CreateHardLink(data->clientkey, data->keyfile, NULL) != 0); 1033 #endif 1034 } 1035 1036 TLS_ROOT_REQ_SIMPLE(cacertreq, data->cacert); 1037 if (args->clientcert) { 1038 TLS_CERT_REQ_SIMPLE_CLIENT(servercertreq, cacertreq, 1039 args->hostileclient ? 1040 QCRYPTO_TLS_TEST_CLIENT_HOSTILE_NAME : 1041 QCRYPTO_TLS_TEST_CLIENT_NAME, 1042 data->clientcert); 1043 } 1044 1045 TLS_CERT_REQ_SIMPLE_SERVER(clientcertreq, cacertreq, 1046 data->servercert, 1047 args->certhostname, 1048 args->certipaddr); 1049 1050 qtest_qmp_assert_success(from, 1051 "{ 'execute': 'object-add'," 1052 " 'arguments': { 'qom-type': 'tls-creds-x509'," 1053 " 'id': 'tlscredsx509client0'," 1054 " 'endpoint': 'client'," 1055 " 'dir': %s," 1056 " 'sanity-check': true," 1057 " 'verify-peer': true} }", 1058 data->workdir); 1059 migrate_set_parameter_str(from, "tls-creds", "tlscredsx509client0"); 1060 if (args->certhostname) { 1061 migrate_set_parameter_str(from, "tls-hostname", args->certhostname); 1062 } 1063 1064 qtest_qmp_assert_success(to, 1065 "{ 'execute': 'object-add'," 1066 " 'arguments': { 'qom-type': 'tls-creds-x509'," 1067 " 'id': 'tlscredsx509server0'," 1068 " 'endpoint': 'server'," 1069 " 'dir': %s," 1070 " 'sanity-check': true," 1071 " 'verify-peer': %i} }", 1072 data->workdir, args->verifyclient); 1073 migrate_set_parameter_str(to, "tls-creds", "tlscredsx509server0"); 1074 1075 if (args->authzclient) { 1076 qtest_qmp_assert_success(to, 1077 "{ 'execute': 'object-add'," 1078 " 'arguments': { 'qom-type': 'authz-simple'," 1079 " 'id': 'tlsauthz0'," 1080 " 'identity': %s} }", 1081 "CN=" QCRYPTO_TLS_TEST_CLIENT_NAME); 1082 migrate_set_parameter_str(to, "tls-authz", "tlsauthz0"); 1083 } 1084 1085 return data; 1086 } 1087 1088 /* 1089 * The normal case: match server's cert hostname against 1090 * whatever host we were telling QEMU to connect to (if any) 1091 */ 1092 static void * 1093 test_migrate_tls_x509_start_default_host(QTestState *from, 1094 QTestState *to) 1095 { 1096 TestMigrateTLSX509 args = { 1097 .verifyclient = true, 1098 .clientcert = true, 1099 .certipaddr = "127.0.0.1" 1100 }; 1101 return test_migrate_tls_x509_start_common(from, to, &args); 1102 } 1103 1104 /* 1105 * The unusual case: the server's cert is different from 1106 * the address we're telling QEMU to connect to (if any), 1107 * so we must give QEMU an explicit hostname to validate 1108 */ 1109 static void * 1110 test_migrate_tls_x509_start_override_host(QTestState *from, 1111 QTestState *to) 1112 { 1113 TestMigrateTLSX509 args = { 1114 .verifyclient = true, 1115 .clientcert = true, 1116 .certhostname = "qemu.org", 1117 }; 1118 return test_migrate_tls_x509_start_common(from, to, &args); 1119 } 1120 1121 /* 1122 * The unusual case: the server's cert is different from 1123 * the address we're telling QEMU to connect to, and so we 1124 * expect the client to reject the server 1125 */ 1126 static void * 1127 test_migrate_tls_x509_start_mismatch_host(QTestState *from, 1128 QTestState *to) 1129 { 1130 TestMigrateTLSX509 args = { 1131 .verifyclient = true, 1132 .clientcert = true, 1133 .certipaddr = "10.0.0.1", 1134 }; 1135 return test_migrate_tls_x509_start_common(from, to, &args); 1136 } 1137 1138 static void * 1139 test_migrate_tls_x509_start_friendly_client(QTestState *from, 1140 QTestState *to) 1141 { 1142 TestMigrateTLSX509 args = { 1143 .verifyclient = true, 1144 .clientcert = true, 1145 .authzclient = true, 1146 .certipaddr = "127.0.0.1", 1147 }; 1148 return test_migrate_tls_x509_start_common(from, to, &args); 1149 } 1150 1151 static void * 1152 test_migrate_tls_x509_start_hostile_client(QTestState *from, 1153 QTestState *to) 1154 { 1155 TestMigrateTLSX509 args = { 1156 .verifyclient = true, 1157 .clientcert = true, 1158 .hostileclient = true, 1159 .authzclient = true, 1160 .certipaddr = "127.0.0.1", 1161 }; 1162 return test_migrate_tls_x509_start_common(from, to, &args); 1163 } 1164 1165 /* 1166 * The case with no client certificate presented, 1167 * and no server verification 1168 */ 1169 static void * 1170 test_migrate_tls_x509_start_allow_anon_client(QTestState *from, 1171 QTestState *to) 1172 { 1173 TestMigrateTLSX509 args = { 1174 .certipaddr = "127.0.0.1", 1175 }; 1176 return test_migrate_tls_x509_start_common(from, to, &args); 1177 } 1178 1179 /* 1180 * The case with no client certificate presented, 1181 * and server verification rejecting 1182 */ 1183 static void * 1184 test_migrate_tls_x509_start_reject_anon_client(QTestState *from, 1185 QTestState *to) 1186 { 1187 TestMigrateTLSX509 args = { 1188 .verifyclient = true, 1189 .certipaddr = "127.0.0.1", 1190 }; 1191 return test_migrate_tls_x509_start_common(from, to, &args); 1192 } 1193 1194 static void 1195 test_migrate_tls_x509_finish(QTestState *from, 1196 QTestState *to, 1197 void *opaque) 1198 { 1199 TestMigrateTLSX509Data *data = opaque; 1200 1201 test_tls_cleanup(data->keyfile); 1202 g_free(data->keyfile); 1203 1204 unlink(data->cacert); 1205 g_free(data->cacert); 1206 unlink(data->servercert); 1207 g_free(data->servercert); 1208 unlink(data->serverkey); 1209 g_free(data->serverkey); 1210 1211 if (data->clientcert) { 1212 unlink(data->clientcert); 1213 g_free(data->clientcert); 1214 } 1215 if (data->clientkey) { 1216 unlink(data->clientkey); 1217 g_free(data->clientkey); 1218 } 1219 1220 rmdir(data->workdir); 1221 g_free(data->workdir); 1222 1223 g_free(data); 1224 } 1225 #endif /* CONFIG_TASN1 */ 1226 #endif /* CONFIG_GNUTLS */ 1227 1228 static int migrate_postcopy_prepare(QTestState **from_ptr, 1229 QTestState **to_ptr, 1230 MigrateCommon *args) 1231 { 1232 QTestState *from, *to; 1233 1234 if (test_migrate_start(&from, &to, "defer", &args->start)) { 1235 return -1; 1236 } 1237 1238 if (args->start_hook) { 1239 args->postcopy_data = args->start_hook(from, to); 1240 } 1241 1242 migrate_set_capability(from, "postcopy-ram", true); 1243 migrate_set_capability(to, "postcopy-ram", true); 1244 migrate_set_capability(to, "postcopy-blocktime", true); 1245 1246 if (args->postcopy_preempt) { 1247 migrate_set_capability(from, "postcopy-preempt", true); 1248 migrate_set_capability(to, "postcopy-preempt", true); 1249 } 1250 1251 migrate_ensure_non_converge(from); 1252 1253 migrate_prepare_for_dirty_mem(from); 1254 qtest_qmp_assert_success(to, "{ 'execute': 'migrate-incoming'," 1255 " 'arguments': { " 1256 " 'channels': [ { 'channel-type': 'main'," 1257 " 'addr': { 'transport': 'socket'," 1258 " 'type': 'inet'," 1259 " 'host': '127.0.0.1'," 1260 " 'port': '0' } } ] } }"); 1261 1262 /* Wait for the first serial output from the source */ 1263 wait_for_serial("src_serial"); 1264 wait_for_suspend(from, &src_state); 1265 1266 migrate_qmp(from, to, NULL, NULL, "{}"); 1267 1268 migrate_wait_for_dirty_mem(from, to); 1269 1270 *from_ptr = from; 1271 *to_ptr = to; 1272 1273 return 0; 1274 } 1275 1276 static void migrate_postcopy_complete(QTestState *from, QTestState *to, 1277 MigrateCommon *args) 1278 { 1279 wait_for_migration_complete(from); 1280 1281 if (args->start.suspend_me) { 1282 /* wakeup succeeds only if guest is suspended */ 1283 qtest_qmp_assert_success(to, "{'execute': 'system_wakeup'}"); 1284 } 1285 1286 /* Make sure we get at least one "B" on destination */ 1287 wait_for_serial("dest_serial"); 1288 1289 if (uffd_feature_thread_id) { 1290 read_blocktime(to); 1291 } 1292 1293 if (args->finish_hook) { 1294 args->finish_hook(from, to, args->postcopy_data); 1295 args->postcopy_data = NULL; 1296 } 1297 1298 test_migrate_end(from, to, true); 1299 } 1300 1301 static void test_postcopy_common(MigrateCommon *args) 1302 { 1303 QTestState *from, *to; 1304 1305 if (migrate_postcopy_prepare(&from, &to, args)) { 1306 return; 1307 } 1308 migrate_postcopy_start(from, to); 1309 migrate_postcopy_complete(from, to, args); 1310 } 1311 1312 static void test_postcopy(void) 1313 { 1314 MigrateCommon args = { }; 1315 1316 test_postcopy_common(&args); 1317 } 1318 1319 static void test_postcopy_suspend(void) 1320 { 1321 MigrateCommon args = { 1322 .start.suspend_me = true, 1323 }; 1324 1325 test_postcopy_common(&args); 1326 } 1327 1328 static void test_postcopy_preempt(void) 1329 { 1330 MigrateCommon args = { 1331 .postcopy_preempt = true, 1332 }; 1333 1334 test_postcopy_common(&args); 1335 } 1336 1337 #ifdef CONFIG_GNUTLS 1338 static void test_postcopy_tls_psk(void) 1339 { 1340 MigrateCommon args = { 1341 .start_hook = test_migrate_tls_psk_start_match, 1342 .finish_hook = test_migrate_tls_psk_finish, 1343 }; 1344 1345 test_postcopy_common(&args); 1346 } 1347 1348 static void test_postcopy_preempt_tls_psk(void) 1349 { 1350 MigrateCommon args = { 1351 .postcopy_preempt = true, 1352 .start_hook = test_migrate_tls_psk_start_match, 1353 .finish_hook = test_migrate_tls_psk_finish, 1354 }; 1355 1356 test_postcopy_common(&args); 1357 } 1358 #endif 1359 1360 static void wait_for_postcopy_status(QTestState *one, const char *status) 1361 { 1362 wait_for_migration_status(one, status, 1363 (const char * []) { "failed", "active", 1364 "completed", NULL }); 1365 } 1366 1367 #ifndef _WIN32 1368 static void postcopy_recover_fail(QTestState *from, QTestState *to) 1369 { 1370 int ret, pair1[2], pair2[2]; 1371 char c; 1372 1373 /* Create two unrelated socketpairs */ 1374 ret = qemu_socketpair(PF_LOCAL, SOCK_STREAM, 0, pair1); 1375 g_assert_cmpint(ret, ==, 0); 1376 1377 ret = qemu_socketpair(PF_LOCAL, SOCK_STREAM, 0, pair2); 1378 g_assert_cmpint(ret, ==, 0); 1379 1380 /* 1381 * Give the guests unpaired ends of the sockets, so they'll all blocked 1382 * at reading. This mimics a wrong channel established. 1383 */ 1384 qtest_qmp_fds_assert_success(from, &pair1[0], 1, 1385 "{ 'execute': 'getfd'," 1386 " 'arguments': { 'fdname': 'fd-mig' }}"); 1387 qtest_qmp_fds_assert_success(to, &pair2[0], 1, 1388 "{ 'execute': 'getfd'," 1389 " 'arguments': { 'fdname': 'fd-mig' }}"); 1390 1391 /* 1392 * Write the 1st byte as QEMU_VM_COMMAND (0x8) for the dest socket, to 1393 * emulate the 1st byte of a real recovery, but stops from there to 1394 * keep dest QEMU in RECOVER. This is needed so that we can kick off 1395 * the recover process on dest QEMU (by triggering the G_IO_IN event). 1396 * 1397 * NOTE: this trick is not needed on src QEMUs, because src doesn't 1398 * rely on an pre-existing G_IO_IN event, so it will always trigger the 1399 * upcoming recovery anyway even if it can read nothing. 1400 */ 1401 #define QEMU_VM_COMMAND 0x08 1402 c = QEMU_VM_COMMAND; 1403 ret = send(pair2[1], &c, 1, 0); 1404 g_assert_cmpint(ret, ==, 1); 1405 1406 migrate_recover(to, "fd:fd-mig"); 1407 migrate_qmp(from, to, "fd:fd-mig", NULL, "{'resume': true}"); 1408 1409 /* 1410 * Make sure both QEMU instances will go into RECOVER stage, then test 1411 * kicking them out using migrate-pause. 1412 */ 1413 wait_for_postcopy_status(from, "postcopy-recover"); 1414 wait_for_postcopy_status(to, "postcopy-recover"); 1415 1416 /* 1417 * This would be issued by the admin upon noticing the hang, we should 1418 * make sure we're able to kick this out. 1419 */ 1420 migrate_pause(from); 1421 wait_for_postcopy_status(from, "postcopy-paused"); 1422 1423 /* Do the same test on dest */ 1424 migrate_pause(to); 1425 wait_for_postcopy_status(to, "postcopy-paused"); 1426 1427 close(pair1[0]); 1428 close(pair1[1]); 1429 close(pair2[0]); 1430 close(pair2[1]); 1431 } 1432 #endif /* _WIN32 */ 1433 1434 static void test_postcopy_recovery_common(MigrateCommon *args) 1435 { 1436 QTestState *from, *to; 1437 g_autofree char *uri = NULL; 1438 1439 /* Always hide errors for postcopy recover tests since they're expected */ 1440 args->start.hide_stderr = true; 1441 1442 if (migrate_postcopy_prepare(&from, &to, args)) { 1443 return; 1444 } 1445 1446 /* Turn postcopy speed down, 4K/s is slow enough on any machines */ 1447 migrate_set_parameter_int(from, "max-postcopy-bandwidth", 4096); 1448 1449 /* Now we start the postcopy */ 1450 migrate_postcopy_start(from, to); 1451 1452 /* 1453 * Wait until postcopy is really started; we can only run the 1454 * migrate-pause command during a postcopy 1455 */ 1456 wait_for_migration_status(from, "postcopy-active", NULL); 1457 1458 /* 1459 * Manually stop the postcopy migration. This emulates a network 1460 * failure with the migration socket 1461 */ 1462 migrate_pause(from); 1463 1464 /* 1465 * Wait for destination side to reach postcopy-paused state. The 1466 * migrate-recover command can only succeed if destination machine 1467 * is in the paused state 1468 */ 1469 wait_for_postcopy_status(to, "postcopy-paused"); 1470 wait_for_postcopy_status(from, "postcopy-paused"); 1471 1472 #ifndef _WIN32 1473 if (args->postcopy_recovery_test_fail) { 1474 /* 1475 * Test when a wrong socket specified for recover, and then the 1476 * ability to kick it out, and continue with a correct socket. 1477 */ 1478 postcopy_recover_fail(from, to); 1479 /* continue with a good recovery */ 1480 } 1481 #endif /* _WIN32 */ 1482 1483 /* 1484 * Create a new socket to emulate a new channel that is different 1485 * from the broken migration channel; tell the destination to 1486 * listen to the new port 1487 */ 1488 uri = g_strdup_printf("unix:%s/migsocket-recover", tmpfs); 1489 migrate_recover(to, uri); 1490 1491 /* 1492 * Try to rebuild the migration channel using the resume flag and 1493 * the newly created channel 1494 */ 1495 migrate_qmp(from, to, uri, NULL, "{'resume': true}"); 1496 1497 /* Restore the postcopy bandwidth to unlimited */ 1498 migrate_set_parameter_int(from, "max-postcopy-bandwidth", 0); 1499 1500 migrate_postcopy_complete(from, to, args); 1501 } 1502 1503 static void test_postcopy_recovery(void) 1504 { 1505 MigrateCommon args = { }; 1506 1507 test_postcopy_recovery_common(&args); 1508 } 1509 1510 #ifndef _WIN32 1511 static void test_postcopy_recovery_double_fail(void) 1512 { 1513 MigrateCommon args = { 1514 .postcopy_recovery_test_fail = true, 1515 }; 1516 1517 test_postcopy_recovery_common(&args); 1518 } 1519 #endif /* _WIN32 */ 1520 1521 #ifdef CONFIG_GNUTLS 1522 static void test_postcopy_recovery_tls_psk(void) 1523 { 1524 MigrateCommon args = { 1525 .start_hook = test_migrate_tls_psk_start_match, 1526 .finish_hook = test_migrate_tls_psk_finish, 1527 }; 1528 1529 test_postcopy_recovery_common(&args); 1530 } 1531 #endif 1532 1533 static void test_postcopy_preempt_recovery(void) 1534 { 1535 MigrateCommon args = { 1536 .postcopy_preempt = true, 1537 }; 1538 1539 test_postcopy_recovery_common(&args); 1540 } 1541 1542 #ifdef CONFIG_GNUTLS 1543 /* This contains preempt+recovery+tls test altogether */ 1544 static void test_postcopy_preempt_all(void) 1545 { 1546 MigrateCommon args = { 1547 .postcopy_preempt = true, 1548 .start_hook = test_migrate_tls_psk_start_match, 1549 .finish_hook = test_migrate_tls_psk_finish, 1550 }; 1551 1552 test_postcopy_recovery_common(&args); 1553 } 1554 1555 #endif 1556 1557 static void test_baddest(void) 1558 { 1559 MigrateStart args = { 1560 .hide_stderr = true 1561 }; 1562 QTestState *from, *to; 1563 1564 if (test_migrate_start(&from, &to, "tcp:127.0.0.1:0", &args)) { 1565 return; 1566 } 1567 migrate_qmp(from, to, "tcp:127.0.0.1:0", NULL, "{}"); 1568 wait_for_migration_fail(from, false); 1569 test_migrate_end(from, to, false); 1570 } 1571 1572 #ifndef _WIN32 1573 static void test_analyze_script(void) 1574 { 1575 MigrateStart args = { 1576 .opts_source = "-uuid 11111111-1111-1111-1111-111111111111", 1577 }; 1578 QTestState *from, *to; 1579 g_autofree char *uri = NULL; 1580 g_autofree char *file = NULL; 1581 int pid, wstatus; 1582 const char *python = g_getenv("PYTHON"); 1583 1584 if (!python) { 1585 g_test_skip("PYTHON variable not set"); 1586 return; 1587 } 1588 1589 /* dummy url */ 1590 if (test_migrate_start(&from, &to, "tcp:127.0.0.1:0", &args)) { 1591 return; 1592 } 1593 1594 /* 1595 * Setting these two capabilities causes the "configuration" 1596 * vmstate to include subsections for them. The script needs to 1597 * parse those subsections properly. 1598 */ 1599 migrate_set_capability(from, "validate-uuid", true); 1600 migrate_set_capability(from, "x-ignore-shared", true); 1601 1602 file = g_strdup_printf("%s/migfile", tmpfs); 1603 uri = g_strdup_printf("exec:cat > %s", file); 1604 1605 migrate_ensure_converge(from); 1606 migrate_qmp(from, to, uri, NULL, "{}"); 1607 wait_for_migration_complete(from); 1608 1609 pid = fork(); 1610 if (!pid) { 1611 close(1); 1612 open("/dev/null", O_WRONLY); 1613 execl(python, python, ANALYZE_SCRIPT, "-f", file, NULL); 1614 g_assert_not_reached(); 1615 } 1616 1617 g_assert(waitpid(pid, &wstatus, 0) == pid); 1618 if (!WIFEXITED(wstatus) || WEXITSTATUS(wstatus) != 0) { 1619 g_test_message("Failed to analyze the migration stream"); 1620 g_test_fail(); 1621 } 1622 test_migrate_end(from, to, false); 1623 cleanup("migfile"); 1624 } 1625 1626 static void test_vmstate_checker_script(void) 1627 { 1628 g_autofree gchar *cmd_src = NULL; 1629 g_autofree gchar *cmd_dst = NULL; 1630 g_autofree gchar *vmstate_src = NULL; 1631 g_autofree gchar *vmstate_dst = NULL; 1632 const char *machine_alias, *machine_opts = ""; 1633 g_autofree char *machine = NULL; 1634 const char *arch = qtest_get_arch(); 1635 int pid, wstatus; 1636 const char *python = g_getenv("PYTHON"); 1637 1638 if (!getenv(QEMU_ENV_SRC) && !getenv(QEMU_ENV_DST)) { 1639 g_test_skip("Test needs two different QEMU versions"); 1640 return; 1641 } 1642 1643 if (!python) { 1644 g_test_skip("PYTHON variable not set"); 1645 return; 1646 } 1647 1648 if (strcmp(arch, "i386") == 0 || strcmp(arch, "x86_64") == 0) { 1649 if (g_str_equal(arch, "i386")) { 1650 machine_alias = "pc"; 1651 } else { 1652 machine_alias = "q35"; 1653 } 1654 } else if (g_str_equal(arch, "s390x")) { 1655 machine_alias = "s390-ccw-virtio"; 1656 } else if (strcmp(arch, "ppc64") == 0) { 1657 machine_alias = "pseries"; 1658 } else if (strcmp(arch, "aarch64") == 0) { 1659 machine_alias = "virt"; 1660 } else { 1661 g_assert_not_reached(); 1662 } 1663 1664 if (!qtest_has_machine(machine_alias)) { 1665 g_autofree char *msg = g_strdup_printf("machine %s not supported", machine_alias); 1666 g_test_skip(msg); 1667 return; 1668 } 1669 1670 machine = resolve_machine_version(machine_alias, QEMU_ENV_SRC, 1671 QEMU_ENV_DST); 1672 1673 vmstate_src = g_strdup_printf("%s/vmstate-src", tmpfs); 1674 vmstate_dst = g_strdup_printf("%s/vmstate-dst", tmpfs); 1675 1676 cmd_dst = g_strdup_printf("-machine %s,%s -dump-vmstate %s", 1677 machine, machine_opts, vmstate_dst); 1678 cmd_src = g_strdup_printf("-machine %s,%s -dump-vmstate %s", 1679 machine, machine_opts, vmstate_src); 1680 1681 qtest_init_with_env_no_handshake(QEMU_ENV_SRC, cmd_src); 1682 qtest_init_with_env_no_handshake(QEMU_ENV_DST, cmd_dst); 1683 1684 pid = fork(); 1685 if (!pid) { 1686 close(1); 1687 open("/dev/null", O_WRONLY); 1688 execl(python, python, VMSTATE_CHECKER_SCRIPT, 1689 "-s", vmstate_src, 1690 "-d", vmstate_dst, 1691 NULL); 1692 g_assert_not_reached(); 1693 } 1694 1695 g_assert(waitpid(pid, &wstatus, 0) == pid); 1696 if (!WIFEXITED(wstatus) || WEXITSTATUS(wstatus) != 0) { 1697 g_test_message("Failed to run vmstate-static-checker.py"); 1698 g_test_fail(); 1699 } 1700 1701 cleanup("vmstate-src"); 1702 cleanup("vmstate-dst"); 1703 } 1704 #endif 1705 1706 static void test_precopy_common(MigrateCommon *args) 1707 { 1708 QTestState *from, *to; 1709 void *data_hook = NULL; 1710 1711 if (test_migrate_start(&from, &to, args->listen_uri, &args->start)) { 1712 return; 1713 } 1714 1715 if (args->start_hook) { 1716 data_hook = args->start_hook(from, to); 1717 } 1718 1719 /* Wait for the first serial output from the source */ 1720 if (args->result == MIG_TEST_SUCCEED) { 1721 wait_for_serial("src_serial"); 1722 wait_for_suspend(from, &src_state); 1723 } 1724 1725 if (args->live) { 1726 migrate_ensure_non_converge(from); 1727 migrate_prepare_for_dirty_mem(from); 1728 } else { 1729 /* 1730 * Testing non-live migration, we allow it to run at 1731 * full speed to ensure short test case duration. 1732 * For tests expected to fail, we don't need to 1733 * change anything. 1734 */ 1735 if (args->result == MIG_TEST_SUCCEED) { 1736 qtest_qmp_assert_success(from, "{ 'execute' : 'stop'}"); 1737 wait_for_stop(from, &src_state); 1738 migrate_ensure_converge(from); 1739 } 1740 } 1741 1742 if (args->result == MIG_TEST_QMP_ERROR) { 1743 migrate_qmp_fail(from, args->connect_uri, args->connect_channels, "{}"); 1744 goto finish; 1745 } 1746 1747 migrate_qmp(from, to, args->connect_uri, args->connect_channels, "{}"); 1748 1749 if (args->result != MIG_TEST_SUCCEED) { 1750 bool allow_active = args->result == MIG_TEST_FAIL; 1751 wait_for_migration_fail(from, allow_active); 1752 1753 if (args->result == MIG_TEST_FAIL_DEST_QUIT_ERR) { 1754 qtest_set_expected_status(to, EXIT_FAILURE); 1755 } 1756 } else { 1757 if (args->live) { 1758 /* 1759 * For initial iteration(s) we must do a full pass, 1760 * but for the final iteration, we need only wait 1761 * for some dirty mem before switching to converge 1762 */ 1763 while (args->iterations > 1) { 1764 wait_for_migration_pass(from); 1765 args->iterations--; 1766 } 1767 migrate_wait_for_dirty_mem(from, to); 1768 1769 migrate_ensure_converge(from); 1770 1771 /* 1772 * We do this first, as it has a timeout to stop us 1773 * hanging forever if migration didn't converge 1774 */ 1775 wait_for_migration_complete(from); 1776 1777 wait_for_stop(from, &src_state); 1778 1779 } else { 1780 wait_for_migration_complete(from); 1781 /* 1782 * Must wait for dst to finish reading all incoming 1783 * data on the socket before issuing 'cont' otherwise 1784 * it'll be ignored 1785 */ 1786 wait_for_migration_complete(to); 1787 1788 qtest_qmp_assert_success(to, "{ 'execute' : 'cont'}"); 1789 } 1790 1791 wait_for_resume(to, &dst_state); 1792 1793 if (args->start.suspend_me) { 1794 /* wakeup succeeds only if guest is suspended */ 1795 qtest_qmp_assert_success(to, "{'execute': 'system_wakeup'}"); 1796 } 1797 1798 wait_for_serial("dest_serial"); 1799 } 1800 1801 finish: 1802 if (args->finish_hook) { 1803 args->finish_hook(from, to, data_hook); 1804 } 1805 1806 test_migrate_end(from, to, args->result == MIG_TEST_SUCCEED); 1807 } 1808 1809 static void file_dirty_offset_region(void) 1810 { 1811 g_autofree char *path = g_strdup_printf("%s/%s", tmpfs, FILE_TEST_FILENAME); 1812 size_t size = FILE_TEST_OFFSET; 1813 g_autofree char *data = g_new0(char, size); 1814 1815 memset(data, FILE_TEST_MARKER, size); 1816 g_assert(g_file_set_contents(path, data, size, NULL)); 1817 } 1818 1819 static void file_check_offset_region(void) 1820 { 1821 g_autofree char *path = g_strdup_printf("%s/%s", tmpfs, FILE_TEST_FILENAME); 1822 size_t size = FILE_TEST_OFFSET; 1823 g_autofree char *expected = g_new0(char, size); 1824 g_autofree char *actual = NULL; 1825 uint64_t *stream_start; 1826 1827 /* 1828 * Ensure the skipped offset region's data has not been touched 1829 * and the migration stream starts at the right place. 1830 */ 1831 1832 memset(expected, FILE_TEST_MARKER, size); 1833 1834 g_assert(g_file_get_contents(path, &actual, NULL, NULL)); 1835 g_assert(!memcmp(actual, expected, size)); 1836 1837 stream_start = (uint64_t *)(actual + size); 1838 g_assert_cmpint(cpu_to_be64(*stream_start) >> 32, ==, QEMU_VM_FILE_MAGIC); 1839 } 1840 1841 static void test_file_common(MigrateCommon *args, bool stop_src) 1842 { 1843 QTestState *from, *to; 1844 void *data_hook = NULL; 1845 bool check_offset = false; 1846 1847 if (test_migrate_start(&from, &to, args->listen_uri, &args->start)) { 1848 return; 1849 } 1850 1851 /* 1852 * File migration is never live. We can keep the source VM running 1853 * during migration, but the destination will not be running 1854 * concurrently. 1855 */ 1856 g_assert_false(args->live); 1857 1858 if (g_strrstr(args->connect_uri, "offset=")) { 1859 check_offset = true; 1860 /* 1861 * This comes before the start_hook because it's equivalent to 1862 * a management application creating the file and writing to 1863 * it so hooks should expect the file to be already present. 1864 */ 1865 file_dirty_offset_region(); 1866 } 1867 1868 if (args->start_hook) { 1869 data_hook = args->start_hook(from, to); 1870 } 1871 1872 migrate_ensure_converge(from); 1873 wait_for_serial("src_serial"); 1874 1875 if (stop_src) { 1876 qtest_qmp_assert_success(from, "{ 'execute' : 'stop'}"); 1877 wait_for_stop(from, &src_state); 1878 } 1879 1880 if (args->result == MIG_TEST_QMP_ERROR) { 1881 migrate_qmp_fail(from, args->connect_uri, NULL, "{}"); 1882 goto finish; 1883 } 1884 1885 migrate_qmp(from, to, args->connect_uri, NULL, "{}"); 1886 wait_for_migration_complete(from); 1887 1888 /* 1889 * We need to wait for the source to finish before starting the 1890 * destination. 1891 */ 1892 migrate_incoming_qmp(to, args->connect_uri, "{}"); 1893 wait_for_migration_complete(to); 1894 1895 if (stop_src) { 1896 qtest_qmp_assert_success(to, "{ 'execute' : 'cont'}"); 1897 } 1898 wait_for_resume(to, &dst_state); 1899 1900 wait_for_serial("dest_serial"); 1901 1902 if (check_offset) { 1903 file_check_offset_region(); 1904 } 1905 1906 finish: 1907 if (args->finish_hook) { 1908 args->finish_hook(from, to, data_hook); 1909 } 1910 1911 test_migrate_end(from, to, args->result == MIG_TEST_SUCCEED); 1912 } 1913 1914 static void test_precopy_unix_plain(void) 1915 { 1916 g_autofree char *uri = g_strdup_printf("unix:%s/migsocket", tmpfs); 1917 MigrateCommon args = { 1918 .listen_uri = uri, 1919 .connect_uri = uri, 1920 /* 1921 * The simplest use case of precopy, covering smoke tests of 1922 * get-dirty-log dirty tracking. 1923 */ 1924 .live = true, 1925 }; 1926 1927 test_precopy_common(&args); 1928 } 1929 1930 static void test_precopy_unix_suspend_live(void) 1931 { 1932 g_autofree char *uri = g_strdup_printf("unix:%s/migsocket", tmpfs); 1933 MigrateCommon args = { 1934 .listen_uri = uri, 1935 .connect_uri = uri, 1936 /* 1937 * despite being live, the test is fast because the src 1938 * suspends immediately. 1939 */ 1940 .live = true, 1941 .start.suspend_me = true, 1942 }; 1943 1944 test_precopy_common(&args); 1945 } 1946 1947 static void test_precopy_unix_suspend_notlive(void) 1948 { 1949 g_autofree char *uri = g_strdup_printf("unix:%s/migsocket", tmpfs); 1950 MigrateCommon args = { 1951 .listen_uri = uri, 1952 .connect_uri = uri, 1953 .start.suspend_me = true, 1954 }; 1955 1956 test_precopy_common(&args); 1957 } 1958 1959 static void test_precopy_unix_dirty_ring(void) 1960 { 1961 g_autofree char *uri = g_strdup_printf("unix:%s/migsocket", tmpfs); 1962 MigrateCommon args = { 1963 .start = { 1964 .use_dirty_ring = true, 1965 }, 1966 .listen_uri = uri, 1967 .connect_uri = uri, 1968 /* 1969 * Besides the precopy/unix basic test, cover dirty ring interface 1970 * rather than get-dirty-log. 1971 */ 1972 .live = true, 1973 }; 1974 1975 test_precopy_common(&args); 1976 } 1977 1978 #ifdef CONFIG_GNUTLS 1979 static void test_precopy_unix_tls_psk(void) 1980 { 1981 g_autofree char *uri = g_strdup_printf("unix:%s/migsocket", tmpfs); 1982 MigrateCommon args = { 1983 .connect_uri = uri, 1984 .listen_uri = uri, 1985 .start_hook = test_migrate_tls_psk_start_match, 1986 .finish_hook = test_migrate_tls_psk_finish, 1987 }; 1988 1989 test_precopy_common(&args); 1990 } 1991 1992 #ifdef CONFIG_TASN1 1993 static void test_precopy_unix_tls_x509_default_host(void) 1994 { 1995 g_autofree char *uri = g_strdup_printf("unix:%s/migsocket", tmpfs); 1996 MigrateCommon args = { 1997 .start = { 1998 .hide_stderr = true, 1999 }, 2000 .connect_uri = uri, 2001 .listen_uri = uri, 2002 .start_hook = test_migrate_tls_x509_start_default_host, 2003 .finish_hook = test_migrate_tls_x509_finish, 2004 .result = MIG_TEST_FAIL_DEST_QUIT_ERR, 2005 }; 2006 2007 test_precopy_common(&args); 2008 } 2009 2010 static void test_precopy_unix_tls_x509_override_host(void) 2011 { 2012 g_autofree char *uri = g_strdup_printf("unix:%s/migsocket", tmpfs); 2013 MigrateCommon args = { 2014 .connect_uri = uri, 2015 .listen_uri = uri, 2016 .start_hook = test_migrate_tls_x509_start_override_host, 2017 .finish_hook = test_migrate_tls_x509_finish, 2018 }; 2019 2020 test_precopy_common(&args); 2021 } 2022 #endif /* CONFIG_TASN1 */ 2023 #endif /* CONFIG_GNUTLS */ 2024 2025 #if 0 2026 /* Currently upset on aarch64 TCG */ 2027 static void test_ignore_shared(void) 2028 { 2029 g_autofree char *uri = g_strdup_printf("unix:%s/migsocket", tmpfs); 2030 QTestState *from, *to; 2031 2032 if (test_migrate_start(&from, &to, uri, false, true, NULL, NULL)) { 2033 return; 2034 } 2035 2036 migrate_ensure_non_converge(from); 2037 migrate_prepare_for_dirty_mem(from); 2038 2039 migrate_set_capability(from, "x-ignore-shared", true); 2040 migrate_set_capability(to, "x-ignore-shared", true); 2041 2042 /* Wait for the first serial output from the source */ 2043 wait_for_serial("src_serial"); 2044 2045 migrate_qmp(from, to, uri, NULL, "{}"); 2046 2047 migrate_wait_for_dirty_mem(from, to); 2048 2049 wait_for_stop(from, &src_state); 2050 2051 qtest_qmp_eventwait(to, "RESUME"); 2052 2053 wait_for_serial("dest_serial"); 2054 wait_for_migration_complete(from); 2055 2056 /* Check whether shared RAM has been really skipped */ 2057 g_assert_cmpint(read_ram_property_int(from, "transferred"), <, 1024 * 1024); 2058 2059 test_migrate_end(from, to, true); 2060 } 2061 #endif 2062 2063 static void * 2064 test_migrate_xbzrle_start(QTestState *from, 2065 QTestState *to) 2066 { 2067 migrate_set_parameter_int(from, "xbzrle-cache-size", 33554432); 2068 2069 migrate_set_capability(from, "xbzrle", true); 2070 migrate_set_capability(to, "xbzrle", true); 2071 2072 return NULL; 2073 } 2074 2075 static void test_precopy_unix_xbzrle(void) 2076 { 2077 g_autofree char *uri = g_strdup_printf("unix:%s/migsocket", tmpfs); 2078 MigrateCommon args = { 2079 .connect_uri = uri, 2080 .listen_uri = uri, 2081 .start_hook = test_migrate_xbzrle_start, 2082 .iterations = 2, 2083 /* 2084 * XBZRLE needs pages to be modified when doing the 2nd+ round 2085 * iteration to have real data pushed to the stream. 2086 */ 2087 .live = true, 2088 }; 2089 2090 test_precopy_common(&args); 2091 } 2092 2093 static void test_precopy_file(void) 2094 { 2095 g_autofree char *uri = g_strdup_printf("file:%s/%s", tmpfs, 2096 FILE_TEST_FILENAME); 2097 MigrateCommon args = { 2098 .connect_uri = uri, 2099 .listen_uri = "defer", 2100 }; 2101 2102 test_file_common(&args, true); 2103 } 2104 2105 #ifndef _WIN32 2106 static void fdset_add_fds(QTestState *qts, const char *file, int flags, 2107 int num_fds, bool direct_io) 2108 { 2109 for (int i = 0; i < num_fds; i++) { 2110 int fd; 2111 2112 #ifdef O_DIRECT 2113 /* only secondary channels can use direct-io */ 2114 if (direct_io && i != 0) { 2115 flags |= O_DIRECT; 2116 } 2117 #endif 2118 2119 fd = open(file, flags, 0660); 2120 assert(fd != -1); 2121 2122 qtest_qmp_fds_assert_success(qts, &fd, 1, "{'execute': 'add-fd', " 2123 "'arguments': {'fdset-id': 1}}"); 2124 close(fd); 2125 } 2126 } 2127 2128 static void *file_offset_fdset_start_hook(QTestState *from, QTestState *to) 2129 { 2130 g_autofree char *file = g_strdup_printf("%s/%s", tmpfs, FILE_TEST_FILENAME); 2131 2132 fdset_add_fds(from, file, O_WRONLY, 1, false); 2133 fdset_add_fds(to, file, O_RDONLY, 1, false); 2134 2135 return NULL; 2136 } 2137 2138 static void test_precopy_file_offset_fdset(void) 2139 { 2140 g_autofree char *uri = g_strdup_printf("file:/dev/fdset/1,offset=%d", 2141 FILE_TEST_OFFSET); 2142 MigrateCommon args = { 2143 .connect_uri = uri, 2144 .listen_uri = "defer", 2145 .start_hook = file_offset_fdset_start_hook, 2146 }; 2147 2148 test_file_common(&args, false); 2149 } 2150 #endif 2151 2152 static void test_precopy_file_offset(void) 2153 { 2154 g_autofree char *uri = g_strdup_printf("file:%s/%s,offset=%d", tmpfs, 2155 FILE_TEST_FILENAME, 2156 FILE_TEST_OFFSET); 2157 MigrateCommon args = { 2158 .connect_uri = uri, 2159 .listen_uri = "defer", 2160 }; 2161 2162 test_file_common(&args, false); 2163 } 2164 2165 static void test_precopy_file_offset_bad(void) 2166 { 2167 /* using a value not supported by qemu_strtosz() */ 2168 g_autofree char *uri = g_strdup_printf("file:%s/%s,offset=0x20M", 2169 tmpfs, FILE_TEST_FILENAME); 2170 MigrateCommon args = { 2171 .connect_uri = uri, 2172 .listen_uri = "defer", 2173 .result = MIG_TEST_QMP_ERROR, 2174 }; 2175 2176 test_file_common(&args, false); 2177 } 2178 2179 static void *test_mode_reboot_start(QTestState *from, QTestState *to) 2180 { 2181 migrate_set_parameter_str(from, "mode", "cpr-reboot"); 2182 migrate_set_parameter_str(to, "mode", "cpr-reboot"); 2183 2184 migrate_set_capability(from, "x-ignore-shared", true); 2185 migrate_set_capability(to, "x-ignore-shared", true); 2186 2187 return NULL; 2188 } 2189 2190 static void *migrate_mapped_ram_start(QTestState *from, QTestState *to) 2191 { 2192 migrate_set_capability(from, "mapped-ram", true); 2193 migrate_set_capability(to, "mapped-ram", true); 2194 2195 return NULL; 2196 } 2197 2198 static void test_mode_reboot(void) 2199 { 2200 g_autofree char *uri = g_strdup_printf("file:%s/%s", tmpfs, 2201 FILE_TEST_FILENAME); 2202 MigrateCommon args = { 2203 .start.use_shmem = true, 2204 .connect_uri = uri, 2205 .listen_uri = "defer", 2206 .start_hook = test_mode_reboot_start 2207 }; 2208 2209 test_file_common(&args, true); 2210 } 2211 2212 static void test_precopy_file_mapped_ram_live(void) 2213 { 2214 g_autofree char *uri = g_strdup_printf("file:%s/%s", tmpfs, 2215 FILE_TEST_FILENAME); 2216 MigrateCommon args = { 2217 .connect_uri = uri, 2218 .listen_uri = "defer", 2219 .start_hook = migrate_mapped_ram_start, 2220 }; 2221 2222 test_file_common(&args, false); 2223 } 2224 2225 static void test_precopy_file_mapped_ram(void) 2226 { 2227 g_autofree char *uri = g_strdup_printf("file:%s/%s", tmpfs, 2228 FILE_TEST_FILENAME); 2229 MigrateCommon args = { 2230 .connect_uri = uri, 2231 .listen_uri = "defer", 2232 .start_hook = migrate_mapped_ram_start, 2233 }; 2234 2235 test_file_common(&args, true); 2236 } 2237 2238 static void *migrate_multifd_mapped_ram_start(QTestState *from, QTestState *to) 2239 { 2240 migrate_mapped_ram_start(from, to); 2241 2242 migrate_set_parameter_int(from, "multifd-channels", 4); 2243 migrate_set_parameter_int(to, "multifd-channels", 4); 2244 2245 migrate_set_capability(from, "multifd", true); 2246 migrate_set_capability(to, "multifd", true); 2247 2248 return NULL; 2249 } 2250 2251 static void test_multifd_file_mapped_ram_live(void) 2252 { 2253 g_autofree char *uri = g_strdup_printf("file:%s/%s", tmpfs, 2254 FILE_TEST_FILENAME); 2255 MigrateCommon args = { 2256 .connect_uri = uri, 2257 .listen_uri = "defer", 2258 .start_hook = migrate_multifd_mapped_ram_start, 2259 }; 2260 2261 test_file_common(&args, false); 2262 } 2263 2264 static void test_multifd_file_mapped_ram(void) 2265 { 2266 g_autofree char *uri = g_strdup_printf("file:%s/%s", tmpfs, 2267 FILE_TEST_FILENAME); 2268 MigrateCommon args = { 2269 .connect_uri = uri, 2270 .listen_uri = "defer", 2271 .start_hook = migrate_multifd_mapped_ram_start, 2272 }; 2273 2274 test_file_common(&args, true); 2275 } 2276 2277 static void *multifd_mapped_ram_dio_start(QTestState *from, QTestState *to) 2278 { 2279 migrate_multifd_mapped_ram_start(from, to); 2280 2281 migrate_set_parameter_bool(from, "direct-io", true); 2282 migrate_set_parameter_bool(to, "direct-io", true); 2283 2284 return NULL; 2285 } 2286 2287 static void test_multifd_file_mapped_ram_dio(void) 2288 { 2289 g_autofree char *uri = g_strdup_printf("file:%s/%s", tmpfs, 2290 FILE_TEST_FILENAME); 2291 MigrateCommon args = { 2292 .connect_uri = uri, 2293 .listen_uri = "defer", 2294 .start_hook = multifd_mapped_ram_dio_start, 2295 }; 2296 2297 if (!probe_o_direct_support(tmpfs)) { 2298 g_test_skip("Filesystem does not support O_DIRECT"); 2299 return; 2300 } 2301 2302 test_file_common(&args, true); 2303 } 2304 2305 #ifndef _WIN32 2306 static void multifd_mapped_ram_fdset_end(QTestState *from, QTestState *to, 2307 void *opaque) 2308 { 2309 QDict *resp; 2310 QList *fdsets; 2311 2312 /* 2313 * Remove the fdsets after migration, otherwise a second migration 2314 * would fail due fdset reuse. 2315 */ 2316 qtest_qmp_assert_success(from, "{'execute': 'remove-fd', " 2317 "'arguments': { 'fdset-id': 1}}"); 2318 2319 /* 2320 * Make sure no fdsets are left after migration, otherwise a 2321 * second migration would fail due fdset reuse. 2322 */ 2323 resp = qtest_qmp(from, "{'execute': 'query-fdsets', " 2324 "'arguments': {}}"); 2325 g_assert(qdict_haskey(resp, "return")); 2326 fdsets = qdict_get_qlist(resp, "return"); 2327 g_assert(fdsets && qlist_empty(fdsets)); 2328 } 2329 2330 static void *multifd_mapped_ram_fdset_dio(QTestState *from, QTestState *to) 2331 { 2332 g_autofree char *file = g_strdup_printf("%s/%s", tmpfs, FILE_TEST_FILENAME); 2333 2334 fdset_add_fds(from, file, O_WRONLY, 2, true); 2335 fdset_add_fds(to, file, O_RDONLY, 2, true); 2336 2337 migrate_multifd_mapped_ram_start(from, to); 2338 migrate_set_parameter_bool(from, "direct-io", true); 2339 migrate_set_parameter_bool(to, "direct-io", true); 2340 2341 return NULL; 2342 } 2343 2344 static void *multifd_mapped_ram_fdset(QTestState *from, QTestState *to) 2345 { 2346 g_autofree char *file = g_strdup_printf("%s/%s", tmpfs, FILE_TEST_FILENAME); 2347 2348 fdset_add_fds(from, file, O_WRONLY, 2, false); 2349 fdset_add_fds(to, file, O_RDONLY, 2, false); 2350 2351 migrate_multifd_mapped_ram_start(from, to); 2352 2353 return NULL; 2354 } 2355 2356 static void test_multifd_file_mapped_ram_fdset(void) 2357 { 2358 g_autofree char *uri = g_strdup_printf("file:/dev/fdset/1,offset=%d", 2359 FILE_TEST_OFFSET); 2360 MigrateCommon args = { 2361 .connect_uri = uri, 2362 .listen_uri = "defer", 2363 .start_hook = multifd_mapped_ram_fdset, 2364 .finish_hook = multifd_mapped_ram_fdset_end, 2365 }; 2366 2367 test_file_common(&args, true); 2368 } 2369 2370 static void test_multifd_file_mapped_ram_fdset_dio(void) 2371 { 2372 g_autofree char *uri = g_strdup_printf("file:/dev/fdset/1,offset=%d", 2373 FILE_TEST_OFFSET); 2374 MigrateCommon args = { 2375 .connect_uri = uri, 2376 .listen_uri = "defer", 2377 .start_hook = multifd_mapped_ram_fdset_dio, 2378 .finish_hook = multifd_mapped_ram_fdset_end, 2379 }; 2380 2381 if (!probe_o_direct_support(tmpfs)) { 2382 g_test_skip("Filesystem does not support O_DIRECT"); 2383 return; 2384 } 2385 2386 test_file_common(&args, true); 2387 } 2388 #endif /* !_WIN32 */ 2389 2390 static void test_precopy_tcp_plain(void) 2391 { 2392 MigrateCommon args = { 2393 .listen_uri = "tcp:127.0.0.1:0", 2394 }; 2395 2396 test_precopy_common(&args); 2397 } 2398 2399 static void *test_migrate_switchover_ack_start(QTestState *from, QTestState *to) 2400 { 2401 2402 migrate_set_capability(from, "return-path", true); 2403 migrate_set_capability(to, "return-path", true); 2404 2405 migrate_set_capability(from, "switchover-ack", true); 2406 migrate_set_capability(to, "switchover-ack", true); 2407 2408 return NULL; 2409 } 2410 2411 static void test_precopy_tcp_switchover_ack(void) 2412 { 2413 MigrateCommon args = { 2414 .listen_uri = "tcp:127.0.0.1:0", 2415 .start_hook = test_migrate_switchover_ack_start, 2416 /* 2417 * Source VM must be running in order to consider the switchover ACK 2418 * when deciding to do switchover or not. 2419 */ 2420 .live = true, 2421 }; 2422 2423 test_precopy_common(&args); 2424 } 2425 2426 #ifdef CONFIG_GNUTLS 2427 static void test_precopy_tcp_tls_psk_match(void) 2428 { 2429 MigrateCommon args = { 2430 .listen_uri = "tcp:127.0.0.1:0", 2431 .start_hook = test_migrate_tls_psk_start_match, 2432 .finish_hook = test_migrate_tls_psk_finish, 2433 }; 2434 2435 test_precopy_common(&args); 2436 } 2437 2438 static void test_precopy_tcp_tls_psk_mismatch(void) 2439 { 2440 MigrateCommon args = { 2441 .start = { 2442 .hide_stderr = true, 2443 }, 2444 .listen_uri = "tcp:127.0.0.1:0", 2445 .start_hook = test_migrate_tls_psk_start_mismatch, 2446 .finish_hook = test_migrate_tls_psk_finish, 2447 .result = MIG_TEST_FAIL, 2448 }; 2449 2450 test_precopy_common(&args); 2451 } 2452 2453 #ifdef CONFIG_TASN1 2454 static void test_precopy_tcp_tls_x509_default_host(void) 2455 { 2456 MigrateCommon args = { 2457 .listen_uri = "tcp:127.0.0.1:0", 2458 .start_hook = test_migrate_tls_x509_start_default_host, 2459 .finish_hook = test_migrate_tls_x509_finish, 2460 }; 2461 2462 test_precopy_common(&args); 2463 } 2464 2465 static void test_precopy_tcp_tls_x509_override_host(void) 2466 { 2467 MigrateCommon args = { 2468 .listen_uri = "tcp:127.0.0.1:0", 2469 .start_hook = test_migrate_tls_x509_start_override_host, 2470 .finish_hook = test_migrate_tls_x509_finish, 2471 }; 2472 2473 test_precopy_common(&args); 2474 } 2475 2476 static void test_precopy_tcp_tls_x509_mismatch_host(void) 2477 { 2478 MigrateCommon args = { 2479 .start = { 2480 .hide_stderr = true, 2481 }, 2482 .listen_uri = "tcp:127.0.0.1:0", 2483 .start_hook = test_migrate_tls_x509_start_mismatch_host, 2484 .finish_hook = test_migrate_tls_x509_finish, 2485 .result = MIG_TEST_FAIL_DEST_QUIT_ERR, 2486 }; 2487 2488 test_precopy_common(&args); 2489 } 2490 2491 static void test_precopy_tcp_tls_x509_friendly_client(void) 2492 { 2493 MigrateCommon args = { 2494 .listen_uri = "tcp:127.0.0.1:0", 2495 .start_hook = test_migrate_tls_x509_start_friendly_client, 2496 .finish_hook = test_migrate_tls_x509_finish, 2497 }; 2498 2499 test_precopy_common(&args); 2500 } 2501 2502 static void test_precopy_tcp_tls_x509_hostile_client(void) 2503 { 2504 MigrateCommon args = { 2505 .start = { 2506 .hide_stderr = true, 2507 }, 2508 .listen_uri = "tcp:127.0.0.1:0", 2509 .start_hook = test_migrate_tls_x509_start_hostile_client, 2510 .finish_hook = test_migrate_tls_x509_finish, 2511 .result = MIG_TEST_FAIL, 2512 }; 2513 2514 test_precopy_common(&args); 2515 } 2516 2517 static void test_precopy_tcp_tls_x509_allow_anon_client(void) 2518 { 2519 MigrateCommon args = { 2520 .listen_uri = "tcp:127.0.0.1:0", 2521 .start_hook = test_migrate_tls_x509_start_allow_anon_client, 2522 .finish_hook = test_migrate_tls_x509_finish, 2523 }; 2524 2525 test_precopy_common(&args); 2526 } 2527 2528 static void test_precopy_tcp_tls_x509_reject_anon_client(void) 2529 { 2530 MigrateCommon args = { 2531 .start = { 2532 .hide_stderr = true, 2533 }, 2534 .listen_uri = "tcp:127.0.0.1:0", 2535 .start_hook = test_migrate_tls_x509_start_reject_anon_client, 2536 .finish_hook = test_migrate_tls_x509_finish, 2537 .result = MIG_TEST_FAIL, 2538 }; 2539 2540 test_precopy_common(&args); 2541 } 2542 #endif /* CONFIG_TASN1 */ 2543 #endif /* CONFIG_GNUTLS */ 2544 2545 #ifndef _WIN32 2546 static void *test_migrate_fd_start_hook(QTestState *from, 2547 QTestState *to) 2548 { 2549 int ret; 2550 int pair[2]; 2551 2552 /* Create two connected sockets for migration */ 2553 ret = qemu_socketpair(PF_LOCAL, SOCK_STREAM, 0, pair); 2554 g_assert_cmpint(ret, ==, 0); 2555 2556 /* Send the 1st socket to the target */ 2557 qtest_qmp_fds_assert_success(to, &pair[0], 1, 2558 "{ 'execute': 'getfd'," 2559 " 'arguments': { 'fdname': 'fd-mig' }}"); 2560 close(pair[0]); 2561 2562 /* Start incoming migration from the 1st socket */ 2563 migrate_incoming_qmp(to, "fd:fd-mig", "{}"); 2564 2565 /* Send the 2nd socket to the target */ 2566 qtest_qmp_fds_assert_success(from, &pair[1], 1, 2567 "{ 'execute': 'getfd'," 2568 " 'arguments': { 'fdname': 'fd-mig' }}"); 2569 close(pair[1]); 2570 2571 return NULL; 2572 } 2573 2574 static void test_migrate_fd_finish_hook(QTestState *from, 2575 QTestState *to, 2576 void *opaque) 2577 { 2578 QDict *rsp; 2579 const char *error_desc; 2580 2581 /* Test closing fds */ 2582 /* We assume, that QEMU removes named fd from its list, 2583 * so this should fail */ 2584 rsp = qtest_qmp(from, "{ 'execute': 'closefd'," 2585 " 'arguments': { 'fdname': 'fd-mig' }}"); 2586 g_assert_true(qdict_haskey(rsp, "error")); 2587 error_desc = qdict_get_str(qdict_get_qdict(rsp, "error"), "desc"); 2588 g_assert_cmpstr(error_desc, ==, "File descriptor named 'fd-mig' not found"); 2589 qobject_unref(rsp); 2590 2591 rsp = qtest_qmp(to, "{ 'execute': 'closefd'," 2592 " 'arguments': { 'fdname': 'fd-mig' }}"); 2593 g_assert_true(qdict_haskey(rsp, "error")); 2594 error_desc = qdict_get_str(qdict_get_qdict(rsp, "error"), "desc"); 2595 g_assert_cmpstr(error_desc, ==, "File descriptor named 'fd-mig' not found"); 2596 qobject_unref(rsp); 2597 } 2598 2599 static void test_migrate_precopy_fd_socket(void) 2600 { 2601 MigrateCommon args = { 2602 .listen_uri = "defer", 2603 .connect_uri = "fd:fd-mig", 2604 .start_hook = test_migrate_fd_start_hook, 2605 .finish_hook = test_migrate_fd_finish_hook 2606 }; 2607 test_precopy_common(&args); 2608 } 2609 2610 static void *migrate_precopy_fd_file_start(QTestState *from, QTestState *to) 2611 { 2612 g_autofree char *file = g_strdup_printf("%s/%s", tmpfs, FILE_TEST_FILENAME); 2613 int src_flags = O_CREAT | O_RDWR; 2614 int dst_flags = O_CREAT | O_RDWR; 2615 int fds[2]; 2616 2617 fds[0] = open(file, src_flags, 0660); 2618 assert(fds[0] != -1); 2619 2620 fds[1] = open(file, dst_flags, 0660); 2621 assert(fds[1] != -1); 2622 2623 2624 qtest_qmp_fds_assert_success(to, &fds[0], 1, 2625 "{ 'execute': 'getfd'," 2626 " 'arguments': { 'fdname': 'fd-mig' }}"); 2627 2628 qtest_qmp_fds_assert_success(from, &fds[1], 1, 2629 "{ 'execute': 'getfd'," 2630 " 'arguments': { 'fdname': 'fd-mig' }}"); 2631 2632 close(fds[0]); 2633 close(fds[1]); 2634 2635 return NULL; 2636 } 2637 2638 static void test_migrate_precopy_fd_file(void) 2639 { 2640 MigrateCommon args = { 2641 .listen_uri = "defer", 2642 .connect_uri = "fd:fd-mig", 2643 .start_hook = migrate_precopy_fd_file_start, 2644 .finish_hook = test_migrate_fd_finish_hook 2645 }; 2646 test_file_common(&args, true); 2647 } 2648 #endif /* _WIN32 */ 2649 2650 static void do_test_validate_uuid(MigrateStart *args, bool should_fail) 2651 { 2652 g_autofree char *uri = g_strdup_printf("unix:%s/migsocket", tmpfs); 2653 QTestState *from, *to; 2654 2655 if (test_migrate_start(&from, &to, uri, args)) { 2656 return; 2657 } 2658 2659 /* 2660 * UUID validation is at the begin of migration. So, the main process of 2661 * migration is not interesting for us here. Thus, set huge downtime for 2662 * very fast migration. 2663 */ 2664 migrate_set_parameter_int(from, "downtime-limit", 1000000); 2665 migrate_set_capability(from, "validate-uuid", true); 2666 2667 /* Wait for the first serial output from the source */ 2668 wait_for_serial("src_serial"); 2669 2670 migrate_qmp(from, to, uri, NULL, "{}"); 2671 2672 if (should_fail) { 2673 qtest_set_expected_status(to, EXIT_FAILURE); 2674 wait_for_migration_fail(from, true); 2675 } else { 2676 wait_for_migration_complete(from); 2677 } 2678 2679 test_migrate_end(from, to, false); 2680 } 2681 2682 static void test_validate_uuid(void) 2683 { 2684 MigrateStart args = { 2685 .opts_source = "-uuid 11111111-1111-1111-1111-111111111111", 2686 .opts_target = "-uuid 11111111-1111-1111-1111-111111111111", 2687 }; 2688 2689 do_test_validate_uuid(&args, false); 2690 } 2691 2692 static void test_validate_uuid_error(void) 2693 { 2694 MigrateStart args = { 2695 .opts_source = "-uuid 11111111-1111-1111-1111-111111111111", 2696 .opts_target = "-uuid 22222222-2222-2222-2222-222222222222", 2697 .hide_stderr = true, 2698 }; 2699 2700 do_test_validate_uuid(&args, true); 2701 } 2702 2703 static void test_validate_uuid_src_not_set(void) 2704 { 2705 MigrateStart args = { 2706 .opts_target = "-uuid 22222222-2222-2222-2222-222222222222", 2707 .hide_stderr = true, 2708 }; 2709 2710 do_test_validate_uuid(&args, false); 2711 } 2712 2713 static void test_validate_uuid_dst_not_set(void) 2714 { 2715 MigrateStart args = { 2716 .opts_source = "-uuid 11111111-1111-1111-1111-111111111111", 2717 .hide_stderr = true, 2718 }; 2719 2720 do_test_validate_uuid(&args, false); 2721 } 2722 2723 static void do_test_validate_uri_channel(MigrateCommon *args) 2724 { 2725 QTestState *from, *to; 2726 2727 if (test_migrate_start(&from, &to, args->listen_uri, &args->start)) { 2728 return; 2729 } 2730 2731 /* Wait for the first serial output from the source */ 2732 wait_for_serial("src_serial"); 2733 2734 /* 2735 * 'uri' and 'channels' validation is checked even before the migration 2736 * starts. 2737 */ 2738 migrate_qmp_fail(from, args->connect_uri, args->connect_channels, "{}"); 2739 test_migrate_end(from, to, false); 2740 } 2741 2742 static void test_validate_uri_channels_both_set(void) 2743 { 2744 MigrateCommon args = { 2745 .start = { 2746 .hide_stderr = true, 2747 }, 2748 .listen_uri = "defer", 2749 .connect_uri = "tcp:127.0.0.1:0", 2750 .connect_channels = "[ { 'channel-type': 'main'," 2751 " 'addr': { 'transport': 'socket'," 2752 " 'type': 'inet'," 2753 " 'host': '127.0.0.1'," 2754 " 'port': '0' } } ]", 2755 }; 2756 2757 do_test_validate_uri_channel(&args); 2758 } 2759 2760 static void test_validate_uri_channels_none_set(void) 2761 { 2762 MigrateCommon args = { 2763 .start = { 2764 .hide_stderr = true, 2765 }, 2766 .listen_uri = "defer", 2767 }; 2768 2769 do_test_validate_uri_channel(&args); 2770 } 2771 2772 /* 2773 * The way auto_converge works, we need to do too many passes to 2774 * run this test. Auto_converge logic is only run once every 2775 * three iterations, so: 2776 * 2777 * - 3 iterations without auto_converge enabled 2778 * - 3 iterations with pct = 5 2779 * - 3 iterations with pct = 30 2780 * - 3 iterations with pct = 55 2781 * - 3 iterations with pct = 80 2782 * - 3 iterations with pct = 95 (max(95, 80 + 25)) 2783 * 2784 * To make things even worse, we need to run the initial stage at 2785 * 3MB/s so we enter autoconverge even when host is (over)loaded. 2786 */ 2787 static void test_migrate_auto_converge(void) 2788 { 2789 g_autofree char *uri = g_strdup_printf("unix:%s/migsocket", tmpfs); 2790 MigrateStart args = {}; 2791 QTestState *from, *to; 2792 int64_t percentage; 2793 2794 /* 2795 * We want the test to be stable and as fast as possible. 2796 * E.g., with 1Gb/s bandwidth migration may pass without throttling, 2797 * so we need to decrease a bandwidth. 2798 */ 2799 const int64_t init_pct = 5, inc_pct = 25, max_pct = 95; 2800 2801 if (test_migrate_start(&from, &to, uri, &args)) { 2802 return; 2803 } 2804 2805 migrate_set_capability(from, "auto-converge", true); 2806 migrate_set_parameter_int(from, "cpu-throttle-initial", init_pct); 2807 migrate_set_parameter_int(from, "cpu-throttle-increment", inc_pct); 2808 migrate_set_parameter_int(from, "max-cpu-throttle", max_pct); 2809 2810 /* 2811 * Set the initial parameters so that the migration could not converge 2812 * without throttling. 2813 */ 2814 migrate_ensure_non_converge(from); 2815 2816 /* To check remaining size after precopy */ 2817 migrate_set_capability(from, "pause-before-switchover", true); 2818 2819 /* Wait for the first serial output from the source */ 2820 wait_for_serial("src_serial"); 2821 2822 migrate_qmp(from, to, uri, NULL, "{}"); 2823 2824 /* Wait for throttling begins */ 2825 percentage = 0; 2826 do { 2827 percentage = read_migrate_property_int(from, "cpu-throttle-percentage"); 2828 if (percentage != 0) { 2829 break; 2830 } 2831 usleep(20); 2832 g_assert_false(src_state.stop_seen); 2833 } while (true); 2834 /* The first percentage of throttling should be at least init_pct */ 2835 g_assert_cmpint(percentage, >=, init_pct); 2836 /* Now, when we tested that throttling works, let it converge */ 2837 migrate_ensure_converge(from); 2838 2839 /* 2840 * Wait for pre-switchover status to check last throttle percentage 2841 * and remaining. These values will be zeroed later 2842 */ 2843 wait_for_migration_status(from, "pre-switchover", NULL); 2844 2845 /* The final percentage of throttling shouldn't be greater than max_pct */ 2846 percentage = read_migrate_property_int(from, "cpu-throttle-percentage"); 2847 g_assert_cmpint(percentage, <=, max_pct); 2848 migrate_continue(from, "pre-switchover"); 2849 2850 qtest_qmp_eventwait(to, "RESUME"); 2851 2852 wait_for_serial("dest_serial"); 2853 wait_for_migration_complete(from); 2854 2855 test_migrate_end(from, to, true); 2856 } 2857 2858 static void * 2859 test_migrate_precopy_tcp_multifd_start_common(QTestState *from, 2860 QTestState *to, 2861 const char *method) 2862 { 2863 migrate_set_parameter_int(from, "multifd-channels", 16); 2864 migrate_set_parameter_int(to, "multifd-channels", 16); 2865 2866 migrate_set_parameter_str(from, "multifd-compression", method); 2867 migrate_set_parameter_str(to, "multifd-compression", method); 2868 2869 migrate_set_capability(from, "multifd", true); 2870 migrate_set_capability(to, "multifd", true); 2871 2872 /* Start incoming migration from the 1st socket */ 2873 migrate_incoming_qmp(to, "tcp:127.0.0.1:0", "{}"); 2874 2875 return NULL; 2876 } 2877 2878 static void * 2879 test_migrate_precopy_tcp_multifd_start(QTestState *from, 2880 QTestState *to) 2881 { 2882 return test_migrate_precopy_tcp_multifd_start_common(from, to, "none"); 2883 } 2884 2885 static void * 2886 test_migrate_precopy_tcp_multifd_start_zero_page_legacy(QTestState *from, 2887 QTestState *to) 2888 { 2889 test_migrate_precopy_tcp_multifd_start_common(from, to, "none"); 2890 migrate_set_parameter_str(from, "zero-page-detection", "legacy"); 2891 return NULL; 2892 } 2893 2894 static void * 2895 test_migration_precopy_tcp_multifd_start_no_zero_page(QTestState *from, 2896 QTestState *to) 2897 { 2898 test_migrate_precopy_tcp_multifd_start_common(from, to, "none"); 2899 migrate_set_parameter_str(from, "zero-page-detection", "none"); 2900 return NULL; 2901 } 2902 2903 static void * 2904 test_migrate_precopy_tcp_multifd_zlib_start(QTestState *from, 2905 QTestState *to) 2906 { 2907 /* 2908 * Overloading this test to also check that set_parameter does not error. 2909 * This is also done in the tests for the other compression methods. 2910 */ 2911 migrate_set_parameter_int(from, "multifd-zlib-level", 2); 2912 migrate_set_parameter_int(to, "multifd-zlib-level", 2); 2913 2914 return test_migrate_precopy_tcp_multifd_start_common(from, to, "zlib"); 2915 } 2916 2917 #ifdef CONFIG_ZSTD 2918 static void * 2919 test_migrate_precopy_tcp_multifd_zstd_start(QTestState *from, 2920 QTestState *to) 2921 { 2922 migrate_set_parameter_int(from, "multifd-zstd-level", 2); 2923 migrate_set_parameter_int(to, "multifd-zstd-level", 2); 2924 2925 return test_migrate_precopy_tcp_multifd_start_common(from, to, "zstd"); 2926 } 2927 #endif /* CONFIG_ZSTD */ 2928 2929 #ifdef CONFIG_QPL 2930 static void * 2931 test_migrate_precopy_tcp_multifd_qpl_start(QTestState *from, 2932 QTestState *to) 2933 { 2934 return test_migrate_precopy_tcp_multifd_start_common(from, to, "qpl"); 2935 } 2936 #endif /* CONFIG_QPL */ 2937 #ifdef CONFIG_UADK 2938 static void * 2939 test_migrate_precopy_tcp_multifd_uadk_start(QTestState *from, 2940 QTestState *to) 2941 { 2942 return test_migrate_precopy_tcp_multifd_start_common(from, to, "uadk"); 2943 } 2944 #endif /* CONFIG_UADK */ 2945 2946 static void test_multifd_tcp_uri_none(void) 2947 { 2948 MigrateCommon args = { 2949 .listen_uri = "defer", 2950 .start_hook = test_migrate_precopy_tcp_multifd_start, 2951 /* 2952 * Multifd is more complicated than most of the features, it 2953 * directly takes guest page buffers when sending, make sure 2954 * everything will work alright even if guest page is changing. 2955 */ 2956 .live = true, 2957 }; 2958 test_precopy_common(&args); 2959 } 2960 2961 static void test_multifd_tcp_zero_page_legacy(void) 2962 { 2963 MigrateCommon args = { 2964 .listen_uri = "defer", 2965 .start_hook = test_migrate_precopy_tcp_multifd_start_zero_page_legacy, 2966 /* 2967 * Multifd is more complicated than most of the features, it 2968 * directly takes guest page buffers when sending, make sure 2969 * everything will work alright even if guest page is changing. 2970 */ 2971 .live = true, 2972 }; 2973 test_precopy_common(&args); 2974 } 2975 2976 static void test_multifd_tcp_no_zero_page(void) 2977 { 2978 MigrateCommon args = { 2979 .listen_uri = "defer", 2980 .start_hook = test_migration_precopy_tcp_multifd_start_no_zero_page, 2981 /* 2982 * Multifd is more complicated than most of the features, it 2983 * directly takes guest page buffers when sending, make sure 2984 * everything will work alright even if guest page is changing. 2985 */ 2986 .live = true, 2987 }; 2988 test_precopy_common(&args); 2989 } 2990 2991 static void test_multifd_tcp_channels_none(void) 2992 { 2993 MigrateCommon args = { 2994 .listen_uri = "defer", 2995 .start_hook = test_migrate_precopy_tcp_multifd_start, 2996 .live = true, 2997 .connect_channels = "[ { 'channel-type': 'main'," 2998 " 'addr': { 'transport': 'socket'," 2999 " 'type': 'inet'," 3000 " 'host': '127.0.0.1'," 3001 " 'port': '0' } } ]", 3002 }; 3003 test_precopy_common(&args); 3004 } 3005 3006 static void test_multifd_tcp_zlib(void) 3007 { 3008 MigrateCommon args = { 3009 .listen_uri = "defer", 3010 .start_hook = test_migrate_precopy_tcp_multifd_zlib_start, 3011 }; 3012 test_precopy_common(&args); 3013 } 3014 3015 #ifdef CONFIG_ZSTD 3016 static void test_multifd_tcp_zstd(void) 3017 { 3018 MigrateCommon args = { 3019 .listen_uri = "defer", 3020 .start_hook = test_migrate_precopy_tcp_multifd_zstd_start, 3021 }; 3022 test_precopy_common(&args); 3023 } 3024 #endif 3025 3026 #ifdef CONFIG_QPL 3027 static void test_multifd_tcp_qpl(void) 3028 { 3029 MigrateCommon args = { 3030 .listen_uri = "defer", 3031 .start_hook = test_migrate_precopy_tcp_multifd_qpl_start, 3032 }; 3033 test_precopy_common(&args); 3034 } 3035 #endif 3036 3037 #ifdef CONFIG_UADK 3038 static void test_multifd_tcp_uadk(void) 3039 { 3040 MigrateCommon args = { 3041 .listen_uri = "defer", 3042 .start_hook = test_migrate_precopy_tcp_multifd_uadk_start, 3043 }; 3044 test_precopy_common(&args); 3045 } 3046 #endif 3047 3048 #ifdef CONFIG_GNUTLS 3049 static void * 3050 test_migrate_multifd_tcp_tls_psk_start_match(QTestState *from, 3051 QTestState *to) 3052 { 3053 test_migrate_precopy_tcp_multifd_start_common(from, to, "none"); 3054 return test_migrate_tls_psk_start_match(from, to); 3055 } 3056 3057 static void * 3058 test_migrate_multifd_tcp_tls_psk_start_mismatch(QTestState *from, 3059 QTestState *to) 3060 { 3061 test_migrate_precopy_tcp_multifd_start_common(from, to, "none"); 3062 return test_migrate_tls_psk_start_mismatch(from, to); 3063 } 3064 3065 #ifdef CONFIG_TASN1 3066 static void * 3067 test_migrate_multifd_tls_x509_start_default_host(QTestState *from, 3068 QTestState *to) 3069 { 3070 test_migrate_precopy_tcp_multifd_start_common(from, to, "none"); 3071 return test_migrate_tls_x509_start_default_host(from, to); 3072 } 3073 3074 static void * 3075 test_migrate_multifd_tls_x509_start_override_host(QTestState *from, 3076 QTestState *to) 3077 { 3078 test_migrate_precopy_tcp_multifd_start_common(from, to, "none"); 3079 return test_migrate_tls_x509_start_override_host(from, to); 3080 } 3081 3082 static void * 3083 test_migrate_multifd_tls_x509_start_mismatch_host(QTestState *from, 3084 QTestState *to) 3085 { 3086 test_migrate_precopy_tcp_multifd_start_common(from, to, "none"); 3087 return test_migrate_tls_x509_start_mismatch_host(from, to); 3088 } 3089 3090 static void * 3091 test_migrate_multifd_tls_x509_start_allow_anon_client(QTestState *from, 3092 QTestState *to) 3093 { 3094 test_migrate_precopy_tcp_multifd_start_common(from, to, "none"); 3095 return test_migrate_tls_x509_start_allow_anon_client(from, to); 3096 } 3097 3098 static void * 3099 test_migrate_multifd_tls_x509_start_reject_anon_client(QTestState *from, 3100 QTestState *to) 3101 { 3102 test_migrate_precopy_tcp_multifd_start_common(from, to, "none"); 3103 return test_migrate_tls_x509_start_reject_anon_client(from, to); 3104 } 3105 #endif /* CONFIG_TASN1 */ 3106 3107 static void test_multifd_tcp_tls_psk_match(void) 3108 { 3109 MigrateCommon args = { 3110 .listen_uri = "defer", 3111 .start_hook = test_migrate_multifd_tcp_tls_psk_start_match, 3112 .finish_hook = test_migrate_tls_psk_finish, 3113 }; 3114 test_precopy_common(&args); 3115 } 3116 3117 static void test_multifd_tcp_tls_psk_mismatch(void) 3118 { 3119 MigrateCommon args = { 3120 .start = { 3121 .hide_stderr = true, 3122 }, 3123 .listen_uri = "defer", 3124 .start_hook = test_migrate_multifd_tcp_tls_psk_start_mismatch, 3125 .finish_hook = test_migrate_tls_psk_finish, 3126 .result = MIG_TEST_FAIL, 3127 }; 3128 test_precopy_common(&args); 3129 } 3130 3131 #ifdef CONFIG_TASN1 3132 static void test_multifd_tcp_tls_x509_default_host(void) 3133 { 3134 MigrateCommon args = { 3135 .listen_uri = "defer", 3136 .start_hook = test_migrate_multifd_tls_x509_start_default_host, 3137 .finish_hook = test_migrate_tls_x509_finish, 3138 }; 3139 test_precopy_common(&args); 3140 } 3141 3142 static void test_multifd_tcp_tls_x509_override_host(void) 3143 { 3144 MigrateCommon args = { 3145 .listen_uri = "defer", 3146 .start_hook = test_migrate_multifd_tls_x509_start_override_host, 3147 .finish_hook = test_migrate_tls_x509_finish, 3148 }; 3149 test_precopy_common(&args); 3150 } 3151 3152 static void test_multifd_tcp_tls_x509_mismatch_host(void) 3153 { 3154 /* 3155 * This has different behaviour to the non-multifd case. 3156 * 3157 * In non-multifd case when client aborts due to mismatched 3158 * cert host, the server has already started trying to load 3159 * migration state, and so it exits with I/O failure. 3160 * 3161 * In multifd case when client aborts due to mismatched 3162 * cert host, the server is still waiting for the other 3163 * multifd connections to arrive so hasn't started trying 3164 * to load migration state, and thus just aborts the migration 3165 * without exiting. 3166 */ 3167 MigrateCommon args = { 3168 .start = { 3169 .hide_stderr = true, 3170 }, 3171 .listen_uri = "defer", 3172 .start_hook = test_migrate_multifd_tls_x509_start_mismatch_host, 3173 .finish_hook = test_migrate_tls_x509_finish, 3174 .result = MIG_TEST_FAIL, 3175 }; 3176 test_precopy_common(&args); 3177 } 3178 3179 static void test_multifd_tcp_tls_x509_allow_anon_client(void) 3180 { 3181 MigrateCommon args = { 3182 .listen_uri = "defer", 3183 .start_hook = test_migrate_multifd_tls_x509_start_allow_anon_client, 3184 .finish_hook = test_migrate_tls_x509_finish, 3185 }; 3186 test_precopy_common(&args); 3187 } 3188 3189 static void test_multifd_tcp_tls_x509_reject_anon_client(void) 3190 { 3191 MigrateCommon args = { 3192 .start = { 3193 .hide_stderr = true, 3194 }, 3195 .listen_uri = "defer", 3196 .start_hook = test_migrate_multifd_tls_x509_start_reject_anon_client, 3197 .finish_hook = test_migrate_tls_x509_finish, 3198 .result = MIG_TEST_FAIL, 3199 }; 3200 test_precopy_common(&args); 3201 } 3202 #endif /* CONFIG_TASN1 */ 3203 #endif /* CONFIG_GNUTLS */ 3204 3205 /* 3206 * This test does: 3207 * source target 3208 * migrate_incoming 3209 * migrate 3210 * migrate_cancel 3211 * launch another target 3212 * migrate 3213 * 3214 * And see that it works 3215 */ 3216 static void test_multifd_tcp_cancel(void) 3217 { 3218 MigrateStart args = { 3219 .hide_stderr = true, 3220 }; 3221 QTestState *from, *to, *to2; 3222 3223 if (test_migrate_start(&from, &to, "defer", &args)) { 3224 return; 3225 } 3226 3227 migrate_ensure_non_converge(from); 3228 migrate_prepare_for_dirty_mem(from); 3229 3230 migrate_set_parameter_int(from, "multifd-channels", 16); 3231 migrate_set_parameter_int(to, "multifd-channels", 16); 3232 3233 migrate_set_capability(from, "multifd", true); 3234 migrate_set_capability(to, "multifd", true); 3235 3236 /* Start incoming migration from the 1st socket */ 3237 migrate_incoming_qmp(to, "tcp:127.0.0.1:0", "{}"); 3238 3239 /* Wait for the first serial output from the source */ 3240 wait_for_serial("src_serial"); 3241 3242 migrate_qmp(from, to, NULL, NULL, "{}"); 3243 3244 migrate_wait_for_dirty_mem(from, to); 3245 3246 migrate_cancel(from); 3247 3248 /* Make sure QEMU process "to" exited */ 3249 qtest_set_expected_status(to, EXIT_FAILURE); 3250 qtest_wait_qemu(to); 3251 3252 args = (MigrateStart){ 3253 .only_target = true, 3254 }; 3255 3256 if (test_migrate_start(&from, &to2, "defer", &args)) { 3257 return; 3258 } 3259 3260 migrate_set_parameter_int(to2, "multifd-channels", 16); 3261 3262 migrate_set_capability(to2, "multifd", true); 3263 3264 /* Start incoming migration from the 1st socket */ 3265 migrate_incoming_qmp(to2, "tcp:127.0.0.1:0", "{}"); 3266 3267 wait_for_migration_status(from, "cancelled", NULL); 3268 3269 migrate_ensure_non_converge(from); 3270 3271 migrate_qmp(from, to2, NULL, NULL, "{}"); 3272 3273 migrate_wait_for_dirty_mem(from, to2); 3274 3275 migrate_ensure_converge(from); 3276 3277 wait_for_stop(from, &src_state); 3278 qtest_qmp_eventwait(to2, "RESUME"); 3279 3280 wait_for_serial("dest_serial"); 3281 wait_for_migration_complete(from); 3282 test_migrate_end(from, to2, true); 3283 } 3284 3285 static void calc_dirty_rate(QTestState *who, uint64_t calc_time) 3286 { 3287 qtest_qmp_assert_success(who, 3288 "{ 'execute': 'calc-dirty-rate'," 3289 "'arguments': { " 3290 "'calc-time': %" PRIu64 "," 3291 "'mode': 'dirty-ring' }}", 3292 calc_time); 3293 } 3294 3295 static QDict *query_dirty_rate(QTestState *who) 3296 { 3297 return qtest_qmp_assert_success_ref(who, 3298 "{ 'execute': 'query-dirty-rate' }"); 3299 } 3300 3301 static void dirtylimit_set_all(QTestState *who, uint64_t dirtyrate) 3302 { 3303 qtest_qmp_assert_success(who, 3304 "{ 'execute': 'set-vcpu-dirty-limit'," 3305 "'arguments': { " 3306 "'dirty-rate': %" PRIu64 " } }", 3307 dirtyrate); 3308 } 3309 3310 static void cancel_vcpu_dirty_limit(QTestState *who) 3311 { 3312 qtest_qmp_assert_success(who, 3313 "{ 'execute': 'cancel-vcpu-dirty-limit' }"); 3314 } 3315 3316 static QDict *query_vcpu_dirty_limit(QTestState *who) 3317 { 3318 QDict *rsp; 3319 3320 rsp = qtest_qmp(who, "{ 'execute': 'query-vcpu-dirty-limit' }"); 3321 g_assert(!qdict_haskey(rsp, "error")); 3322 g_assert(qdict_haskey(rsp, "return")); 3323 3324 return rsp; 3325 } 3326 3327 static bool calc_dirtyrate_ready(QTestState *who) 3328 { 3329 QDict *rsp_return; 3330 gchar *status; 3331 3332 rsp_return = query_dirty_rate(who); 3333 g_assert(rsp_return); 3334 3335 status = g_strdup(qdict_get_str(rsp_return, "status")); 3336 g_assert(status); 3337 3338 return g_strcmp0(status, "measuring"); 3339 } 3340 3341 static void wait_for_calc_dirtyrate_complete(QTestState *who, 3342 int64_t time_s) 3343 { 3344 int max_try_count = 10000; 3345 usleep(time_s * 1000000); 3346 3347 while (!calc_dirtyrate_ready(who) && max_try_count--) { 3348 usleep(1000); 3349 } 3350 3351 /* 3352 * Set the timeout with 10 s(max_try_count * 1000us), 3353 * if dirtyrate measurement not complete, fail test. 3354 */ 3355 g_assert_cmpint(max_try_count, !=, 0); 3356 } 3357 3358 static int64_t get_dirty_rate(QTestState *who) 3359 { 3360 QDict *rsp_return; 3361 gchar *status; 3362 QList *rates; 3363 const QListEntry *entry; 3364 QDict *rate; 3365 int64_t dirtyrate; 3366 3367 rsp_return = query_dirty_rate(who); 3368 g_assert(rsp_return); 3369 3370 status = g_strdup(qdict_get_str(rsp_return, "status")); 3371 g_assert(status); 3372 g_assert_cmpstr(status, ==, "measured"); 3373 3374 rates = qdict_get_qlist(rsp_return, "vcpu-dirty-rate"); 3375 g_assert(rates && !qlist_empty(rates)); 3376 3377 entry = qlist_first(rates); 3378 g_assert(entry); 3379 3380 rate = qobject_to(QDict, qlist_entry_obj(entry)); 3381 g_assert(rate); 3382 3383 dirtyrate = qdict_get_try_int(rate, "dirty-rate", -1); 3384 3385 qobject_unref(rsp_return); 3386 return dirtyrate; 3387 } 3388 3389 static int64_t get_limit_rate(QTestState *who) 3390 { 3391 QDict *rsp_return; 3392 QList *rates; 3393 const QListEntry *entry; 3394 QDict *rate; 3395 int64_t dirtyrate; 3396 3397 rsp_return = query_vcpu_dirty_limit(who); 3398 g_assert(rsp_return); 3399 3400 rates = qdict_get_qlist(rsp_return, "return"); 3401 g_assert(rates && !qlist_empty(rates)); 3402 3403 entry = qlist_first(rates); 3404 g_assert(entry); 3405 3406 rate = qobject_to(QDict, qlist_entry_obj(entry)); 3407 g_assert(rate); 3408 3409 dirtyrate = qdict_get_try_int(rate, "limit-rate", -1); 3410 3411 qobject_unref(rsp_return); 3412 return dirtyrate; 3413 } 3414 3415 static QTestState *dirtylimit_start_vm(void) 3416 { 3417 QTestState *vm = NULL; 3418 g_autofree gchar *cmd = NULL; 3419 3420 bootfile_create(tmpfs, false); 3421 cmd = g_strdup_printf("-accel kvm,dirty-ring-size=4096 " 3422 "-name dirtylimit-test,debug-threads=on " 3423 "-m 150M -smp 1 " 3424 "-serial file:%s/vm_serial " 3425 "-drive file=%s,format=raw ", 3426 tmpfs, bootpath); 3427 3428 vm = qtest_init(cmd); 3429 return vm; 3430 } 3431 3432 static void dirtylimit_stop_vm(QTestState *vm) 3433 { 3434 qtest_quit(vm); 3435 cleanup("vm_serial"); 3436 } 3437 3438 static void test_vcpu_dirty_limit(void) 3439 { 3440 QTestState *vm; 3441 int64_t origin_rate; 3442 int64_t quota_rate; 3443 int64_t rate ; 3444 int max_try_count = 20; 3445 int hit = 0; 3446 3447 /* Start vm for vcpu dirtylimit test */ 3448 vm = dirtylimit_start_vm(); 3449 3450 /* Wait for the first serial output from the vm*/ 3451 wait_for_serial("vm_serial"); 3452 3453 /* Do dirtyrate measurement with calc time equals 1s */ 3454 calc_dirty_rate(vm, 1); 3455 3456 /* Sleep calc time and wait for calc dirtyrate complete */ 3457 wait_for_calc_dirtyrate_complete(vm, 1); 3458 3459 /* Query original dirty page rate */ 3460 origin_rate = get_dirty_rate(vm); 3461 3462 /* VM booted from bootsect should dirty memory steadily */ 3463 assert(origin_rate != 0); 3464 3465 /* Setup quota dirty page rate at half of origin */ 3466 quota_rate = origin_rate / 2; 3467 3468 /* Set dirtylimit */ 3469 dirtylimit_set_all(vm, quota_rate); 3470 3471 /* 3472 * Check if set-vcpu-dirty-limit and query-vcpu-dirty-limit 3473 * works literally 3474 */ 3475 g_assert_cmpint(quota_rate, ==, get_limit_rate(vm)); 3476 3477 /* Sleep a bit to check if it take effect */ 3478 usleep(2000000); 3479 3480 /* 3481 * Check if dirtylimit take effect realistically, set the 3482 * timeout with 20 s(max_try_count * 1s), if dirtylimit 3483 * doesn't take effect, fail test. 3484 */ 3485 while (--max_try_count) { 3486 calc_dirty_rate(vm, 1); 3487 wait_for_calc_dirtyrate_complete(vm, 1); 3488 rate = get_dirty_rate(vm); 3489 3490 /* 3491 * Assume hitting if current rate is less 3492 * than quota rate (within accepting error) 3493 */ 3494 if (rate < (quota_rate + DIRTYLIMIT_TOLERANCE_RANGE)) { 3495 hit = 1; 3496 break; 3497 } 3498 } 3499 3500 g_assert_cmpint(hit, ==, 1); 3501 3502 hit = 0; 3503 max_try_count = 20; 3504 3505 /* Check if dirtylimit cancellation take effect */ 3506 cancel_vcpu_dirty_limit(vm); 3507 while (--max_try_count) { 3508 calc_dirty_rate(vm, 1); 3509 wait_for_calc_dirtyrate_complete(vm, 1); 3510 rate = get_dirty_rate(vm); 3511 3512 /* 3513 * Assume dirtylimit be canceled if current rate is 3514 * greater than quota rate (within accepting error) 3515 */ 3516 if (rate > (quota_rate + DIRTYLIMIT_TOLERANCE_RANGE)) { 3517 hit = 1; 3518 break; 3519 } 3520 } 3521 3522 g_assert_cmpint(hit, ==, 1); 3523 dirtylimit_stop_vm(vm); 3524 } 3525 3526 static void migrate_dirty_limit_wait_showup(QTestState *from, 3527 const int64_t period, 3528 const int64_t value) 3529 { 3530 /* Enable dirty limit capability */ 3531 migrate_set_capability(from, "dirty-limit", true); 3532 3533 /* Set dirty limit parameters */ 3534 migrate_set_parameter_int(from, "x-vcpu-dirty-limit-period", period); 3535 migrate_set_parameter_int(from, "vcpu-dirty-limit", value); 3536 3537 /* Make sure migrate can't converge */ 3538 migrate_ensure_non_converge(from); 3539 3540 /* To check limit rate after precopy */ 3541 migrate_set_capability(from, "pause-before-switchover", true); 3542 3543 /* Wait for the serial output from the source */ 3544 wait_for_serial("src_serial"); 3545 } 3546 3547 /* 3548 * This test does: 3549 * source destination 3550 * start vm 3551 * start incoming vm 3552 * migrate 3553 * wait dirty limit to begin 3554 * cancel migrate 3555 * cancellation check 3556 * restart incoming vm 3557 * migrate 3558 * wait dirty limit to begin 3559 * wait pre-switchover event 3560 * convergence condition check 3561 * 3562 * And see if dirty limit migration works correctly. 3563 * This test case involves many passes, so it runs in slow mode only. 3564 */ 3565 static void test_migrate_dirty_limit(void) 3566 { 3567 g_autofree char *uri = g_strdup_printf("unix:%s/migsocket", tmpfs); 3568 QTestState *from, *to; 3569 int64_t remaining; 3570 uint64_t throttle_us_per_full; 3571 /* 3572 * We want the test to be stable and as fast as possible. 3573 * E.g., with 1Gb/s bandwidth migration may pass without dirty limit, 3574 * so we need to decrease a bandwidth. 3575 */ 3576 const int64_t dirtylimit_period = 1000, dirtylimit_value = 50; 3577 const int64_t max_bandwidth = 400000000; /* ~400Mb/s */ 3578 const int64_t downtime_limit = 250; /* 250ms */ 3579 /* 3580 * We migrate through unix-socket (> 500Mb/s). 3581 * Thus, expected migration speed ~= bandwidth limit (< 500Mb/s). 3582 * So, we can predict expected_threshold 3583 */ 3584 const int64_t expected_threshold = max_bandwidth * downtime_limit / 1000; 3585 int max_try_count = 10; 3586 MigrateCommon args = { 3587 .start = { 3588 .hide_stderr = true, 3589 .use_dirty_ring = true, 3590 }, 3591 .listen_uri = uri, 3592 .connect_uri = uri, 3593 }; 3594 3595 /* Start src, dst vm */ 3596 if (test_migrate_start(&from, &to, args.listen_uri, &args.start)) { 3597 return; 3598 } 3599 3600 /* Prepare for dirty limit migration and wait src vm show up */ 3601 migrate_dirty_limit_wait_showup(from, dirtylimit_period, dirtylimit_value); 3602 3603 /* Start migrate */ 3604 migrate_qmp(from, to, args.connect_uri, NULL, "{}"); 3605 3606 /* Wait for dirty limit throttle begin */ 3607 throttle_us_per_full = 0; 3608 while (throttle_us_per_full == 0) { 3609 throttle_us_per_full = 3610 read_migrate_property_int(from, "dirty-limit-throttle-time-per-round"); 3611 usleep(100); 3612 g_assert_false(src_state.stop_seen); 3613 } 3614 3615 /* Now cancel migrate and wait for dirty limit throttle switch off */ 3616 migrate_cancel(from); 3617 wait_for_migration_status(from, "cancelled", NULL); 3618 3619 /* Check if dirty limit throttle switched off, set timeout 1ms */ 3620 do { 3621 throttle_us_per_full = 3622 read_migrate_property_int(from, "dirty-limit-throttle-time-per-round"); 3623 usleep(100); 3624 g_assert_false(src_state.stop_seen); 3625 } while (throttle_us_per_full != 0 && --max_try_count); 3626 3627 /* Assert dirty limit is not in service */ 3628 g_assert_cmpint(throttle_us_per_full, ==, 0); 3629 3630 args = (MigrateCommon) { 3631 .start = { 3632 .only_target = true, 3633 .use_dirty_ring = true, 3634 }, 3635 .listen_uri = uri, 3636 .connect_uri = uri, 3637 }; 3638 3639 /* Restart dst vm, src vm already show up so we needn't wait anymore */ 3640 if (test_migrate_start(&from, &to, args.listen_uri, &args.start)) { 3641 return; 3642 } 3643 3644 /* Start migrate */ 3645 migrate_qmp(from, to, args.connect_uri, NULL, "{}"); 3646 3647 /* Wait for dirty limit throttle begin */ 3648 throttle_us_per_full = 0; 3649 while (throttle_us_per_full == 0) { 3650 throttle_us_per_full = 3651 read_migrate_property_int(from, "dirty-limit-throttle-time-per-round"); 3652 usleep(100); 3653 g_assert_false(src_state.stop_seen); 3654 } 3655 3656 /* 3657 * The dirty limit rate should equals the return value of 3658 * query-vcpu-dirty-limit if dirty limit cap set 3659 */ 3660 g_assert_cmpint(dirtylimit_value, ==, get_limit_rate(from)); 3661 3662 /* Now, we have tested if dirty limit works, let it converge */ 3663 migrate_set_parameter_int(from, "downtime-limit", downtime_limit); 3664 migrate_set_parameter_int(from, "max-bandwidth", max_bandwidth); 3665 3666 /* 3667 * Wait for pre-switchover status to check if migration 3668 * satisfy the convergence condition 3669 */ 3670 wait_for_migration_status(from, "pre-switchover", NULL); 3671 3672 remaining = read_ram_property_int(from, "remaining"); 3673 g_assert_cmpint(remaining, <, 3674 (expected_threshold + expected_threshold / 100)); 3675 3676 migrate_continue(from, "pre-switchover"); 3677 3678 qtest_qmp_eventwait(to, "RESUME"); 3679 3680 wait_for_serial("dest_serial"); 3681 wait_for_migration_complete(from); 3682 3683 test_migrate_end(from, to, true); 3684 } 3685 3686 static bool kvm_dirty_ring_supported(void) 3687 { 3688 #if defined(__linux__) && defined(HOST_X86_64) 3689 int ret, kvm_fd = open("/dev/kvm", O_RDONLY); 3690 3691 if (kvm_fd < 0) { 3692 return false; 3693 } 3694 3695 ret = ioctl(kvm_fd, KVM_CHECK_EXTENSION, KVM_CAP_DIRTY_LOG_RING); 3696 close(kvm_fd); 3697 3698 /* We test with 4096 slots */ 3699 if (ret < 4096) { 3700 return false; 3701 } 3702 3703 return true; 3704 #else 3705 return false; 3706 #endif 3707 } 3708 3709 int main(int argc, char **argv) 3710 { 3711 bool has_kvm, has_tcg; 3712 bool has_uffd, is_x86; 3713 const char *arch; 3714 g_autoptr(GError) err = NULL; 3715 const char *qemu_src = getenv(QEMU_ENV_SRC); 3716 const char *qemu_dst = getenv(QEMU_ENV_DST); 3717 int ret; 3718 3719 g_test_init(&argc, &argv, NULL); 3720 3721 /* 3722 * The default QTEST_QEMU_BINARY must always be provided because 3723 * that is what helpers use to query the accel type and 3724 * architecture. 3725 */ 3726 if (qemu_src && qemu_dst) { 3727 g_test_message("Only one of %s, %s is allowed", 3728 QEMU_ENV_SRC, QEMU_ENV_DST); 3729 exit(1); 3730 } 3731 3732 has_kvm = qtest_has_accel("kvm"); 3733 has_tcg = qtest_has_accel("tcg"); 3734 3735 if (!has_tcg && !has_kvm) { 3736 g_test_skip("No KVM or TCG accelerator available"); 3737 return 0; 3738 } 3739 3740 has_uffd = ufd_version_check(); 3741 arch = qtest_get_arch(); 3742 is_x86 = !strcmp(arch, "i386") || !strcmp(arch, "x86_64"); 3743 3744 tmpfs = g_dir_make_tmp("migration-test-XXXXXX", &err); 3745 if (!tmpfs) { 3746 g_test_message("Can't create temporary directory in %s: %s", 3747 g_get_tmp_dir(), err->message); 3748 } 3749 g_assert(tmpfs); 3750 3751 module_call_init(MODULE_INIT_QOM); 3752 3753 migration_test_add("/migration/bad_dest", test_baddest); 3754 #ifndef _WIN32 3755 migration_test_add("/migration/analyze-script", test_analyze_script); 3756 migration_test_add("/migration/vmstate-checker-script", 3757 test_vmstate_checker_script); 3758 #endif 3759 3760 /* 3761 * On s390x with TCG, migration is observed to hang due to the 'pending' 3762 * state of the flic interrupt controller not being migrated or 3763 * reconstructed post-migration. Disable it until the problem is resolved. 3764 */ 3765 if (g_str_equal(arch, "s390x") && !has_kvm) { 3766 g_test_message("Skipping tests: s390x host with KVM is required"); 3767 goto test_add_done; 3768 } 3769 3770 if (is_x86) { 3771 migration_test_add("/migration/precopy/unix/suspend/live", 3772 test_precopy_unix_suspend_live); 3773 migration_test_add("/migration/precopy/unix/suspend/notlive", 3774 test_precopy_unix_suspend_notlive); 3775 } 3776 3777 if (has_uffd) { 3778 migration_test_add("/migration/postcopy/plain", test_postcopy); 3779 migration_test_add("/migration/postcopy/recovery/plain", 3780 test_postcopy_recovery); 3781 migration_test_add("/migration/postcopy/preempt/plain", 3782 test_postcopy_preempt); 3783 migration_test_add("/migration/postcopy/preempt/recovery/plain", 3784 test_postcopy_preempt_recovery); 3785 #ifndef _WIN32 3786 migration_test_add("/migration/postcopy/recovery/double-failures", 3787 test_postcopy_recovery_double_fail); 3788 #endif /* _WIN32 */ 3789 if (is_x86) { 3790 migration_test_add("/migration/postcopy/suspend", 3791 test_postcopy_suspend); 3792 } 3793 } 3794 3795 migration_test_add("/migration/precopy/unix/plain", 3796 test_precopy_unix_plain); 3797 migration_test_add("/migration/precopy/unix/xbzrle", 3798 test_precopy_unix_xbzrle); 3799 migration_test_add("/migration/precopy/file", 3800 test_precopy_file); 3801 migration_test_add("/migration/precopy/file/offset", 3802 test_precopy_file_offset); 3803 #ifndef _WIN32 3804 migration_test_add("/migration/precopy/file/offset/fdset", 3805 test_precopy_file_offset_fdset); 3806 #endif 3807 migration_test_add("/migration/precopy/file/offset/bad", 3808 test_precopy_file_offset_bad); 3809 3810 /* 3811 * Our CI system has problems with shared memory. 3812 * Don't run this test until we find a workaround. 3813 */ 3814 if (getenv("QEMU_TEST_FLAKY_TESTS")) { 3815 migration_test_add("/migration/mode/reboot", test_mode_reboot); 3816 } 3817 3818 migration_test_add("/migration/precopy/file/mapped-ram", 3819 test_precopy_file_mapped_ram); 3820 migration_test_add("/migration/precopy/file/mapped-ram/live", 3821 test_precopy_file_mapped_ram_live); 3822 3823 migration_test_add("/migration/multifd/file/mapped-ram", 3824 test_multifd_file_mapped_ram); 3825 migration_test_add("/migration/multifd/file/mapped-ram/live", 3826 test_multifd_file_mapped_ram_live); 3827 3828 migration_test_add("/migration/multifd/file/mapped-ram/dio", 3829 test_multifd_file_mapped_ram_dio); 3830 3831 #ifndef _WIN32 3832 migration_test_add("/migration/multifd/file/mapped-ram/fdset", 3833 test_multifd_file_mapped_ram_fdset); 3834 migration_test_add("/migration/multifd/file/mapped-ram/fdset/dio", 3835 test_multifd_file_mapped_ram_fdset_dio); 3836 #endif 3837 3838 #ifdef CONFIG_GNUTLS 3839 migration_test_add("/migration/precopy/unix/tls/psk", 3840 test_precopy_unix_tls_psk); 3841 3842 if (has_uffd) { 3843 /* 3844 * NOTE: psk test is enough for postcopy, as other types of TLS 3845 * channels are tested under precopy. Here what we want to test is the 3846 * general postcopy path that has TLS channel enabled. 3847 */ 3848 migration_test_add("/migration/postcopy/tls/psk", 3849 test_postcopy_tls_psk); 3850 migration_test_add("/migration/postcopy/recovery/tls/psk", 3851 test_postcopy_recovery_tls_psk); 3852 migration_test_add("/migration/postcopy/preempt/tls/psk", 3853 test_postcopy_preempt_tls_psk); 3854 migration_test_add("/migration/postcopy/preempt/recovery/tls/psk", 3855 test_postcopy_preempt_all); 3856 } 3857 #ifdef CONFIG_TASN1 3858 migration_test_add("/migration/precopy/unix/tls/x509/default-host", 3859 test_precopy_unix_tls_x509_default_host); 3860 migration_test_add("/migration/precopy/unix/tls/x509/override-host", 3861 test_precopy_unix_tls_x509_override_host); 3862 #endif /* CONFIG_TASN1 */ 3863 #endif /* CONFIG_GNUTLS */ 3864 3865 migration_test_add("/migration/precopy/tcp/plain", test_precopy_tcp_plain); 3866 3867 migration_test_add("/migration/precopy/tcp/plain/switchover-ack", 3868 test_precopy_tcp_switchover_ack); 3869 3870 #ifdef CONFIG_GNUTLS 3871 migration_test_add("/migration/precopy/tcp/tls/psk/match", 3872 test_precopy_tcp_tls_psk_match); 3873 migration_test_add("/migration/precopy/tcp/tls/psk/mismatch", 3874 test_precopy_tcp_tls_psk_mismatch); 3875 #ifdef CONFIG_TASN1 3876 migration_test_add("/migration/precopy/tcp/tls/x509/default-host", 3877 test_precopy_tcp_tls_x509_default_host); 3878 migration_test_add("/migration/precopy/tcp/tls/x509/override-host", 3879 test_precopy_tcp_tls_x509_override_host); 3880 migration_test_add("/migration/precopy/tcp/tls/x509/mismatch-host", 3881 test_precopy_tcp_tls_x509_mismatch_host); 3882 migration_test_add("/migration/precopy/tcp/tls/x509/friendly-client", 3883 test_precopy_tcp_tls_x509_friendly_client); 3884 migration_test_add("/migration/precopy/tcp/tls/x509/hostile-client", 3885 test_precopy_tcp_tls_x509_hostile_client); 3886 migration_test_add("/migration/precopy/tcp/tls/x509/allow-anon-client", 3887 test_precopy_tcp_tls_x509_allow_anon_client); 3888 migration_test_add("/migration/precopy/tcp/tls/x509/reject-anon-client", 3889 test_precopy_tcp_tls_x509_reject_anon_client); 3890 #endif /* CONFIG_TASN1 */ 3891 #endif /* CONFIG_GNUTLS */ 3892 3893 /* migration_test_add("/migration/ignore_shared", test_ignore_shared); */ 3894 #ifndef _WIN32 3895 migration_test_add("/migration/precopy/fd/tcp", 3896 test_migrate_precopy_fd_socket); 3897 migration_test_add("/migration/precopy/fd/file", 3898 test_migrate_precopy_fd_file); 3899 #endif 3900 migration_test_add("/migration/validate_uuid", test_validate_uuid); 3901 migration_test_add("/migration/validate_uuid_error", 3902 test_validate_uuid_error); 3903 migration_test_add("/migration/validate_uuid_src_not_set", 3904 test_validate_uuid_src_not_set); 3905 migration_test_add("/migration/validate_uuid_dst_not_set", 3906 test_validate_uuid_dst_not_set); 3907 migration_test_add("/migration/validate_uri/channels/both_set", 3908 test_validate_uri_channels_both_set); 3909 migration_test_add("/migration/validate_uri/channels/none_set", 3910 test_validate_uri_channels_none_set); 3911 /* 3912 * See explanation why this test is slow on function definition 3913 */ 3914 if (g_test_slow()) { 3915 migration_test_add("/migration/auto_converge", 3916 test_migrate_auto_converge); 3917 if (g_str_equal(arch, "x86_64") && 3918 has_kvm && kvm_dirty_ring_supported()) { 3919 migration_test_add("/migration/dirty_limit", 3920 test_migrate_dirty_limit); 3921 } 3922 } 3923 migration_test_add("/migration/multifd/tcp/uri/plain/none", 3924 test_multifd_tcp_uri_none); 3925 migration_test_add("/migration/multifd/tcp/channels/plain/none", 3926 test_multifd_tcp_channels_none); 3927 migration_test_add("/migration/multifd/tcp/plain/zero-page/legacy", 3928 test_multifd_tcp_zero_page_legacy); 3929 migration_test_add("/migration/multifd/tcp/plain/zero-page/none", 3930 test_multifd_tcp_no_zero_page); 3931 migration_test_add("/migration/multifd/tcp/plain/cancel", 3932 test_multifd_tcp_cancel); 3933 migration_test_add("/migration/multifd/tcp/plain/zlib", 3934 test_multifd_tcp_zlib); 3935 #ifdef CONFIG_ZSTD 3936 migration_test_add("/migration/multifd/tcp/plain/zstd", 3937 test_multifd_tcp_zstd); 3938 #endif 3939 #ifdef CONFIG_QPL 3940 migration_test_add("/migration/multifd/tcp/plain/qpl", 3941 test_multifd_tcp_qpl); 3942 #endif 3943 #ifdef CONFIG_UADK 3944 migration_test_add("/migration/multifd/tcp/plain/uadk", 3945 test_multifd_tcp_uadk); 3946 #endif 3947 #ifdef CONFIG_GNUTLS 3948 migration_test_add("/migration/multifd/tcp/tls/psk/match", 3949 test_multifd_tcp_tls_psk_match); 3950 migration_test_add("/migration/multifd/tcp/tls/psk/mismatch", 3951 test_multifd_tcp_tls_psk_mismatch); 3952 #ifdef CONFIG_TASN1 3953 migration_test_add("/migration/multifd/tcp/tls/x509/default-host", 3954 test_multifd_tcp_tls_x509_default_host); 3955 migration_test_add("/migration/multifd/tcp/tls/x509/override-host", 3956 test_multifd_tcp_tls_x509_override_host); 3957 migration_test_add("/migration/multifd/tcp/tls/x509/mismatch-host", 3958 test_multifd_tcp_tls_x509_mismatch_host); 3959 migration_test_add("/migration/multifd/tcp/tls/x509/allow-anon-client", 3960 test_multifd_tcp_tls_x509_allow_anon_client); 3961 migration_test_add("/migration/multifd/tcp/tls/x509/reject-anon-client", 3962 test_multifd_tcp_tls_x509_reject_anon_client); 3963 #endif /* CONFIG_TASN1 */ 3964 #endif /* CONFIG_GNUTLS */ 3965 3966 if (g_str_equal(arch, "x86_64") && has_kvm && kvm_dirty_ring_supported()) { 3967 migration_test_add("/migration/dirty_ring", 3968 test_precopy_unix_dirty_ring); 3969 migration_test_add("/migration/vcpu_dirty_limit", 3970 test_vcpu_dirty_limit); 3971 } 3972 3973 test_add_done: 3974 3975 ret = g_test_run(); 3976 3977 g_assert_cmpint(ret, ==, 0); 3978 3979 bootfile_delete(); 3980 ret = rmdir(tmpfs); 3981 if (ret != 0) { 3982 g_test_message("unable to rmdir: path (%s): %s", 3983 tmpfs, strerror(errno)); 3984 } 3985 g_free(tmpfs); 3986 3987 return ret; 3988 } 3989