summaryrefslogtreecommitdiffstats
path: root/include
diff options
context:
space:
mode:
Diffstat (limited to 'include')
-rw-r--r--include/hw/boards.h27
-rw-r--r--include/hw/firmware/smbios.h5
-rw-r--r--include/hw/i386/pc.h8
-rw-r--r--include/hw/i386/topology.h76
4 files changed, 90 insertions, 26 deletions
diff --git a/include/hw/boards.h b/include/hw/boards.h
index c6ad196b14..a71d1a53a5 100644
--- a/include/hw/boards.h
+++ b/include/hw/boards.h
@@ -160,6 +160,12 @@ typedef struct {
* @kvm_type:
* Return the type of KVM corresponding to the kvm-type string option or
* computed based on other criteria such as the host kernel capabilities.
+ * @numa_mem_supported:
+ * true if '--numa node.mem' option is supported and false otherwise
+ * @smp_parse:
+ * The function pointer to hook different machine specific functions for
+ * parsing "smp-opts" from QemuOpts to MachineState::CpuTopology and more
+ * machine specific topology fields, such as smp_dies for PCMachine.
*/
struct MachineClass {
/*< private >*/
@@ -173,9 +179,10 @@ struct MachineClass {
const char *deprecation_reason;
void (*init)(MachineState *state);
- void (*reset)(void);
- void (*hot_add_cpu)(const int64_t id, Error **errp);
+ void (*reset)(MachineState *state);
+ void (*hot_add_cpu)(MachineState *state, const int64_t id, Error **errp);
int (*kvm_type)(MachineState *machine, const char *arg);
+ void (*smp_parse)(MachineState *ms, QemuOpts *opts);
BlockInterfaceType block_default_type;
int units_per_default_bus;
@@ -212,6 +219,7 @@ struct MachineClass {
bool ignore_boot_device_suffixes;
bool smbus_no_migration_support;
bool nvdimm_supported;
+ bool numa_mem_supported;
HotplugHandler *(*get_hotplug_handler)(MachineState *machine,
DeviceState *dev);
@@ -233,6 +241,20 @@ typedef struct DeviceMemoryState {
} DeviceMemoryState;
/**
+ * CpuTopology:
+ * @cpus: the number of present logical processors on the machine
+ * @cores: the number of cores in one package
+ * @threads: the number of threads in one core
+ * @max_cpus: the maximum number of logical processors on the machine
+ */
+typedef struct CpuTopology {
+ unsigned int cpus;
+ unsigned int cores;
+ unsigned int threads;
+ unsigned int max_cpus;
+} CpuTopology;
+
+/**
* MachineState:
*/
struct MachineState {
@@ -274,6 +296,7 @@ struct MachineState {
const char *cpu_type;
AccelState *accelerator;
CPUArchIdList *possible_cpus;
+ CpuTopology smp;
struct NVDIMMState *nvdimms_state;
};
diff --git a/include/hw/firmware/smbios.h b/include/hw/firmware/smbios.h
index 6fef32a3c9..02a0ced0a0 100644
--- a/include/hw/firmware/smbios.h
+++ b/include/hw/firmware/smbios.h
@@ -268,8 +268,9 @@ void smbios_set_cpuid(uint32_t version, uint32_t features);
void smbios_set_defaults(const char *manufacturer, const char *product,
const char *version, bool legacy_mode,
bool uuid_encoded, SmbiosEntryPointType ep_type);
-uint8_t *smbios_get_table_legacy(size_t *length);
-void smbios_get_tables(const struct smbios_phys_mem_area *mem_array,
+uint8_t *smbios_get_table_legacy(MachineState *ms, size_t *length);
+void smbios_get_tables(MachineState *ms,
+ const struct smbios_phys_mem_area *mem_array,
const unsigned int mem_array_size,
uint8_t **tables, size_t *tables_len,
uint8_t **anchor, size_t *anchor_len);
diff --git a/include/hw/i386/pc.h b/include/hw/i386/pc.h
index 853502f277..859b64c51d 100644
--- a/include/hw/i386/pc.h
+++ b/include/hw/i386/pc.h
@@ -24,6 +24,7 @@
* PCMachineState:
* @acpi_dev: link to ACPI PM device that performs ACPI hotplug handling
* @boot_cpus: number of present VCPUs
+ * @smp_dies: number of dies per one package
*/
struct PCMachineState {
/*< private >*/
@@ -59,6 +60,7 @@ struct PCMachineState {
bool apic_xrupt_override;
unsigned apic_id_limit;
uint16_t boot_cpus;
+ unsigned smp_dies;
/* NUMA information: */
uint64_t numa_nodes;
@@ -107,6 +109,9 @@ typedef struct PCMachineClass {
/* Compat options: */
+ /* Default CPU model version. See x86_cpu_set_default_version(). */
+ int default_cpu_version;
+
/* ACPI compat: */
bool has_acpi_build;
bool rsdp_in_ram;
@@ -189,7 +194,8 @@ void pc_register_ferr_irq(qemu_irq irq);
void pc_acpi_smi_interrupt(void *opaque, int irq, int level);
void pc_cpus_init(PCMachineState *pcms);
-void pc_hot_add_cpu(const int64_t id, Error **errp);
+void pc_hot_add_cpu(MachineState *ms, const int64_t id, Error **errp);
+void pc_smp_parse(MachineState *ms, QemuOpts *opts);
void pc_guest_info_init(PCMachineState *pcms);
diff --git a/include/hw/i386/topology.h b/include/hw/i386/topology.h
index 1ebaee0f76..4ff5b2da6c 100644
--- a/include/hw/i386/topology.h
+++ b/include/hw/i386/topology.h
@@ -47,6 +47,7 @@ typedef uint32_t apic_id_t;
typedef struct X86CPUTopoInfo {
unsigned pkg_id;
+ unsigned die_id;
unsigned core_id;
unsigned smt_id;
} X86CPUTopoInfo;
@@ -62,87 +63,120 @@ static unsigned apicid_bitwidth_for_count(unsigned count)
/* Bit width of the SMT_ID (thread ID) field on the APIC ID
*/
-static inline unsigned apicid_smt_width(unsigned nr_cores, unsigned nr_threads)
+static inline unsigned apicid_smt_width(unsigned nr_dies,
+ unsigned nr_cores,
+ unsigned nr_threads)
{
return apicid_bitwidth_for_count(nr_threads);
}
/* Bit width of the Core_ID field
*/
-static inline unsigned apicid_core_width(unsigned nr_cores, unsigned nr_threads)
+static inline unsigned apicid_core_width(unsigned nr_dies,
+ unsigned nr_cores,
+ unsigned nr_threads)
{
return apicid_bitwidth_for_count(nr_cores);
}
+/* Bit width of the Die_ID field */
+static inline unsigned apicid_die_width(unsigned nr_dies,
+ unsigned nr_cores,
+ unsigned nr_threads)
+{
+ return apicid_bitwidth_for_count(nr_dies);
+}
+
/* Bit offset of the Core_ID field
*/
-static inline unsigned apicid_core_offset(unsigned nr_cores,
+static inline unsigned apicid_core_offset(unsigned nr_dies,
+ unsigned nr_cores,
unsigned nr_threads)
{
- return apicid_smt_width(nr_cores, nr_threads);
+ return apicid_smt_width(nr_dies, nr_cores, nr_threads);
+}
+
+/* Bit offset of the Die_ID field */
+static inline unsigned apicid_die_offset(unsigned nr_dies,
+ unsigned nr_cores,
+ unsigned nr_threads)
+{
+ return apicid_core_offset(nr_dies, nr_cores, nr_threads) +
+ apicid_core_width(nr_dies, nr_cores, nr_threads);
}
/* Bit offset of the Pkg_ID (socket ID) field
*/
-static inline unsigned apicid_pkg_offset(unsigned nr_cores, unsigned nr_threads)
+static inline unsigned apicid_pkg_offset(unsigned nr_dies,
+ unsigned nr_cores,
+ unsigned nr_threads)
{
- return apicid_core_offset(nr_cores, nr_threads) +
- apicid_core_width(nr_cores, nr_threads);
+ return apicid_die_offset(nr_dies, nr_cores, nr_threads) +
+ apicid_die_width(nr_dies, nr_cores, nr_threads);
}
/* Make APIC ID for the CPU based on Pkg_ID, Core_ID, SMT_ID
*
* The caller must make sure core_id < nr_cores and smt_id < nr_threads.
*/
-static inline apic_id_t apicid_from_topo_ids(unsigned nr_cores,
+static inline apic_id_t apicid_from_topo_ids(unsigned nr_dies,
+ unsigned nr_cores,
unsigned nr_threads,
const X86CPUTopoInfo *topo)
{
- return (topo->pkg_id << apicid_pkg_offset(nr_cores, nr_threads)) |
- (topo->core_id << apicid_core_offset(nr_cores, nr_threads)) |
+ return (topo->pkg_id << apicid_pkg_offset(nr_dies, nr_cores, nr_threads)) |
+ (topo->die_id << apicid_die_offset(nr_dies, nr_cores, nr_threads)) |
+ (topo->core_id << apicid_core_offset(nr_dies, nr_cores, nr_threads)) |
topo->smt_id;
}
/* Calculate thread/core/package IDs for a specific topology,
* based on (contiguous) CPU index
*/
-static inline void x86_topo_ids_from_idx(unsigned nr_cores,
+static inline void x86_topo_ids_from_idx(unsigned nr_dies,
+ unsigned nr_cores,
unsigned nr_threads,
unsigned cpu_index,
X86CPUTopoInfo *topo)
{
- unsigned core_index = cpu_index / nr_threads;
+ topo->pkg_id = cpu_index / (nr_dies * nr_cores * nr_threads);
+ topo->die_id = cpu_index / (nr_cores * nr_threads) % nr_dies;
+ topo->core_id = cpu_index / nr_threads % nr_cores;
topo->smt_id = cpu_index % nr_threads;
- topo->core_id = core_index % nr_cores;
- topo->pkg_id = core_index / nr_cores;
}
/* Calculate thread/core/package IDs for a specific topology,
* based on APIC ID
*/
static inline void x86_topo_ids_from_apicid(apic_id_t apicid,
+ unsigned nr_dies,
unsigned nr_cores,
unsigned nr_threads,
X86CPUTopoInfo *topo)
{
topo->smt_id = apicid &
- ~(0xFFFFFFFFUL << apicid_smt_width(nr_cores, nr_threads));
- topo->core_id = (apicid >> apicid_core_offset(nr_cores, nr_threads)) &
- ~(0xFFFFFFFFUL << apicid_core_width(nr_cores, nr_threads));
- topo->pkg_id = apicid >> apicid_pkg_offset(nr_cores, nr_threads);
+ ~(0xFFFFFFFFUL << apicid_smt_width(nr_dies, nr_cores, nr_threads));
+ topo->core_id =
+ (apicid >> apicid_core_offset(nr_dies, nr_cores, nr_threads)) &
+ ~(0xFFFFFFFFUL << apicid_core_width(nr_dies, nr_cores, nr_threads));
+ topo->die_id =
+ (apicid >> apicid_die_offset(nr_dies, nr_cores, nr_threads)) &
+ ~(0xFFFFFFFFUL << apicid_die_width(nr_dies, nr_cores, nr_threads));
+ topo->pkg_id = apicid >> apicid_pkg_offset(nr_dies, nr_cores, nr_threads);
}
/* Make APIC ID for the CPU 'cpu_index'
*
* 'cpu_index' is a sequential, contiguous ID for the CPU.
*/
-static inline apic_id_t x86_apicid_from_cpu_idx(unsigned nr_cores,
+static inline apic_id_t x86_apicid_from_cpu_idx(unsigned nr_dies,
+ unsigned nr_cores,
unsigned nr_threads,
unsigned cpu_index)
{
X86CPUTopoInfo topo;
- x86_topo_ids_from_idx(nr_cores, nr_threads, cpu_index, &topo);
- return apicid_from_topo_ids(nr_cores, nr_threads, &topo);
+ x86_topo_ids_from_idx(nr_dies, nr_cores, nr_threads, cpu_index, &topo);
+ return apicid_from_topo_ids(nr_dies, nr_cores, nr_threads, &topo);
}
#endif /* HW_I386_TOPOLOGY_H */