diff options
Diffstat (limited to 'include')
37 files changed, 572 insertions, 204 deletions
diff --git a/include/block/block.h b/include/block/block.h index 36efaeac2d..963a61fa4c 100644 --- a/include/block/block.h +++ b/include/block/block.h @@ -184,7 +184,11 @@ void bdrv_append(BlockDriverState *bs_new, BlockDriverState *bs_top); int bdrv_parse_cache_flags(const char *mode, int *flags); int bdrv_parse_discard_flags(const char *mode, int *flags); int bdrv_file_open(BlockDriverState **pbs, const char *filename, - QDict *options, int flags, Error **errp); + const char *reference, QDict *options, int flags, + Error **errp); +int bdrv_open_image(BlockDriverState **pbs, const char *filename, + QDict *options, const char *bdref_key, int flags, + bool force_raw, bool allow_none, Error **errp); int bdrv_open_backing_file(BlockDriverState *bs, QDict *options, Error **errp); int bdrv_open(BlockDriverState *bs, const char *filename, QDict *options, int flags, BlockDriver *drv, Error **errp); @@ -220,7 +224,6 @@ BlockDriverAIOCB *bdrv_aio_write_zeroes(BlockDriverState *bs, int64_t sector_num int nb_sectors, BdrvRequestFlags flags, BlockDriverCompletionFunc *cb, void *opaque); int bdrv_make_zero(BlockDriverState *bs, BdrvRequestFlags flags); -int bdrv_writev(BlockDriverState *bs, int64_t sector_num, QEMUIOVector *qiov); int bdrv_pread(BlockDriverState *bs, int64_t offset, void *buf, int count); int bdrv_pwrite(BlockDriverState *bs, int64_t offset, @@ -249,6 +252,7 @@ int bdrv_truncate(BlockDriverState *bs, int64_t offset); int64_t bdrv_getlength(BlockDriverState *bs); int64_t bdrv_get_allocated_file_size(BlockDriverState *bs); void bdrv_get_geometry(BlockDriverState *bs, uint64_t *nb_sectors_ptr); +int bdrv_refresh_limits(BlockDriverState *bs); int bdrv_commit(BlockDriverState *bs); int bdrv_commit_all(void); int bdrv_change_backing_file(BlockDriverState *bs, @@ -283,16 +287,16 @@ int bdrv_amend_options(BlockDriverState *bs_new, QEMUOptionParameter *options); /* external snapshots */ typedef enum { - EXT_SNAPSHOT_ALLOWED, - EXT_SNAPSHOT_FORBIDDEN, -} ExtSnapshotPerm; + BS_IS_A_FILTER, + BS_FILTER_PASS_DOWN, + BS_AUTHORIZATION_COUNT, +} BsAuthorization; -/* return EXT_SNAPSHOT_ALLOWED if external snapshot is allowed - * return EXT_SNAPSHOT_FORBIDDEN if external snapshot is forbidden - */ -ExtSnapshotPerm bdrv_check_ext_snapshot(BlockDriverState *bs); -/* helper used to forbid external snapshots like in blkverify */ -ExtSnapshotPerm bdrv_check_ext_snapshot_forbidden(BlockDriverState *bs); +bool bdrv_generic_is_first_non_filter(BlockDriverState *bs, + BlockDriverState *candidate); +bool bdrv_recurse_is_first_non_filter(BlockDriverState *bs, + BlockDriverState *candidate); +bool bdrv_is_first_non_filter(BlockDriverState *candidate); /* async block I/O */ typedef void BlockDriverDirtyHandler(BlockDriverState *bs, int64_t sector, @@ -374,6 +378,11 @@ void bdrv_lock_medium(BlockDriverState *bs, bool locked); void bdrv_eject(BlockDriverState *bs, bool eject_flag); const char *bdrv_get_format_name(BlockDriverState *bs); BlockDriverState *bdrv_find(const char *name); +BlockDriverState *bdrv_find_node(const char *node_name); +BlockDeviceInfoList *bdrv_named_nodes_list(void); +BlockDriverState *bdrv_lookup_bs(const char *device, + const char *node_name, + Error **errp); BlockDriverState *bdrv_next(BlockDriverState *bs); void bdrv_iterate(void (*it)(void *opaque, BlockDriverState *bs), void *opaque); @@ -418,7 +427,10 @@ void bdrv_img_create(const char *filename, const char *fmt, char *options, uint64_t img_size, int flags, Error **errp, bool quiet); -void bdrv_set_buffer_alignment(BlockDriverState *bs, int align); +/* Returns the alignment in bytes that is required so that no bounce buffer + * is required throughout the stack */ +size_t bdrv_opt_mem_align(BlockDriverState *bs); +void bdrv_set_guest_block_size(BlockDriverState *bs, int align); void *qemu_blockalign(BlockDriverState *bs, size_t size); bool bdrv_qiov_is_aligned(BlockDriverState *bs, QEMUIOVector *qiov); @@ -515,6 +527,14 @@ typedef enum { BLKDBG_FLUSH_TO_OS, BLKDBG_FLUSH_TO_DISK, + BLKDBG_PWRITEV_RMW_HEAD, + BLKDBG_PWRITEV_RMW_AFTER_HEAD, + BLKDBG_PWRITEV_RMW_TAIL, + BLKDBG_PWRITEV_RMW_AFTER_TAIL, + BLKDBG_PWRITEV, + BLKDBG_PWRITEV_ZERO, + BLKDBG_PWRITEV_DONE, + BLKDBG_EVENT_MAX, } BlkDebugEvent; diff --git a/include/block/block_int.h b/include/block/block_int.h index 2772f2f1bd..0bcf1c9b8c 100644 --- a/include/block/block_int.h +++ b/include/block/block_int.h @@ -57,22 +57,35 @@ typedef struct BdrvTrackedRequest { BlockDriverState *bs; - int64_t sector_num; - int nb_sectors; + int64_t offset; + unsigned int bytes; bool is_write; + + bool serialising; + int64_t overlap_offset; + unsigned int overlap_bytes; + QLIST_ENTRY(BdrvTrackedRequest) list; Coroutine *co; /* owner, used for deadlock detection */ CoQueue wait_queue; /* coroutines blocked on this request */ + + struct BdrvTrackedRequest *waiting_for; } BdrvTrackedRequest; struct BlockDriver { const char *format_name; int instance_size; - /* if not defined external snapshots are allowed - * future block filters will query their children to build the response + /* this table of boolean contains authorizations for the block operations */ + bool authorizations[BS_AUTHORIZATION_COUNT]; + /* for snapshots complex block filter like Quorum can implement the + * following recursive callback instead of BS_IS_A_FILTER. + * It's purpose is to recurse on the filter children while calling + * bdrv_recurse_is_first_non_filter on them. + * For a sample implementation look in the future Quorum block filter. */ - ExtSnapshotPerm (*bdrv_check_ext_snapshot)(BlockDriverState *bs); + bool (*bdrv_recurse_is_first_non_filter)(BlockDriverState *bs, + BlockDriverState *candidate); int (*bdrv_probe)(const uint8_t *buf, int buf_size, const char *filename); int (*bdrv_probe_device)(const char *filename); @@ -226,6 +239,8 @@ struct BlockDriver { int (*bdrv_debug_resume)(BlockDriverState *bs, const char *tag); bool (*bdrv_debug_is_suspended)(BlockDriverState *bs, const char *tag); + int (*bdrv_refresh_limits)(BlockDriverState *bs); + /* * Returns 1 if newly created images are guaranteed to contain only * zeros, 0 otherwise. @@ -250,6 +265,9 @@ typedef struct BlockLimits { /* optimal transfer length in sectors */ int opt_transfer_length; + + /* memory alignment so that no bounce buffer is needed */ + size_t opt_mem_alignment; } BlockLimits; /* @@ -291,8 +309,8 @@ struct BlockDriverState { /* Callback before write request is processed */ NotifierWithReturnList before_write_notifiers; - /* number of in-flight copy-on-read requests */ - unsigned int copy_on_read_in_flight; + /* number of in-flight serialising requests */ + unsigned int serialising_in_flight; /* I/O throttling */ ThrottleState throttle_state; @@ -314,8 +332,11 @@ struct BlockDriverState { /* Whether produces zeros when read beyond eof */ bool zero_beyond_eof; - /* the memory alignment required for the buffers handled by this driver */ - int buffer_alignment; + /* Alignment requirement for offset/length of I/O requests */ + unsigned int request_alignment; + + /* the block size for which the guest device expects atomicity */ + int guest_block_size; /* do we need to tell the quest if we have a volatile write cache? */ int enable_write_cache; @@ -325,11 +346,18 @@ struct BlockDriverState { BlockdevOnError on_read_error, on_write_error; bool iostatus_enabled; BlockDeviceIoStatus iostatus; + + /* the following member gives a name to every node on the bs graph. */ + char node_name[32]; + /* element of the list of named nodes building the graph */ + QTAILQ_ENTRY(BlockDriverState) node_list; + /* Device name is the name associated with the "drive" the guest sees */ char device_name[32]; + /* element of the list of "drives" the guest sees */ + QTAILQ_ENTRY(BlockDriverState) device_list; QLIST_HEAD(, BdrvDirtyBitmap) dirty_bitmaps; int refcnt; int in_use; /* users other than guest access, eg. block migration */ - QTAILQ_ENTRY(BlockDriverState) list; QLIST_HEAD(, BdrvTrackedRequest) tracked_requests; diff --git a/include/block/qapi.h b/include/block/qapi.h index 9518ee4001..e92c00daf6 100644 --- a/include/block/qapi.h +++ b/include/block/qapi.h @@ -29,6 +29,7 @@ #include "block/block.h" #include "block/snapshot.h" +BlockDeviceInfo *bdrv_block_device_info(BlockDriverState *bs); int bdrv_query_snapshot_info_list(BlockDriverState *bs, SnapshotInfoList **p_list, Error **errp); diff --git a/include/exec/cpu-all.h b/include/exec/cpu-all.h index b6998f055a..4cb4b4a53a 100644 --- a/include/exec/cpu-all.h +++ b/include/exec/cpu-all.h @@ -21,6 +21,7 @@ #include "qemu-common.h" #include "exec/cpu-common.h" +#include "exec/memory.h" #include "qemu/thread.h" #include "qom/cpu.h" @@ -459,7 +460,7 @@ typedef struct RAMBlock { typedef struct RAMList { QemuMutex mutex; /* Protected by the iothread lock. */ - uint8_t *phys_dirty; + unsigned long *dirty_memory[DIRTY_MEMORY_NUM]; RAMBlock *mru_block; /* Protected by the ramlist lock. */ QTAILQ_HEAD(, RAMBlock) blocks; diff --git a/include/exec/exec-all.h b/include/exec/exec-all.h index ea90b649d4..3b03cbfcf8 100644 --- a/include/exec/exec-all.h +++ b/include/exec/exec-all.h @@ -81,6 +81,7 @@ void cpu_gen_init(void); int cpu_gen_code(CPUArchState *env, struct TranslationBlock *tb, int *gen_code_size_ptr); bool cpu_restore_state(CPUArchState *env, uintptr_t searched_pc); +void page_size_init(void); void QEMU_NORETURN cpu_resume_from_signal(CPUArchState *env1, void *puc); void QEMU_NORETURN cpu_io_recompile(CPUArchState *env, uintptr_t retaddr); diff --git a/include/exec/memory-internal.h b/include/exec/memory-internal.h index d0e063392a..25c43c06e9 100644 --- a/include/exec/memory-internal.h +++ b/include/exec/memory-internal.h @@ -20,9 +20,6 @@ #define MEMORY_INTERNAL_H #ifndef CONFIG_USER_ONLY -#include "hw/xen/xen.h" - - typedef struct AddressSpaceDispatch AddressSpaceDispatch; void address_space_init_dispatch(AddressSpace *as); @@ -33,92 +30,5 @@ extern const MemoryRegionOps unassigned_mem_ops; bool memory_region_access_valid(MemoryRegion *mr, hwaddr addr, unsigned size, bool is_write); -ram_addr_t qemu_ram_alloc_from_ptr(ram_addr_t size, void *host, - MemoryRegion *mr); -ram_addr_t qemu_ram_alloc(ram_addr_t size, MemoryRegion *mr); -void *qemu_get_ram_ptr(ram_addr_t addr); -void qemu_ram_free(ram_addr_t addr); -void qemu_ram_free_from_ptr(ram_addr_t addr); - -#define VGA_DIRTY_FLAG 0x01 -#define CODE_DIRTY_FLAG 0x02 -#define MIGRATION_DIRTY_FLAG 0x08 - -static inline int cpu_physical_memory_get_dirty_flags(ram_addr_t addr) -{ - return ram_list.phys_dirty[addr >> TARGET_PAGE_BITS]; -} - -/* read dirty bit (return 0 or 1) */ -static inline int cpu_physical_memory_is_dirty(ram_addr_t addr) -{ - return cpu_physical_memory_get_dirty_flags(addr) == 0xff; -} - -static inline int cpu_physical_memory_get_dirty(ram_addr_t start, - ram_addr_t length, - int dirty_flags) -{ - int ret = 0; - ram_addr_t addr, end; - - end = TARGET_PAGE_ALIGN(start + length); - start &= TARGET_PAGE_MASK; - for (addr = start; addr < end; addr += TARGET_PAGE_SIZE) { - ret |= cpu_physical_memory_get_dirty_flags(addr) & dirty_flags; - } - return ret; -} - -static inline int cpu_physical_memory_set_dirty_flags(ram_addr_t addr, - int dirty_flags) -{ - return ram_list.phys_dirty[addr >> TARGET_PAGE_BITS] |= dirty_flags; -} - -static inline void cpu_physical_memory_set_dirty(ram_addr_t addr) -{ - cpu_physical_memory_set_dirty_flags(addr, 0xff); -} - -static inline int cpu_physical_memory_clear_dirty_flags(ram_addr_t addr, - int dirty_flags) -{ - int mask = ~dirty_flags; - - return ram_list.phys_dirty[addr >> TARGET_PAGE_BITS] &= mask; -} - -static inline void cpu_physical_memory_set_dirty_range(ram_addr_t start, - ram_addr_t length, - int dirty_flags) -{ - ram_addr_t addr, end; - - end = TARGET_PAGE_ALIGN(start + length); - start &= TARGET_PAGE_MASK; - for (addr = start; addr < end; addr += TARGET_PAGE_SIZE) { - cpu_physical_memory_set_dirty_flags(addr, dirty_flags); - } - xen_modified_memory(addr, length); -} - -static inline void cpu_physical_memory_mask_dirty_range(ram_addr_t start, - ram_addr_t length, - int dirty_flags) -{ - ram_addr_t addr, end; - - end = TARGET_PAGE_ALIGN(start + length); - start &= TARGET_PAGE_MASK; - for (addr = start; addr < end; addr += TARGET_PAGE_SIZE) { - cpu_physical_memory_clear_dirty_flags(addr, dirty_flags); - } -} - -void cpu_physical_memory_reset_dirty(ram_addr_t start, ram_addr_t end, - int dirty_flags); - #endif - #endif diff --git a/include/exec/memory.h b/include/exec/memory.h index 480dfbf9da..296d6ab2f4 100644 --- a/include/exec/memory.h +++ b/include/exec/memory.h @@ -16,6 +16,11 @@ #ifndef CONFIG_USER_ONLY +#define DIRTY_MEMORY_VGA 0 +#define DIRTY_MEMORY_CODE 1 +#define DIRTY_MEMORY_MIGRATION 2 +#define DIRTY_MEMORY_NUM 3 /* num of dirty bits */ + #include <stdint.h> #include <stdbool.h> #include "qemu-common.h" @@ -33,13 +38,6 @@ typedef struct MemoryRegionOps MemoryRegionOps; typedef struct MemoryRegionMmio MemoryRegionMmio; -/* Must match *_DIRTY_FLAGS in cpu-all.h. To be replaced with dynamic - * registration. - */ -#define DIRTY_MEMORY_VGA 0 -#define DIRTY_MEMORY_CODE 1 -#define DIRTY_MEMORY_MIGRATION 3 - struct MemoryRegionMmio { CPUReadMemoryFunc *read[3]; CPUWriteMemoryFunc *write[3]; diff --git a/include/exec/ram_addr.h b/include/exec/ram_addr.h new file mode 100644 index 0000000000..481a447417 --- /dev/null +++ b/include/exec/ram_addr.h @@ -0,0 +1,149 @@ +/* + * Declarations for cpu physical memory functions + * + * Copyright 2011 Red Hat, Inc. and/or its affiliates + * + * Authors: + * Avi Kivity <avi@redhat.com> + * + * This work is licensed under the terms of the GNU GPL, version 2 or + * later. See the COPYING file in the top-level directory. + * + */ + +/* + * This header is for use by exec.c and memory.c ONLY. Do not include it. + * The functions declared here will be removed soon. + */ + +#ifndef RAM_ADDR_H +#define RAM_ADDR_H + +#ifndef CONFIG_USER_ONLY +#include "hw/xen/xen.h" + +ram_addr_t qemu_ram_alloc_from_ptr(ram_addr_t size, void *host, + MemoryRegion *mr); +ram_addr_t qemu_ram_alloc(ram_addr_t size, MemoryRegion *mr); +void *qemu_get_ram_ptr(ram_addr_t addr); +void qemu_ram_free(ram_addr_t addr); +void qemu_ram_free_from_ptr(ram_addr_t addr); + +static inline bool cpu_physical_memory_get_dirty(ram_addr_t start, + ram_addr_t length, + unsigned client) +{ + unsigned long end, page, next; + + assert(client < DIRTY_MEMORY_NUM); + + end = TARGET_PAGE_ALIGN(start + length) >> TARGET_PAGE_BITS; + page = start >> TARGET_PAGE_BITS; + next = find_next_bit(ram_list.dirty_memory[client], end, page); + + return next < end; +} + +static inline bool cpu_physical_memory_get_dirty_flag(ram_addr_t addr, + unsigned client) +{ + return cpu_physical_memory_get_dirty(addr, 1, client); +} + +static inline bool cpu_physical_memory_is_clean(ram_addr_t addr) +{ + bool vga = cpu_physical_memory_get_dirty_flag(addr, DIRTY_MEMORY_VGA); + bool code = cpu_physical_memory_get_dirty_flag(addr, DIRTY_MEMORY_CODE); + bool migration = + cpu_physical_memory_get_dirty_flag(addr, DIRTY_MEMORY_MIGRATION); + return !(vga && code && migration); +} + +static inline void cpu_physical_memory_set_dirty_flag(ram_addr_t addr, + unsigned client) +{ + assert(client < DIRTY_MEMORY_NUM); + set_bit(addr >> TARGET_PAGE_BITS, ram_list.dirty_memory[client]); +} + +static inline void cpu_physical_memory_set_dirty_range(ram_addr_t start, + ram_addr_t length) +{ + unsigned long end, page; + + end = TARGET_PAGE_ALIGN(start + length) >> TARGET_PAGE_BITS; + page = start >> TARGET_PAGE_BITS; + bitmap_set(ram_list.dirty_memory[DIRTY_MEMORY_MIGRATION], page, end - page); + bitmap_set(ram_list.dirty_memory[DIRTY_MEMORY_VGA], page, end - page); + bitmap_set(ram_list.dirty_memory[DIRTY_MEMORY_CODE], page, end - page); + xen_modified_memory(start, length); +} + +#if !defined(_WIN32) +static inline void cpu_physical_memory_set_dirty_lebitmap(unsigned long *bitmap, + ram_addr_t start, + ram_addr_t pages) +{ + unsigned long i, j; + unsigned long page_number, c; + hwaddr addr; + ram_addr_t ram_addr; + unsigned long len = (pages + HOST_LONG_BITS - 1) / HOST_LONG_BITS; + unsigned long hpratio = getpagesize() / TARGET_PAGE_SIZE; + unsigned long page = BIT_WORD(start >> TARGET_PAGE_BITS); + + /* start address is aligned at the start of a word? */ + if (((page * BITS_PER_LONG) << TARGET_PAGE_BITS) == start) { + long k; + long nr = BITS_TO_LONGS(pages); + + for (k = 0; k < nr; k++) { + if (bitmap[k]) { + unsigned long temp = leul_to_cpu(bitmap[k]); + + ram_list.dirty_memory[DIRTY_MEMORY_MIGRATION][page + k] |= temp; + ram_list.dirty_memory[DIRTY_MEMORY_VGA][page + k] |= temp; + ram_list.dirty_memory[DIRTY_MEMORY_CODE][page + k] |= temp; + } + } + xen_modified_memory(start, pages); + } else { + /* + * bitmap-traveling is faster than memory-traveling (for addr...) + * especially when most of the memory is not dirty. + */ + for (i = 0; i < len; i++) { + if (bitmap[i] != 0) { + c = leul_to_cpu(bitmap[i]); + do { + j = ffsl(c) - 1; + c &= ~(1ul << j); + page_number = (i * HOST_LONG_BITS + j) * hpratio; + addr = page_number * TARGET_PAGE_SIZE; + ram_addr = start + addr; + cpu_physical_memory_set_dirty_range(ram_addr, + TARGET_PAGE_SIZE * hpratio); + } while (c != 0); + } + } + } +} +#endif /* not _WIN32 */ + +static inline void cpu_physical_memory_clear_dirty_range(ram_addr_t start, + ram_addr_t length, + unsigned client) +{ + unsigned long end, page; + + assert(client < DIRTY_MEMORY_NUM); + end = TARGET_PAGE_ALIGN(start + length) >> TARGET_PAGE_BITS; + page = start >> TARGET_PAGE_BITS; + bitmap_clear(ram_list.dirty_memory[client], page, end - page); +} + +void cpu_physical_memory_reset_dirty(ram_addr_t start, ram_addr_t length, + unsigned client); + +#endif +#endif diff --git a/include/hw/acpi/cpu_hotplug.h b/include/hw/acpi/cpu_hotplug.h new file mode 100644 index 0000000000..4576400fd7 --- /dev/null +++ b/include/hw/acpi/cpu_hotplug.h @@ -0,0 +1,27 @@ +/* + * QEMU ACPI hotplug utilities + * + * Copyright (C) 2013 Red Hat Inc + * + * Authors: + * Igor Mammedov <imammedo@redhat.com> + * + * This work is licensed under the terms of the GNU GPL, version 2 or later. + * See the COPYING file in the top-level directory. + */ +#ifndef ACPI_HOTPLUG_H +#define ACPI_HOTPLUG_H + +#include "hw/acpi/acpi.h" +#include "hw/acpi/cpu_hotplug_defs.h" + +typedef struct AcpiCpuHotplug { + MemoryRegion io; + uint8_t sts[ACPI_GPE_PROC_LEN]; +} AcpiCpuHotplug; + +void AcpiCpuHotplug_add(ACPIGPE *gpe, AcpiCpuHotplug *g, CPUState *cpu); + +void AcpiCpuHotplug_init(MemoryRegion *parent, Object *owner, + AcpiCpuHotplug *gpe_cpu, uint16_t base); +#endif diff --git a/include/hw/acpi/cpu_hotplug_defs.h b/include/hw/acpi/cpu_hotplug_defs.h new file mode 100644 index 0000000000..2725b50aac --- /dev/null +++ b/include/hw/acpi/cpu_hotplug_defs.h @@ -0,0 +1,24 @@ +/* + * QEMU ACPI hotplug utilities shared defines + * + * Copyright (C) 2013 Red Hat Inc + * + * Authors: + * Igor Mammedov <imammedo@redhat.com> + * + * This work is licensed under the terms of the GNU GPL, version 2 or later. + * See the COPYING file in the top-level directory. + */ +#ifndef ACPI_HOTPLUG_DEFS_H +#define ACPI_HOTPLUG_DEFS_H + +/* + * ONLY DEFINEs are permited in this file since it's shared + * between C and ASL code. + */ +#define ACPI_CPU_HOTPLUG_STATUS 4 +#define ACPI_GPE_PROC_LEN 32 +#define ICH9_CPU_HOTPLUG_IO_BASE 0x0CD8 +#define PIIX4_CPU_HOTPLUG_IO_BASE 0xaf00 + +#endif diff --git a/include/hw/acpi/ich9.h b/include/hw/acpi/ich9.h index 82fcf9f2eb..104f419852 100644 --- a/include/hw/acpi/ich9.h +++ b/include/hw/acpi/ich9.h @@ -22,6 +22,7 @@ #define HW_ACPI_ICH9_H #include "hw/acpi/acpi.h" +#include "hw/acpi/cpu_hotplug.h" typedef struct ICH9LPCPMRegs { /* @@ -42,6 +43,9 @@ typedef struct ICH9LPCPMRegs { uint32_t pm_io_base; Notifier powerdown_notifier; + + AcpiCpuHotplug gpe_cpu; + Notifier cpu_added_notifier; } ICH9LPCPMRegs; void ich9_pm_init(PCIDevice *lpc_pci, ICH9LPCPMRegs *pm, diff --git a/include/hw/acpi/pcihp.h b/include/hw/acpi/pcihp.h new file mode 100644 index 0000000000..6230e60954 --- /dev/null +++ b/include/hw/acpi/pcihp.h @@ -0,0 +1,72 @@ +/* + * QEMU<->ACPI BIOS PCI hotplug interface + * + * QEMU supports PCI hotplug via ACPI. This module + * implements the interface between QEMU and the ACPI BIOS. + * Interface specification - see docs/specs/acpi_pci_hotplug.txt + * + * Copyright (c) 2013, Red Hat Inc, Michael S. Tsirkin (mst@redhat.com) + * Copyright (c) 2006 Fabrice Bellard + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License version 2 as published by the Free Software Foundation. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, see <http://www.gnu.org/licenses/> + * + * Contributions after 2012-01-13 are licensed under the terms of the + * GNU GPL, version 2 or (at your option) any later version. + */ + +#ifndef HW_ACPI_PCIHP_H +#define HW_ACPI_PCIHP_H + +#include <inttypes.h> +#include <qemu/typedefs.h> +#include "hw/pci/pci.h" /* for PCIHotplugState */ + +typedef struct AcpiPciHpPciStatus { + uint32_t up; /* deprecated, maintained for migration compatibility */ + uint32_t down; + uint32_t hotplug_enable; + uint32_t device_present; +} AcpiPciHpPciStatus; + +#define ACPI_PCIHP_PROP_BSEL "acpi-pcihp-bsel" +#define ACPI_PCIHP_MAX_HOTPLUG_BUS 256 + +typedef struct AcpiPciHpState { + AcpiPciHpPciStatus acpi_pcihp_pci_status[ACPI_PCIHP_MAX_HOTPLUG_BUS]; + uint32_t hotplug_select; + PCIBus *root; + MemoryRegion io; +} AcpiPciHpState; + +void acpi_pcihp_init(AcpiPciHpState *, PCIBus *root, + MemoryRegion *address_space_io); + +/* Invoke on device hotplug */ +int acpi_pcihp_device_hotplug(AcpiPciHpState *, PCIDevice *, + PCIHotplugState state); + +/* Called on reset */ +void acpi_pcihp_reset(AcpiPciHpState *s); + +extern const VMStateDescription vmstate_acpi_pcihp_pci_status; + +#define VMSTATE_PCI_HOTPLUG(pcihp, state, test_pcihp) \ + VMSTATE_UINT32_TEST(pcihp.hotplug_select, state, \ + test_pcihp), \ + VMSTATE_STRUCT_ARRAY_TEST(pcihp.acpi_pcihp_pci_status, state, \ + ACPI_PCIHP_MAX_HOTPLUG_BUS, \ + test_pcihp, 1, \ + vmstate_acpi_pcihp_pci_status, \ + AcpiPciHpPciStatus) + +#endif diff --git a/include/hw/cris/etraxfs.h b/include/hw/cris/etraxfs.h index ab30559c79..73a6134c1e 100644 --- a/include/hw/cris/etraxfs.h +++ b/include/hw/cris/etraxfs.h @@ -28,8 +28,6 @@ #include "net/net.h" #include "hw/cris/etraxfs_dma.h" -qemu_irq *cris_pic_init_cpu(CPUCRISState *env); - /* Instantiate an ETRAXFS Ethernet MAC. */ static inline DeviceState * etraxfs_eth_init(NICInfo *nd, hwaddr base, int phyaddr, diff --git a/include/hw/i386/pc.h b/include/hw/i386/pc.h index eb3da964f0..3e1e81b27b 100644 --- a/include/hw/i386/pc.h +++ b/include/hw/i386/pc.h @@ -35,7 +35,7 @@ typedef struct PcPciInfo { struct PcGuestInfo { bool has_pci_info; bool isapc_ram_fw; - hwaddr ram_size; + hwaddr ram_size, ram_size_below_4g; unsigned apic_id_limit; bool apic_xrupt_override; uint64_t numa_nodes; @@ -241,6 +241,7 @@ uint16_t pvpanic_port(void); int e820_add_entry(uint64_t, uint64_t, uint32_t); #define PC_Q35_COMPAT_1_7 \ + PC_COMPAT_1_7, \ {\ .driver = "hpet",\ .property = HPET_INTCAP,\ @@ -259,7 +260,20 @@ int e820_add_entry(uint64_t, uint64_t, uint32_t); PC_COMPAT_1_4, \ PC_Q35_COMPAT_1_5 +#define PC_COMPAT_1_7 \ + {\ + .driver = TYPE_USB_DEVICE,\ + .property = "msos-desc",\ + .value = "no",\ + },\ + {\ + .driver = "PIIX4_PM",\ + .property = "acpi-pci-hotplug-with-bridge-support",\ + .value = "off",\ + } + #define PC_COMPAT_1_6 \ + PC_COMPAT_1_7, \ {\ .driver = "e1000",\ .property = "mitigation",\ diff --git a/include/hw/intc/arm_gic_common.h b/include/hw/intc/arm_gic_common.h index 0d232dfb67..8a2aa00cee 100644 --- a/include/hw/intc/arm_gic_common.h +++ b/include/hw/intc/arm_gic_common.h @@ -27,6 +27,7 @@ #define GIC_MAXIRQ 1020 /* First 32 are private to each CPU (SGIs and PPIs). */ #define GIC_INTERNAL 32 +#define GIC_NR_SGIS 16 /* Maximum number of possible CPU interfaces, determined by GIC architecture */ #define GIC_NCPU 8 diff --git a/include/hw/isa/isa.h b/include/hw/isa/isa.h index fa45a5b094..e0c749f9e9 100644 --- a/include/hw/isa/isa.h +++ b/include/hw/isa/isa.h @@ -20,6 +20,13 @@ #define TYPE_ISA_BUS "ISA" #define ISA_BUS(obj) OBJECT_CHECK(ISABus, (obj), TYPE_ISA_BUS) +#define TYPE_APPLE_SMC "isa-applesmc" + +static inline bool applesmc_find(void) +{ + return object_resolve_path_type("", TYPE_APPLE_SMC, NULL); +} + typedef struct ISADeviceClass { DeviceClass parent_class; } ISADeviceClass; diff --git a/include/hw/pci/pci.h b/include/hw/pci/pci.h index 754b82de81..52523467b6 100644 --- a/include/hw/pci/pci.h +++ b/include/hw/pci/pci.h @@ -387,6 +387,20 @@ int pci_bus_num(PCIBus *s); void pci_for_each_device(PCIBus *bus, int bus_num, void (*fn)(PCIBus *bus, PCIDevice *d, void *opaque), void *opaque); +void pci_for_each_bus_depth_first(PCIBus *bus, + void *(*begin)(PCIBus *bus, void *parent_state), + void (*end)(PCIBus *bus, void *state), + void *parent_state); + +/* Use this wrapper when specific scan order is not required. */ +static inline +void pci_for_each_bus(PCIBus *bus, + void (*fn)(PCIBus *bus, void *opaque), + void *opaque) +{ + pci_for_each_bus_depth_first(bus, NULL, fn, opaque); +} + PCIBus *pci_find_primary_bus(void); PCIBus *pci_device_root_bus(const PCIDevice *d); const char *pci_root_bus_path(PCIDevice *dev); diff --git a/include/hw/usb.h b/include/hw/usb.h index 2a3ea0c92e..3ef7af7413 100644 --- a/include/hw/usb.h +++ b/include/hw/usb.h @@ -182,6 +182,7 @@ typedef struct USBDescIface USBDescIface; typedef struct USBDescEndpoint USBDescEndpoint; typedef struct USBDescOther USBDescOther; typedef struct USBDescString USBDescString; +typedef struct USBDescMSOS USBDescMSOS; struct USBDescString { uint8_t index; @@ -208,6 +209,8 @@ struct USBEndpoint { enum USBDeviceFlags { USB_DEV_FLAG_FULL_PATH, USB_DEV_FLAG_IS_HOST, + USB_DEV_FLAG_MSOS_DESC_ENABLE, + USB_DEV_FLAG_MSOS_DESC_IN_USE, }; /* definition of a USB device */ diff --git a/include/hw/xilinx.h b/include/hw/xilinx.h index 0c0251a2e9..9d6debe4d0 100644 --- a/include/hw/xilinx.h +++ b/include/hw/xilinx.h @@ -59,16 +59,13 @@ xilinx_axiethernet_init(DeviceState *dev, NICInfo *nd, StreamSlave *ds, StreamSlave *cs, hwaddr base, qemu_irq irq, int txmem, int rxmem) { - Error *errp = NULL; - qdev_set_nic_properties(dev, nd); qdev_prop_set_uint32(dev, "rxmem", rxmem); qdev_prop_set_uint32(dev, "txmem", txmem); object_property_set_link(OBJECT(dev), OBJECT(ds), - "axistream-connected", &errp); + "axistream-connected", &error_abort); object_property_set_link(OBJECT(dev), OBJECT(cs), - "axistream-control-connected", &errp); - assert_no_error(errp); + "axistream-control-connected", &error_abort); qdev_init_nofail(dev); sysbus_mmio_map(SYS_BUS_DEVICE(dev), 0, base); sysbus_connect_irq(SYS_BUS_DEVICE(dev), 0, irq); @@ -78,14 +75,11 @@ static inline void xilinx_axidma_init(DeviceState *dev, StreamSlave *ds, StreamSlave *cs, hwaddr base, qemu_irq irq, qemu_irq irq2, int freqhz) { - Error *errp = NULL; - qdev_prop_set_uint32(dev, "freqhz", freqhz); object_property_set_link(OBJECT(dev), OBJECT(ds), - "axistream-connected", &errp); + "axistream-connected", &error_abort); object_property_set_link(OBJECT(dev), OBJECT(cs), - "axistream-control-connected", &errp); - assert_no_error(errp); + "axistream-control-connected", &error_abort); qdev_init_nofail(dev); sysbus_mmio_map(SYS_BUS_DEVICE(dev), 0, base); diff --git a/include/migration/migration.h b/include/migration/migration.h index 140e6b471c..bfa3951a61 100644 --- a/include/migration/migration.h +++ b/include/migration/migration.h @@ -23,6 +23,17 @@ #include "qapi-types.h" #include "exec/cpu-common.h" +#define QEMU_VM_FILE_MAGIC 0x5145564d +#define QEMU_VM_FILE_VERSION_COMPAT 0x00000002 +#define QEMU_VM_FILE_VERSION 0x00000003 + +#define QEMU_VM_EOF 0x00 +#define QEMU_VM_SECTION_START 0x01 +#define QEMU_VM_SECTION_PART 0x02 +#define QEMU_VM_SECTION_END 0x03 +#define QEMU_VM_SECTION_FULL 0x04 +#define QEMU_VM_SUBSECTION 0x05 + struct MigrationParams { bool blk; bool shared; diff --git a/include/migration/qemu-file.h b/include/migration/qemu-file.h index 0f757fbeb6..a191fb6d8d 100644 --- a/include/migration/qemu-file.h +++ b/include/migration/qemu-file.h @@ -121,8 +121,11 @@ static inline void qemu_put_ubyte(QEMUFile *f, unsigned int v) void qemu_put_be16(QEMUFile *f, unsigned int v); void qemu_put_be32(QEMUFile *f, unsigned int v); void qemu_put_be64(QEMUFile *f, uint64_t v); +int qemu_peek_buffer(QEMUFile *f, uint8_t *buf, int size, size_t offset); int qemu_get_buffer(QEMUFile *f, uint8_t *buf, int size); +int qemu_peek_byte(QEMUFile *f, int offset); int qemu_get_byte(QEMUFile *f); +void qemu_file_skip(QEMUFile *f, int size); void qemu_update_position(QEMUFile *f, size_t size); static inline unsigned int qemu_get_ubyte(QEMUFile *f) @@ -141,6 +144,7 @@ void qemu_file_reset_rate_limit(QEMUFile *f); void qemu_file_set_rate_limit(QEMUFile *f, int64_t new_rate); int64_t qemu_file_get_rate_limit(QEMUFile *f); int qemu_file_get_error(QEMUFile *f); +void qemu_file_set_error(QEMUFile *f, int ret); void qemu_fflush(QEMUFile *f); static inline void qemu_put_be64s(QEMUFile *f, const uint64_t *pv) diff --git a/include/monitor/monitor.h b/include/monitor/monitor.h index 10fa0e390c..7e5f752b7a 100644 --- a/include/monitor/monitor.h +++ b/include/monitor/monitor.h @@ -5,7 +5,7 @@ #include "qapi/qmp/qerror.h" #include "qapi/qmp/qdict.h" #include "block/block.h" -#include "monitor/readline.h" +#include "qemu/readline.h" extern Monitor *cur_mon; extern Monitor *default_mon; @@ -93,6 +93,9 @@ int monitor_read_password(Monitor *mon, ReadLineFunc *readline_func, int qmp_qom_set(Monitor *mon, const QDict *qdict, QObject **ret); int qmp_qom_get(Monitor *mon, const QDict *qdict, QObject **ret); +int qmp_object_add(Monitor *mon, const QDict *qdict, QObject **ret); +void object_add(const char *type, const char *id, const QDict *qdict, + Visitor *v, Error **errp); AddfdInfo *monitor_fdset_add_fd(int fd, bool has_fdset_id, int64_t fdset_id, bool has_opaque, const char *opaque, diff --git a/include/qapi/error.h b/include/qapi/error.h index 7d4c6963d3..c0f0c3b432 100644 --- a/include/qapi/error.h +++ b/include/qapi/error.h @@ -95,4 +95,10 @@ void error_propagate(Error **dst_err, Error *local_err); */ void error_free(Error *err); +/** + * If passed to error_set and friends, abort(). + */ + +extern Error *error_abort; + #endif diff --git a/include/qapi/qmp/qdict.h b/include/qapi/qmp/qdict.h index 5cefd8022a..1ddf97b1c3 100644 --- a/include/qapi/qmp/qdict.h +++ b/include/qapi/qmp/qdict.h @@ -68,5 +68,6 @@ QDict *qdict_clone_shallow(const QDict *src); void qdict_flatten(QDict *qdict); void qdict_extract_subqdict(QDict *src, QDict **dst, const char *start); +void qdict_array_split(QDict *src, QList **dst); #endif /* QDICT_H */ diff --git a/include/qapi/qmp/qerror.h b/include/qapi/qmp/qerror.h index c30c2f6d7a..73c67b70c2 100644 --- a/include/qapi/qmp/qerror.h +++ b/include/qapi/qmp/qerror.h @@ -29,7 +29,6 @@ typedef struct QError { QString *qerror_human(const QError *qerror); void qerror_report(ErrorClass err_class, const char *fmt, ...) GCC_FMT_ATTR(2, 3); void qerror_report_err(Error *err); -void assert_no_error(Error *err); /* * QError class list diff --git a/include/qapi/visitor.h b/include/qapi/visitor.h index 48a2a2edfd..29da211b47 100644 --- a/include/qapi/visitor.h +++ b/include/qapi/visitor.h @@ -13,6 +13,7 @@ #ifndef QAPI_VISITOR_CORE_H #define QAPI_VISITOR_CORE_H +#include "qemu/typedefs.h" #include "qapi/qmp/qobject.h" #include "qapi/error.h" #include <stdlib.h> @@ -26,8 +27,6 @@ typedef struct GenericList struct GenericList *next; } GenericList; -typedef struct Visitor Visitor; - void visit_start_handle(Visitor *v, void **obj, const char *kind, const char *name, Error **errp); void visit_end_handle(Visitor *v, Error **errp); diff --git a/include/qemu-io.h b/include/qemu-io.h index a418b46a40..7e7c07c09b 100644 --- a/include/qemu-io.h +++ b/include/qemu-io.h @@ -42,5 +42,8 @@ bool qemuio_command(BlockDriverState *bs, const char *cmd); void qemuio_add_command(const cmdinfo_t *ci); int qemuio_command_usage(const cmdinfo_t *ci); +void qemuio_complete_command(const char *input, + void (*fn)(const char *cmd, void *opaque), + void *opaque); #endif /* QEMU_IO_H */ diff --git a/include/qemu/bitmap.h b/include/qemu/bitmap.h index 308bbb71e9..1babd5d812 100644 --- a/include/qemu/bitmap.h +++ b/include/qemu/bitmap.h @@ -31,7 +31,7 @@ * bitmap_andnot(dst, src1, src2, nbits) *dst = *src1 & ~(*src2) * bitmap_complement(dst, src, nbits) *dst = ~(*src) * bitmap_equal(src1, src2, nbits) Are *src1 and *src2 equal? - * bitmap_intersects(src1, src2, nbits) Do *src1 and *src2 overlap? + * bitmap_intersects(src1, src2, nbits) Do *src1 and *src2 overlap? * bitmap_empty(src, nbits) Are all bits zero in *src? * bitmap_full(src, nbits) Are all bits set in *src? * bitmap_set(dst, pos, nbits) Set specified bit area @@ -62,71 +62,71 @@ ) #define DECLARE_BITMAP(name,bits) \ - unsigned long name[BITS_TO_LONGS(bits)] + unsigned long name[BITS_TO_LONGS(bits)] #define small_nbits(nbits) \ - ((nbits) <= BITS_PER_LONG) + ((nbits) <= BITS_PER_LONG) -int slow_bitmap_empty(const unsigned long *bitmap, int bits); -int slow_bitmap_full(const unsigned long *bitmap, int bits); +int slow_bitmap_empty(const unsigned long *bitmap, long bits); +int slow_bitmap_full(const unsigned long *bitmap, long bits); int slow_bitmap_equal(const unsigned long *bitmap1, - const unsigned long *bitmap2, int bits); + const unsigned long *bitmap2, long bits); void slow_bitmap_complement(unsigned long *dst, const unsigned long *src, - int bits); + long bits); void slow_bitmap_shift_right(unsigned long *dst, - const unsigned long *src, int shift, int bits); + const unsigned long *src, int shift, long bits); void slow_bitmap_shift_left(unsigned long *dst, - const unsigned long *src, int shift, int bits); + const unsigned long *src, int shift, long bits); int slow_bitmap_and(unsigned long *dst, const unsigned long *bitmap1, - const unsigned long *bitmap2, int bits); + const unsigned long *bitmap2, long bits); void slow_bitmap_or(unsigned long *dst, const unsigned long *bitmap1, - const unsigned long *bitmap2, int bits); + const unsigned long *bitmap2, long bits); void slow_bitmap_xor(unsigned long *dst, const unsigned long *bitmap1, - const unsigned long *bitmap2, int bits); + const unsigned long *bitmap2, long bits); int slow_bitmap_andnot(unsigned long *dst, const unsigned long *bitmap1, - const unsigned long *bitmap2, int bits); + const unsigned long *bitmap2, long bits); int slow_bitmap_intersects(const unsigned long *bitmap1, - const unsigned long *bitmap2, int bits); + const unsigned long *bitmap2, long bits); -static inline unsigned long *bitmap_new(int nbits) +static inline unsigned long *bitmap_new(long nbits) { - int len = BITS_TO_LONGS(nbits) * sizeof(unsigned long); + long len = BITS_TO_LONGS(nbits) * sizeof(unsigned long); return g_malloc0(len); } -static inline void bitmap_zero(unsigned long *dst, int nbits) +static inline void bitmap_zero(unsigned long *dst, long nbits) { if (small_nbits(nbits)) { *dst = 0UL; } else { - int len = BITS_TO_LONGS(nbits) * sizeof(unsigned long); + long len = BITS_TO_LONGS(nbits) * sizeof(unsigned long); memset(dst, 0, len); } } -static inline void bitmap_fill(unsigned long *dst, int nbits) +static inline void bitmap_fill(unsigned long *dst, long nbits) { size_t nlongs = BITS_TO_LONGS(nbits); if (!small_nbits(nbits)) { - int len = (nlongs - 1) * sizeof(unsigned long); + long len = (nlongs - 1) * sizeof(unsigned long); memset(dst, 0xff, len); } dst[nlongs - 1] = BITMAP_LAST_WORD_MASK(nbits); } static inline void bitmap_copy(unsigned long *dst, const unsigned long *src, - int nbits) + long nbits) { if (small_nbits(nbits)) { *dst = *src; } else { - int len = BITS_TO_LONGS(nbits) * sizeof(unsigned long); + long len = BITS_TO_LONGS(nbits) * sizeof(unsigned long); memcpy(dst, src, len); } } static inline int bitmap_and(unsigned long *dst, const unsigned long *src1, - const unsigned long *src2, int nbits) + const unsigned long *src2, long nbits) { if (small_nbits(nbits)) { return (*dst = *src1 & *src2) != 0; @@ -135,7 +135,7 @@ static inline int bitmap_and(unsigned long *dst, const unsigned long *src1, } static inline void bitmap_or(unsigned long *dst, const unsigned long *src1, - const unsigned long *src2, int nbits) + const unsigned long *src2, long nbits) { if (small_nbits(nbits)) { *dst = *src1 | *src2; @@ -145,7 +145,7 @@ static inline void bitmap_or(unsigned long *dst, const unsigned long *src1, } static inline void bitmap_xor(unsigned long *dst, const unsigned long *src1, - const unsigned long *src2, int nbits) + const unsigned long *src2, long nbits) { if (small_nbits(nbits)) { *dst = *src1 ^ *src2; @@ -155,7 +155,7 @@ static inline void bitmap_xor(unsigned long *dst, const unsigned long *src1, } static inline int bitmap_andnot(unsigned long *dst, const unsigned long *src1, - const unsigned long *src2, int nbits) + const unsigned long *src2, long nbits) { if (small_nbits(nbits)) { return (*dst = *src1 & ~(*src2)) != 0; @@ -163,8 +163,9 @@ static inline int bitmap_andnot(unsigned long *dst, const unsigned long *src1, return slow_bitmap_andnot(dst, src1, src2, nbits); } -static inline void bitmap_complement(unsigned long *dst, const unsigned long *src, - int nbits) +static inline void bitmap_complement(unsigned long *dst, + const unsigned long *src, + long nbits) { if (small_nbits(nbits)) { *dst = ~(*src) & BITMAP_LAST_WORD_MASK(nbits); @@ -174,7 +175,7 @@ static inline void bitmap_complement(unsigned long *dst, const unsigned long *sr } static inline int bitmap_equal(const unsigned long *src1, - const unsigned long *src2, int nbits) + const unsigned long *src2, long nbits) { if (small_nbits(nbits)) { return ! ((*src1 ^ *src2) & BITMAP_LAST_WORD_MASK(nbits)); @@ -183,7 +184,7 @@ static inline int bitmap_equal(const unsigned long *src1, } } -static inline int bitmap_empty(const unsigned long *src, int nbits) +static inline int bitmap_empty(const unsigned long *src, long nbits) { if (small_nbits(nbits)) { return ! (*src & BITMAP_LAST_WORD_MASK(nbits)); @@ -192,7 +193,7 @@ static inline int bitmap_empty(const unsigned long *src, int nbits) } } -static inline int bitmap_full(const unsigned long *src, int nbits) +static inline int bitmap_full(const unsigned long *src, long nbits) { if (small_nbits(nbits)) { return ! (~(*src) & BITMAP_LAST_WORD_MASK(nbits)); @@ -202,7 +203,7 @@ static inline int bitmap_full(const unsigned long *src, int nbits) } static inline int bitmap_intersects(const unsigned long *src1, - const unsigned long *src2, int nbits) + const unsigned long *src2, long nbits) { if (small_nbits(nbits)) { return ((*src1 & *src2) & BITMAP_LAST_WORD_MASK(nbits)) != 0; @@ -211,12 +212,21 @@ static inline int bitmap_intersects(const unsigned long *src1, } } -void bitmap_set(unsigned long *map, int i, int len); -void bitmap_clear(unsigned long *map, int start, int nr); +void bitmap_set(unsigned long *map, long i, long len); +void bitmap_clear(unsigned long *map, long start, long nr); unsigned long bitmap_find_next_zero_area(unsigned long *map, - unsigned long size, - unsigned long start, - unsigned int nr, - unsigned long align_mask); + unsigned long size, + unsigned long start, + unsigned long nr, + unsigned long align_mask); + +static inline unsigned long *bitmap_zero_extend(unsigned long *old, + long old_nbits, long new_nbits) +{ + long new_len = BITS_TO_LONGS(new_nbits) * sizeof(unsigned long); + unsigned long *new = g_realloc(old, new_len); + bitmap_clear(new, old_nbits, new_nbits - old_nbits); + return new; +} #endif /* BITMAP_H */ diff --git a/include/qemu/bitops.h b/include/qemu/bitops.h index 304c90c2b4..340b1e73bd 100644 --- a/include/qemu/bitops.h +++ b/include/qemu/bitops.h @@ -28,7 +28,7 @@ * @nr: the bit to set * @addr: the address to start counting from */ -static inline void set_bit(int nr, unsigned long *addr) +static inline void set_bit(long nr, unsigned long *addr) { unsigned long mask = BIT_MASK(nr); unsigned long *p = addr + BIT_WORD(nr); @@ -41,7 +41,7 @@ static inline void set_bit(int nr, unsigned long *addr) * @nr: Bit to clear * @addr: Address to start counting from */ -static inline void clear_bit(int nr, unsigned long *addr) +static inline void clear_bit(long nr, unsigned long *addr) { unsigned long mask = BIT_MASK(nr); unsigned long *p = addr + BIT_WORD(nr); @@ -54,7 +54,7 @@ static inline void clear_bit(int nr, unsigned long *addr) * @nr: Bit to change * @addr: Address to start counting from */ -static inline void change_bit(int nr, unsigned long *addr) +static inline void change_bit(long nr, unsigned long *addr) { unsigned long mask = BIT_MASK(nr); unsigned long *p = addr + BIT_WORD(nr); @@ -67,7 +67,7 @@ static inline void change_bit(int nr, unsigned long *addr) * @nr: Bit to set * @addr: Address to count from */ -static inline int test_and_set_bit(int nr, unsigned long *addr) +static inline int test_and_set_bit(long nr, unsigned long *addr) { unsigned long mask = BIT_MASK(nr); unsigned long *p = addr + BIT_WORD(nr); @@ -82,7 +82,7 @@ static inline int test_and_set_bit(int nr, unsigned long *addr) * @nr: Bit to clear * @addr: Address to count from */ -static inline int test_and_clear_bit(int nr, unsigned long *addr) +static inline int test_and_clear_bit(long nr, unsigned long *addr) { unsigned long mask = BIT_MASK(nr); unsigned long *p = addr + BIT_WORD(nr); @@ -97,7 +97,7 @@ static inline int test_and_clear_bit(int nr, unsigned long *addr) * @nr: Bit to change * @addr: Address to count from */ -static inline int test_and_change_bit(int nr, unsigned long *addr) +static inline int test_and_change_bit(long nr, unsigned long *addr) { unsigned long mask = BIT_MASK(nr); unsigned long *p = addr + BIT_WORD(nr); @@ -112,7 +112,7 @@ static inline int test_and_change_bit(int nr, unsigned long *addr) * @nr: bit number to test * @addr: Address to start counting from */ -static inline int test_bit(int nr, const unsigned long *addr) +static inline int test_bit(long nr, const unsigned long *addr) { return 1UL & (addr[BIT_WORD(nr)] >> (nr & (BITS_PER_LONG-1))); } diff --git a/include/qemu/config-file.h b/include/qemu/config-file.h index 508428ff32..dbd97c4bdb 100644 --- a/include/qemu/config-file.h +++ b/include/qemu/config-file.h @@ -4,6 +4,7 @@ #include <stdio.h> #include "qemu/option.h" #include "qapi/error.h" +#include "qapi/qmp/qdict.h" QemuOptsList *qemu_find_opts(const char *group); QemuOptsList *qemu_find_opts_err(const char *group, Error **errp); @@ -18,6 +19,11 @@ int qemu_config_parse(FILE *fp, QemuOptsList **lists, const char *fname); int qemu_read_config_file(const char *filename); +/* Parse QDict options as a replacement for a config file (allowing multiple + enumerated (0..(n-1)) configuration "sections") */ +void qemu_config_parse_qdict(QDict *options, QemuOptsList **lists, + Error **errp); + /* Read default QEMU config files */ int qemu_read_default_config_files(bool userconfig); diff --git a/include/qemu/option.h b/include/qemu/option.h index 5c0c6dd294..3ea871a3ba 100644 --- a/include/qemu/option.h +++ b/include/qemu/option.h @@ -136,7 +136,6 @@ int qemu_opt_foreach(QemuOpts *opts, qemu_opt_loopfunc func, void *opaque, QemuOpts *qemu_opts_find(QemuOptsList *list, const char *id); QemuOpts *qemu_opts_create(QemuOptsList *list, const char *id, int fail_if_exists, Error **errp); -QemuOpts *qemu_opts_create_nofail(QemuOptsList *list); void qemu_opts_reset(QemuOptsList *list); void qemu_opts_loc_restore(QemuOpts *opts); int qemu_opts_set(QemuOptsList *list, const char *id, diff --git a/include/qemu/osdep.h b/include/qemu/osdep.h index b3e2b6d8ea..eac7172bcb 100644 --- a/include/qemu/osdep.h +++ b/include/qemu/osdep.h @@ -240,4 +240,6 @@ static inline void qemu_init_auxval(char **envp) { } void qemu_init_auxval(char **envp); #endif +void qemu_set_tty_echo(int fd, bool echo); + #endif diff --git a/include/monitor/readline.h b/include/qemu/readline.h index 0faf6e1db7..a89fe4a9a9 100644 --- a/include/monitor/readline.h +++ b/include/qemu/readline.h @@ -1,14 +1,15 @@ #ifndef READLINE_H #define READLINE_H -#include "qemu-common.h" - #define READLINE_CMD_BUF_SIZE 4095 #define READLINE_MAX_CMDS 64 #define READLINE_MAX_COMPLETIONS 256 -typedef void ReadLineFunc(Monitor *mon, const char *str, void *opaque); -typedef void ReadLineCompletionFunc(Monitor *mon, +typedef void ReadLinePrintfFunc(void *opaque, const char *fmt, ...); +typedef void ReadLineFlushFunc(void *opaque); +typedef void ReadLineFunc(void *opaque, const char *str, + void *readline_opaque); +typedef void ReadLineCompletionFunc(void *opaque, const char *cmdline); typedef struct ReadLineState { @@ -35,7 +36,10 @@ typedef struct ReadLineState { void *readline_opaque; int read_password; char prompt[256]; - Monitor *mon; + + ReadLinePrintfFunc *printf_func; + ReadLineFlushFunc *flush_func; + void *opaque; } ReadLineState; void readline_add_completion(ReadLineState *rs, const char *str); @@ -46,11 +50,13 @@ const char *readline_get_history(ReadLineState *rs, unsigned int index); void readline_handle_byte(ReadLineState *rs, int ch); void readline_start(ReadLineState *rs, const char *prompt, int read_password, - ReadLineFunc *readline_func, void *opaque); + ReadLineFunc *readline_func, void *readline_opaque); void readline_restart(ReadLineState *rs); void readline_show_prompt(ReadLineState *rs); -ReadLineState *readline_init(Monitor *mon, +ReadLineState *readline_init(ReadLinePrintfFunc *printf_func, + ReadLineFlushFunc *flush_func, + void *opaque, ReadLineCompletionFunc *completion_finder); #endif /* !READLINE_H */ diff --git a/include/qemu/timer.h b/include/qemu/timer.h index 5afcffc3f9..7f9a074c2a 100644 --- a/include/qemu/timer.h +++ b/include/qemu/timer.h @@ -405,7 +405,7 @@ int64_t timerlistgroup_deadline_ns(QEMUTimerListGroup *tlg); * timer_init: * @ts: the timer to be initialised * @timer_list: the timer list to attach the timer to - * @scale: the scale value for the tiemr + * @scale: the scale value for the timer * @cb: the callback to be called when the timer expires * @opaque: the opaque pointer to be passed to the callback * @@ -422,7 +422,7 @@ void timer_init(QEMUTimer *ts, /** * timer_new_tl: * @timer_list: the timer list to attach the timer to - * @scale: the scale value for the tiemr + * @scale: the scale value for the timer * @cb: the callback to be called when the timer expires * @opaque: the opaque pointer to be passed to the callback * @@ -447,7 +447,7 @@ static inline QEMUTimer *timer_new_tl(QEMUTimerList *timer_list, /** * timer_new: * @type: the clock type to use - * @scale: the scale value for the tiemr + * @scale: the scale value for the timer * @cb: the callback to be called when the timer expires * @opaque: the opaque pointer to be passed to the callback * diff --git a/include/qemu/typedefs.h b/include/qemu/typedefs.h index a4c1b84d69..45244960b5 100644 --- a/include/qemu/typedefs.h +++ b/include/qemu/typedefs.h @@ -10,6 +10,8 @@ typedef struct QEMUBH QEMUBH; typedef struct AioContext AioContext; +typedef struct Visitor Visitor; + struct Monitor; typedef struct Monitor Monitor; typedef struct MigrationParams MigrationParams; diff --git a/include/qom/object_interfaces.h b/include/qom/object_interfaces.h new file mode 100644 index 0000000000..b7922833e1 --- /dev/null +++ b/include/qom/object_interfaces.h @@ -0,0 +1,62 @@ +#ifndef OBJECT_INTERFACES_H +#define OBJECT_INTERFACES_H + +#include "qom/object.h" + +#define TYPE_USER_CREATABLE "user-creatable" + +#define USER_CREATABLE_CLASS(klass) \ + OBJECT_CLASS_CHECK(UserCreatableClass, (klass), \ + TYPE_USER_CREATABLE) +#define USER_CREATABLE_GET_CLASS(obj) \ + OBJECT_GET_CLASS(UserCreatableClass, (obj), \ + TYPE_USER_CREATABLE) +#define USER_CREATABLE(obj) \ + INTERFACE_CHECK(UserCreatable, (obj), \ + TYPE_USER_CREATABLE) + + +typedef struct UserCreatable { + /* <private> */ + Object Parent; +} UserCreatable; + +/** + * UserCreatableClass: + * @parent_class: the base class + * @complete: callback to be called after @obj's properties are set. + * + * Interface is designed to work with -object/object-add/object_add + * commands. + * Interface is mandatory for objects that are designed to be user + * creatable (i.e. -object/object-add/object_add, will accept only + * objects that inherit this interface). + * + * Interface also provides an optional ability to do the second + * stage * initialization of the object after its properties were + * set. + * + * For objects created without using -object/object-add/object_add, + * @user_creatable_complete() wrapper should be called manually if + * object's type implements USER_CREATABLE interface and needs + * complete() callback to be called. + */ +typedef struct UserCreatableClass { + /* <private> */ + InterfaceClass parent_class; + + /* <public> */ + void (*complete)(UserCreatable *uc, Error **errp); +} UserCreatableClass; + +/** + * user_creatable_complete: + * @obj: the object whose complete() method is called if defined + * @errp: if an error occurs, a pointer to an area to store the error + * + * Wrapper to call complete() method if one of types it's inherited + * from implements USER_CREATABLE interface, otherwise the call does + * nothing. + */ +void user_creatable_complete(Object *obj, Error **errp); +#endif diff --git a/include/sysemu/rng.h b/include/sysemu/rng.h index 7637fac52d..0a27c9b88c 100644 --- a/include/sysemu/rng.h +++ b/include/sysemu/rng.h @@ -79,15 +79,4 @@ void rng_backend_request_entropy(RngBackend *s, size_t size, * to stop tracking any request. */ void rng_backend_cancel_requests(RngBackend *s); - -/** - * rng_backend_open: - * @s: the backend to open - * @errp: a pointer to return the #Error object if an error occurs. - * - * This function will open the backend if it is not already open. Calling this - * function on an already opened backend will not result in an error. - */ -void rng_backend_open(RngBackend *s, Error **errp); - #endif |