17fe55c3cSAndreas Färber /* 2*152e0393SThomas Huth * QTest testcase for CPU plugging 37fe55c3cSAndreas Färber * 47fe55c3cSAndreas Färber * Copyright (c) 2015 SUSE Linux GmbH 57fe55c3cSAndreas Färber * 67fe55c3cSAndreas Färber * This work is licensed under the terms of the GNU GPL, version 2 or later. 77fe55c3cSAndreas Färber * See the COPYING file in the top-level directory. 87fe55c3cSAndreas Färber */ 97fe55c3cSAndreas Färber 10681c28a3SPeter Maydell #include "qemu/osdep.h" 117fe55c3cSAndreas Färber 127fe55c3cSAndreas Färber #include "qemu-common.h" 137fe55c3cSAndreas Färber #include "libqtest.h" 147fe55c3cSAndreas Färber #include "qapi/qmp/types.h" 157fe55c3cSAndreas Färber 16*152e0393SThomas Huth struct PlugTestData { 1734e46f60SMarc-André Lureau char *machine; 187fe55c3cSAndreas Färber const char *cpu_model; 197fe55c3cSAndreas Färber unsigned sockets; 207fe55c3cSAndreas Färber unsigned cores; 217fe55c3cSAndreas Färber unsigned threads; 227fe55c3cSAndreas Färber unsigned maxcpus; 237fe55c3cSAndreas Färber }; 24*152e0393SThomas Huth typedef struct PlugTestData PlugTestData; 257fe55c3cSAndreas Färber 26*152e0393SThomas Huth static void test_plug_with_cpu_add(gconstpointer data) 277fe55c3cSAndreas Färber { 28*152e0393SThomas Huth const PlugTestData *s = data; 297fe55c3cSAndreas Färber char *args; 307fe55c3cSAndreas Färber QDict *response; 317fe55c3cSAndreas Färber unsigned int i; 327fe55c3cSAndreas Färber 337fe55c3cSAndreas Färber args = g_strdup_printf("-machine %s -cpu %s " 347fe55c3cSAndreas Färber "-smp sockets=%u,cores=%u,threads=%u,maxcpus=%u", 357fe55c3cSAndreas Färber s->machine, s->cpu_model, 367fe55c3cSAndreas Färber s->sockets, s->cores, s->threads, s->maxcpus); 377fe55c3cSAndreas Färber qtest_start(args); 387fe55c3cSAndreas Färber 397fe55c3cSAndreas Färber for (i = s->sockets * s->cores * s->threads; i < s->maxcpus; i++) { 407fe55c3cSAndreas Färber response = qmp("{ 'execute': 'cpu-add'," 417fe55c3cSAndreas Färber " 'arguments': { 'id': %d } }", i); 427fe55c3cSAndreas Färber g_assert(response); 437fe55c3cSAndreas Färber g_assert(!qdict_haskey(response, "error")); 447fe55c3cSAndreas Färber QDECREF(response); 457fe55c3cSAndreas Färber } 467fe55c3cSAndreas Färber 477fe55c3cSAndreas Färber qtest_end(); 487fe55c3cSAndreas Färber g_free(args); 497fe55c3cSAndreas Färber } 507fe55c3cSAndreas Färber 51*152e0393SThomas Huth static void test_plug_without_cpu_add(gconstpointer data) 527fe55c3cSAndreas Färber { 53*152e0393SThomas Huth const PlugTestData *s = data; 547fe55c3cSAndreas Färber char *args; 557fe55c3cSAndreas Färber QDict *response; 567fe55c3cSAndreas Färber 577fe55c3cSAndreas Färber args = g_strdup_printf("-machine %s -cpu %s " 587fe55c3cSAndreas Färber "-smp sockets=%u,cores=%u,threads=%u,maxcpus=%u", 597fe55c3cSAndreas Färber s->machine, s->cpu_model, 607fe55c3cSAndreas Färber s->sockets, s->cores, s->threads, s->maxcpus); 617fe55c3cSAndreas Färber qtest_start(args); 627fe55c3cSAndreas Färber 637fe55c3cSAndreas Färber response = qmp("{ 'execute': 'cpu-add'," 647fe55c3cSAndreas Färber " 'arguments': { 'id': %d } }", 657fe55c3cSAndreas Färber s->sockets * s->cores * s->threads); 667fe55c3cSAndreas Färber g_assert(response); 677fe55c3cSAndreas Färber g_assert(qdict_haskey(response, "error")); 687fe55c3cSAndreas Färber QDECREF(response); 697fe55c3cSAndreas Färber 707fe55c3cSAndreas Färber qtest_end(); 717fe55c3cSAndreas Färber g_free(args); 727fe55c3cSAndreas Färber } 737fe55c3cSAndreas Färber 7434e46f60SMarc-André Lureau static void test_data_free(gpointer data) 7534e46f60SMarc-André Lureau { 76*152e0393SThomas Huth PlugTestData *pc = data; 7734e46f60SMarc-André Lureau 7834e46f60SMarc-André Lureau g_free(pc->machine); 7934e46f60SMarc-André Lureau g_free(pc); 8034e46f60SMarc-André Lureau } 8134e46f60SMarc-André Lureau 8202ef6e87SThomas Huth static void add_pc_test_case(const char *mname) 837fe55c3cSAndreas Färber { 8434e46f60SMarc-André Lureau char *path; 85*152e0393SThomas Huth PlugTestData *data; 867fe55c3cSAndreas Färber 877fe55c3cSAndreas Färber if (!g_str_has_prefix(mname, "pc-")) { 8802ef6e87SThomas Huth return; 897fe55c3cSAndreas Färber } 90*152e0393SThomas Huth data = g_new(PlugTestData, 1); 9134e46f60SMarc-André Lureau data->machine = g_strdup(mname); 927fe55c3cSAndreas Färber data->cpu_model = "Haswell"; /* 1.3+ theoretically */ 937fe55c3cSAndreas Färber data->sockets = 1; 947fe55c3cSAndreas Färber data->cores = 3; 957fe55c3cSAndreas Färber data->threads = 2; 967fe55c3cSAndreas Färber data->maxcpus = data->sockets * data->cores * data->threads * 2; 977fe55c3cSAndreas Färber if (g_str_has_suffix(mname, "-1.4") || 987fe55c3cSAndreas Färber (strcmp(mname, "pc-1.3") == 0) || 997fe55c3cSAndreas Färber (strcmp(mname, "pc-1.2") == 0) || 1007fe55c3cSAndreas Färber (strcmp(mname, "pc-1.1") == 0) || 1017fe55c3cSAndreas Färber (strcmp(mname, "pc-1.0") == 0) || 1027fe55c3cSAndreas Färber (strcmp(mname, "pc-0.15") == 0) || 1037fe55c3cSAndreas Färber (strcmp(mname, "pc-0.14") == 0) || 1047fe55c3cSAndreas Färber (strcmp(mname, "pc-0.13") == 0) || 1057fe55c3cSAndreas Färber (strcmp(mname, "pc-0.12") == 0) || 1067fe55c3cSAndreas Färber (strcmp(mname, "pc-0.11") == 0) || 1077fe55c3cSAndreas Färber (strcmp(mname, "pc-0.10") == 0)) { 10853f77e45SAndreas Färber path = g_strdup_printf("cpu/%s/init/%ux%ux%u&maxcpus=%u", 10953f77e45SAndreas Färber mname, data->sockets, data->cores, 1107fe55c3cSAndreas Färber data->threads, data->maxcpus); 111*152e0393SThomas Huth qtest_add_data_func_full(path, data, test_plug_without_cpu_add, 11234e46f60SMarc-André Lureau test_data_free); 11334e46f60SMarc-André Lureau g_free(path); 1147fe55c3cSAndreas Färber } else { 11553f77e45SAndreas Färber path = g_strdup_printf("cpu/%s/add/%ux%ux%u&maxcpus=%u", 11653f77e45SAndreas Färber mname, data->sockets, data->cores, 1177fe55c3cSAndreas Färber data->threads, data->maxcpus); 118*152e0393SThomas Huth qtest_add_data_func_full(path, data, test_plug_with_cpu_add, 11934e46f60SMarc-André Lureau test_data_free); 12034e46f60SMarc-André Lureau g_free(path); 1217fe55c3cSAndreas Färber } 1227fe55c3cSAndreas Färber } 1237fe55c3cSAndreas Färber 1247fe55c3cSAndreas Färber int main(int argc, char **argv) 1257fe55c3cSAndreas Färber { 1267fe55c3cSAndreas Färber const char *arch = qtest_get_arch(); 1277fe55c3cSAndreas Färber 1287fe55c3cSAndreas Färber g_test_init(&argc, &argv, NULL); 1297fe55c3cSAndreas Färber 1307fe55c3cSAndreas Färber if (strcmp(arch, "i386") == 0 || strcmp(arch, "x86_64") == 0) { 13102ef6e87SThomas Huth qtest_cb_for_every_machine(add_pc_test_case); 1327fe55c3cSAndreas Färber } 1337fe55c3cSAndreas Färber 1347fe55c3cSAndreas Färber return g_test_run(); 1357fe55c3cSAndreas Färber } 136