1 /* 2 * HMP commands related to machines and CPUs 3 * 4 * Copyright IBM, Corp. 2011 5 * 6 * Authors: 7 * Anthony Liguori <aliguori@us.ibm.com> 8 * 9 * This work is licensed under the terms of the GNU GPL, version 2. See 10 * the COPYING file in the top-level directory. 11 * 12 * Contributions after 2012-01-13 are licensed under the terms of the 13 * GNU GPL, version 2 or (at your option) any later version. 14 */ 15 16 #include "qemu/osdep.h" 17 #include "monitor/hmp.h" 18 #include "monitor/monitor.h" 19 #include "qapi/error.h" 20 #include "qapi/qapi-builtin-visit.h" 21 #include "qapi/qapi-commands-machine.h" 22 #include "qapi/qmp/qdict.h" 23 #include "qapi/string-output-visitor.h" 24 #include "qemu/error-report.h" 25 #include "sysemu/numa.h" 26 #include "hw/boards.h" 27 28 void hmp_info_cpus(Monitor *mon, const QDict *qdict) 29 { 30 CpuInfoFastList *cpu_list, *cpu; 31 32 cpu_list = qmp_query_cpus_fast(NULL); 33 34 for (cpu = cpu_list; cpu; cpu = cpu->next) { 35 int active = ' '; 36 37 if (cpu->value->cpu_index == monitor_get_cpu_index(mon)) { 38 active = '*'; 39 } 40 41 monitor_printf(mon, "%c CPU #%" PRId64 ":", active, 42 cpu->value->cpu_index); 43 monitor_printf(mon, " thread_id=%" PRId64 "\n", cpu->value->thread_id); 44 } 45 46 qapi_free_CpuInfoFastList(cpu_list); 47 } 48 49 void hmp_hotpluggable_cpus(Monitor *mon, const QDict *qdict) 50 { 51 Error *err = NULL; 52 HotpluggableCPUList *l = qmp_query_hotpluggable_cpus(&err); 53 HotpluggableCPUList *saved = l; 54 CpuInstanceProperties *c; 55 56 if (err != NULL) { 57 hmp_handle_error(mon, err); 58 return; 59 } 60 61 monitor_printf(mon, "Hotpluggable CPUs:\n"); 62 while (l) { 63 monitor_printf(mon, " type: \"%s\"\n", l->value->type); 64 monitor_printf(mon, " vcpus_count: \"%" PRIu64 "\"\n", 65 l->value->vcpus_count); 66 if (l->value->has_qom_path) { 67 monitor_printf(mon, " qom_path: \"%s\"\n", l->value->qom_path); 68 } 69 70 c = l->value->props; 71 monitor_printf(mon, " CPUInstance Properties:\n"); 72 if (c->has_node_id) { 73 monitor_printf(mon, " node-id: \"%" PRIu64 "\"\n", c->node_id); 74 } 75 if (c->has_socket_id) { 76 monitor_printf(mon, " socket-id: \"%" PRIu64 "\"\n", c->socket_id); 77 } 78 if (c->has_die_id) { 79 monitor_printf(mon, " die-id: \"%" PRIu64 "\"\n", c->die_id); 80 } 81 if (c->has_core_id) { 82 monitor_printf(mon, " core-id: \"%" PRIu64 "\"\n", c->core_id); 83 } 84 if (c->has_thread_id) { 85 monitor_printf(mon, " thread-id: \"%" PRIu64 "\"\n", c->thread_id); 86 } 87 88 l = l->next; 89 } 90 91 qapi_free_HotpluggableCPUList(saved); 92 } 93 94 void hmp_info_memdev(Monitor *mon, const QDict *qdict) 95 { 96 Error *err = NULL; 97 MemdevList *memdev_list = qmp_query_memdev(&err); 98 MemdevList *m = memdev_list; 99 Visitor *v; 100 char *str; 101 102 while (m) { 103 v = string_output_visitor_new(false, &str); 104 visit_type_uint16List(v, NULL, &m->value->host_nodes, &error_abort); 105 monitor_printf(mon, "memory backend: %s\n", m->value->id); 106 monitor_printf(mon, " size: %" PRId64 "\n", m->value->size); 107 monitor_printf(mon, " merge: %s\n", 108 m->value->merge ? "true" : "false"); 109 monitor_printf(mon, " dump: %s\n", 110 m->value->dump ? "true" : "false"); 111 monitor_printf(mon, " prealloc: %s\n", 112 m->value->prealloc ? "true" : "false"); 113 monitor_printf(mon, " share: %s\n", 114 m->value->share ? "true" : "false"); 115 if (m->value->has_reserve) { 116 monitor_printf(mon, " reserve: %s\n", 117 m->value->reserve ? "true" : "false"); 118 } 119 monitor_printf(mon, " policy: %s\n", 120 HostMemPolicy_str(m->value->policy)); 121 visit_complete(v, &str); 122 monitor_printf(mon, " host nodes: %s\n", str); 123 124 g_free(str); 125 visit_free(v); 126 m = m->next; 127 } 128 129 monitor_printf(mon, "\n"); 130 131 qapi_free_MemdevList(memdev_list); 132 hmp_handle_error(mon, err); 133 } 134 135 void hmp_info_numa(Monitor *mon, const QDict *qdict) 136 { 137 int i, nb_numa_nodes; 138 NumaNodeMem *node_mem; 139 CpuInfoFastList *cpu_list, *cpu; 140 MachineState *ms = MACHINE(qdev_get_machine()); 141 142 nb_numa_nodes = ms->numa_state ? ms->numa_state->num_nodes : 0; 143 monitor_printf(mon, "%d nodes\n", nb_numa_nodes); 144 if (!nb_numa_nodes) { 145 return; 146 } 147 148 cpu_list = qmp_query_cpus_fast(&error_abort); 149 node_mem = g_new0(NumaNodeMem, nb_numa_nodes); 150 151 query_numa_node_mem(node_mem, ms); 152 for (i = 0; i < nb_numa_nodes; i++) { 153 monitor_printf(mon, "node %d cpus:", i); 154 for (cpu = cpu_list; cpu; cpu = cpu->next) { 155 if (cpu->value->has_props && cpu->value->props->has_node_id && 156 cpu->value->props->node_id == i) { 157 monitor_printf(mon, " %" PRIi64, cpu->value->cpu_index); 158 } 159 } 160 monitor_printf(mon, "\n"); 161 monitor_printf(mon, "node %d size: %" PRId64 " MB\n", i, 162 node_mem[i].node_mem >> 20); 163 monitor_printf(mon, "node %d plugged: %" PRId64 " MB\n", i, 164 node_mem[i].node_plugged_mem >> 20); 165 } 166 qapi_free_CpuInfoFastList(cpu_list); 167 g_free(node_mem); 168 } 169