mirror of
https://github.com/Motorhead1991/qemu.git
synced 2025-08-05 08:43:55 -06:00
migration/next for 20151110
-----BEGIN PGP SIGNATURE----- Version: GnuPG v1 iQIcBAABCAAGBQJWQf3eAAoJEPSH7xhYctcjqnsP/iIvpP9wfHxNCFWy3o9pjeJm s5SEyA+/Rzef0+eoUlETyuWeivZA40lyhYzCRBZfjAshLiAjGl2T+/S+gkwNB4Na IMgYfdQ6EzGzZIUgskqFcdHF0PkYKsFjQN9OnDdkVDG7WW20MEf7UmhgEDMZ2fnA 4o2e/jPcZSF4v4J6/Dl1J6pev50OBwoGclFaVIRA5U3Me9/+0C8U9nodrWvRW1Yp 3bLxA3/Sr8pjApap+gYADuAMq/C85H0nxU1bnUZEdJc5KyLiFC1hqLC7zQS0+FMW 6wdPULWeqf03enFONeiRa2TGlYP0kPFDrdmz8HGQgJ5PgjtlkUdmDK8flTLnoN7z 7yX9C8qF/afe/FjCyCxphEM1NBmu8d/8LjoNpxZOY4AKhm4YVWfRLJCrePBilx3l qLbeIBTjjcq59JYnj0cqIamLRf7U9CvFxb6dVT/ejX8aqvH1a1wNfgMgn5Vh9ICv PmnAHO1gaYthhd76uHASMSE9v/neY6xa8r+f3VP8RveC/SmriAtkTMa/VpL8Bp0B O5ERqQg27RjUbfKidAUcrlC1jb4pWwX48Lh3yo6cSrCUGBiVoESfEbpgCfZQQDnD l8tapPZX14y1wUN5Rn9HjFq11AN0MKGlRaTA5KMzL3eaAExKWwNlAV6tawQnsghQ NOzZfechjlENjpfJJbc2 =tlQv -----END PGP SIGNATURE----- Merge remote-tracking branch 'remotes/juanquintela/tags/migration/20151110' into staging migration/next for 20151110 # gpg: Signature made Tue 10 Nov 2015 14:23:26 GMT using RSA key ID 5872D723 # gpg: Good signature from "Juan Quintela <quintela@redhat.com>" # gpg: aka "Juan Quintela <quintela@trasno.org>" * remotes/juanquintela/tags/migration/20151110: (57 commits) migration: qemu_savevm_state_cleanup becomes mandatory operation Inhibit ballooning during postcopy Disable mlock around incoming postcopy End of migration for postcopy Postcopy: Mark nohugepage before discard postcopy: Wire up loadvm_postcopy_handle_ commands Start up a postcopy/listener thread ready for incoming page data Postcopy; Handle userfault requests Round up RAMBlock sizes to host page sizes Host page!=target page: Cleanup bitmaps Don't iterate on precopy-only devices during postcopy Don't sync dirty bitmaps in postcopy postcopy: Check order of received target pages Postcopy: Use helpers to map pages during migration postcopy_ram.c: place_page and helpers Page request: Consume pages off the post-copy queue Page request: Process incoming page request Page request: Add MIG_RP_MSG_REQ_PAGES reverse command Postcopy: End of iteration Postcopy: Postcopy startup in migration thread ... Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
This commit is contained in:
commit
a77067f6ac
35 changed files with 4208 additions and 291 deletions
|
@ -64,8 +64,12 @@ typedef uint32_t CPUReadMemoryFunc(void *opaque, hwaddr addr);
|
|||
void qemu_ram_remap(ram_addr_t addr, ram_addr_t length);
|
||||
/* This should not be used by devices. */
|
||||
MemoryRegion *qemu_ram_addr_from_host(void *ptr, ram_addr_t *ram_addr);
|
||||
RAMBlock *qemu_ram_block_by_name(const char *name);
|
||||
RAMBlock *qemu_ram_block_from_host(void *ptr, bool round_offset,
|
||||
ram_addr_t *ram_addr, ram_addr_t *offset);
|
||||
void qemu_ram_set_idstr(ram_addr_t addr, const char *name, DeviceState *dev);
|
||||
void qemu_ram_unset_idstr(ram_addr_t addr);
|
||||
const char *qemu_ram_get_idstr(RAMBlock *rb);
|
||||
|
||||
void cpu_physical_memory_rw(hwaddr addr, uint8_t *buf,
|
||||
int len, int is_write);
|
||||
|
|
|
@ -72,7 +72,6 @@ void restore_state_to_opc(CPUArchState *env, struct TranslationBlock *tb,
|
|||
|
||||
void cpu_gen_init(void);
|
||||
bool cpu_restore_state(CPUState *cpu, uintptr_t searched_pc);
|
||||
void page_size_init(void);
|
||||
|
||||
void QEMU_NORETURN cpu_resume_from_signal(CPUState *cpu, void *puc);
|
||||
void QEMU_NORETURN cpu_io_recompile(CPUState *cpu, uintptr_t retaddr);
|
||||
|
|
|
@ -22,8 +22,6 @@
|
|||
#ifndef CONFIG_USER_ONLY
|
||||
#include "hw/xen/xen.h"
|
||||
|
||||
typedef struct RAMBlock RAMBlock;
|
||||
|
||||
struct RAMBlock {
|
||||
struct rcu_head rcu;
|
||||
struct MemoryRegion *mr;
|
||||
|
|
|
@ -35,6 +35,7 @@
|
|||
#define QEMU_VM_SUBSECTION 0x05
|
||||
#define QEMU_VM_VMDESCRIPTION 0x06
|
||||
#define QEMU_VM_CONFIGURATION 0x07
|
||||
#define QEMU_VM_COMMAND 0x08
|
||||
#define QEMU_VM_SECTION_FOOTER 0x7e
|
||||
|
||||
struct MigrationParams {
|
||||
|
@ -42,13 +43,67 @@ struct MigrationParams {
|
|||
bool shared;
|
||||
};
|
||||
|
||||
typedef struct MigrationState MigrationState;
|
||||
/* Messages sent on the return path from destination to source */
|
||||
enum mig_rp_message_type {
|
||||
MIG_RP_MSG_INVALID = 0, /* Must be 0 */
|
||||
MIG_RP_MSG_SHUT, /* sibling will not send any more RP messages */
|
||||
MIG_RP_MSG_PONG, /* Response to a PING; data (seq: be32 ) */
|
||||
|
||||
MIG_RP_MSG_REQ_PAGES_ID, /* data (start: be64, len: be32, id: string) */
|
||||
MIG_RP_MSG_REQ_PAGES, /* data (start: be64, len: be32) */
|
||||
|
||||
MIG_RP_MSG_MAX
|
||||
};
|
||||
|
||||
typedef QLIST_HEAD(, LoadStateEntry) LoadStateEntry_Head;
|
||||
|
||||
/* The current postcopy state is read/set by postcopy_state_get/set
|
||||
* which update it atomically.
|
||||
* The state is updated as postcopy messages are received, and
|
||||
* in general only one thread should be writing to the state at any one
|
||||
* time, initially the main thread and then the listen thread;
|
||||
* Corner cases are where either thread finishes early and/or errors.
|
||||
* The state is checked as messages are received to ensure that
|
||||
* the source is sending us messages in the correct order.
|
||||
* The state is also used by the RAM reception code to know if it
|
||||
* has to place pages atomically, and the cleanup code at the end of
|
||||
* the main thread to know if it has to delay cleanup until the end
|
||||
* of postcopy.
|
||||
*/
|
||||
typedef enum {
|
||||
POSTCOPY_INCOMING_NONE = 0, /* Initial state - no postcopy */
|
||||
POSTCOPY_INCOMING_ADVISE,
|
||||
POSTCOPY_INCOMING_DISCARD,
|
||||
POSTCOPY_INCOMING_LISTENING,
|
||||
POSTCOPY_INCOMING_RUNNING,
|
||||
POSTCOPY_INCOMING_END
|
||||
} PostcopyState;
|
||||
|
||||
/* State for the incoming migration */
|
||||
struct MigrationIncomingState {
|
||||
QEMUFile *file;
|
||||
QEMUFile *from_src_file;
|
||||
|
||||
/*
|
||||
* Free at the start of the main state load, set as the main thread finishes
|
||||
* loading state.
|
||||
*/
|
||||
QemuEvent main_thread_load_event;
|
||||
|
||||
bool have_fault_thread;
|
||||
QemuThread fault_thread;
|
||||
QemuSemaphore fault_thread_sem;
|
||||
|
||||
bool have_listen_thread;
|
||||
QemuThread listen_thread;
|
||||
QemuSemaphore listen_thread_sem;
|
||||
|
||||
/* For the kernel to send us notifications */
|
||||
int userfault_fd;
|
||||
/* To tell the fault_thread to quit */
|
||||
int userfault_quit_fd;
|
||||
QEMUFile *to_src_file;
|
||||
QemuMutex rp_mutex; /* We send replies from multiple threads */
|
||||
void *postcopy_tmp_page;
|
||||
|
||||
/* See savevm.c */
|
||||
LoadStateEntry_Head loadvm_handlers;
|
||||
|
@ -58,6 +113,18 @@ MigrationIncomingState *migration_incoming_get_current(void);
|
|||
MigrationIncomingState *migration_incoming_state_new(QEMUFile *f);
|
||||
void migration_incoming_state_destroy(void);
|
||||
|
||||
/*
|
||||
* An outstanding page request, on the source, having been received
|
||||
* and queued
|
||||
*/
|
||||
struct MigrationSrcPageRequest {
|
||||
RAMBlock *rb;
|
||||
hwaddr offset;
|
||||
hwaddr len;
|
||||
|
||||
QSIMPLEQ_ENTRY(MigrationSrcPageRequest) next_req;
|
||||
};
|
||||
|
||||
struct MigrationState
|
||||
{
|
||||
int64_t bandwidth_limit;
|
||||
|
@ -70,6 +137,14 @@ struct MigrationState
|
|||
|
||||
int state;
|
||||
MigrationParams params;
|
||||
|
||||
/* State related to return path */
|
||||
struct {
|
||||
QEMUFile *from_dst_file;
|
||||
QemuThread rp_thread;
|
||||
bool error;
|
||||
} rp_state;
|
||||
|
||||
double mbps;
|
||||
int64_t total_time;
|
||||
int64_t downtime;
|
||||
|
@ -80,6 +155,18 @@ struct MigrationState
|
|||
int64_t xbzrle_cache_size;
|
||||
int64_t setup_time;
|
||||
int64_t dirty_sync_count;
|
||||
|
||||
/* Flag set once the migration has been asked to enter postcopy */
|
||||
bool start_postcopy;
|
||||
|
||||
/* Flag set once the migration thread is running (and needs joining) */
|
||||
bool migration_thread_running;
|
||||
|
||||
/* Queue of outstanding page requests from the destination */
|
||||
QemuMutex src_page_req_mutex;
|
||||
QSIMPLEQ_HEAD(src_page_requests, MigrationSrcPageRequest) src_page_requests;
|
||||
/* The RAMBlock used in the last src_page_request */
|
||||
RAMBlock *last_req_rb;
|
||||
};
|
||||
|
||||
void process_incoming_migration(QEMUFile *f);
|
||||
|
@ -116,9 +203,12 @@ int migrate_fd_close(MigrationState *s);
|
|||
|
||||
void add_migration_state_change_notifier(Notifier *notify);
|
||||
void remove_migration_state_change_notifier(Notifier *notify);
|
||||
MigrationState *migrate_init(const MigrationParams *params);
|
||||
bool migration_in_setup(MigrationState *);
|
||||
bool migration_has_finished(MigrationState *);
|
||||
bool migration_has_failed(MigrationState *);
|
||||
/* True if outgoing migration has entered postcopy phase */
|
||||
bool migration_in_postcopy(MigrationState *);
|
||||
MigrationState *migrate_get_current(void);
|
||||
|
||||
void migrate_compress_threads_create(void);
|
||||
|
@ -145,6 +235,13 @@ uint64_t xbzrle_mig_pages_cache_miss(void);
|
|||
double xbzrle_mig_cache_miss_rate(void);
|
||||
|
||||
void ram_handle_compressed(void *host, uint8_t ch, uint64_t size);
|
||||
void ram_debug_dump_bitmap(unsigned long *todump, bool expected);
|
||||
/* For outgoing discard bitmap */
|
||||
int ram_postcopy_send_discard_bitmap(MigrationState *ms);
|
||||
/* For incoming postcopy discard */
|
||||
int ram_discard_range(MigrationIncomingState *mis, const char *block_name,
|
||||
uint64_t start, size_t length);
|
||||
int ram_postcopy_incoming_init(MigrationIncomingState *mis);
|
||||
|
||||
/**
|
||||
* @migrate_add_blocker - prevent migration from proceeding
|
||||
|
@ -160,6 +257,7 @@ void migrate_add_blocker(Error *reason);
|
|||
*/
|
||||
void migrate_del_blocker(Error *reason);
|
||||
|
||||
bool migrate_postcopy_ram(void);
|
||||
bool migrate_zero_blocks(void);
|
||||
|
||||
bool migrate_auto_converge(void);
|
||||
|
@ -179,6 +277,17 @@ int migrate_compress_threads(void);
|
|||
int migrate_decompress_threads(void);
|
||||
bool migrate_use_events(void);
|
||||
|
||||
/* Sending on the return path - generic and then for each message type */
|
||||
void migrate_send_rp_message(MigrationIncomingState *mis,
|
||||
enum mig_rp_message_type message_type,
|
||||
uint16_t len, void *data);
|
||||
void migrate_send_rp_shut(MigrationIncomingState *mis,
|
||||
uint32_t value);
|
||||
void migrate_send_rp_pong(MigrationIncomingState *mis,
|
||||
uint32_t value);
|
||||
void migrate_send_rp_req_pages(MigrationIncomingState *mis, const char* rbname,
|
||||
ram_addr_t start, size_t len);
|
||||
|
||||
void ram_control_before_iterate(QEMUFile *f, uint64_t flags);
|
||||
void ram_control_after_iterate(QEMUFile *f, uint64_t flags);
|
||||
void ram_control_load_hook(QEMUFile *f, uint64_t flags, void *data);
|
||||
|
@ -204,4 +313,12 @@ void global_state_set_optional(void);
|
|||
void savevm_skip_configuration(void);
|
||||
int global_state_store(void);
|
||||
void global_state_store_running(void);
|
||||
|
||||
void flush_page_queue(MigrationState *ms);
|
||||
int ram_save_queue_pages(MigrationState *ms, const char *rbname,
|
||||
ram_addr_t start, ram_addr_t len);
|
||||
|
||||
PostcopyState postcopy_state_get(void);
|
||||
/* Set the state and return the old state */
|
||||
PostcopyState postcopy_state_set(PostcopyState new_state);
|
||||
#endif
|
||||
|
|
99
include/migration/postcopy-ram.h
Normal file
99
include/migration/postcopy-ram.h
Normal file
|
@ -0,0 +1,99 @@
|
|||
/*
|
||||
* Postcopy migration for RAM
|
||||
*
|
||||
* Copyright 2013 Red Hat, Inc. and/or its affiliates
|
||||
*
|
||||
* Authors:
|
||||
* Dave Gilbert <dgilbert@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 QEMU_POSTCOPY_RAM_H
|
||||
#define QEMU_POSTCOPY_RAM_H
|
||||
|
||||
/* Return true if the host supports everything we need to do postcopy-ram */
|
||||
bool postcopy_ram_supported_by_host(void);
|
||||
|
||||
/*
|
||||
* Make all of RAM sensitive to accesses to areas that haven't yet been written
|
||||
* and wire up anything necessary to deal with it.
|
||||
*/
|
||||
int postcopy_ram_enable_notify(MigrationIncomingState *mis);
|
||||
|
||||
/*
|
||||
* Initialise postcopy-ram, setting the RAM to a state where we can go into
|
||||
* postcopy later; must be called prior to any precopy.
|
||||
* called from ram.c's similarly named ram_postcopy_incoming_init
|
||||
*/
|
||||
int postcopy_ram_incoming_init(MigrationIncomingState *mis, size_t ram_pages);
|
||||
|
||||
/*
|
||||
* At the end of a migration where postcopy_ram_incoming_init was called.
|
||||
*/
|
||||
int postcopy_ram_incoming_cleanup(MigrationIncomingState *mis);
|
||||
|
||||
/*
|
||||
* Discard the contents of 'length' bytes from 'start'
|
||||
* We can assume that if we've been called postcopy_ram_hosttest returned true
|
||||
*/
|
||||
int postcopy_ram_discard_range(MigrationIncomingState *mis, uint8_t *start,
|
||||
size_t length);
|
||||
|
||||
/*
|
||||
* Userfault requires us to mark RAM as NOHUGEPAGE prior to discard
|
||||
* however leaving it until after precopy means that most of the precopy
|
||||
* data is still THPd
|
||||
*/
|
||||
int postcopy_ram_prepare_discard(MigrationIncomingState *mis);
|
||||
|
||||
/*
|
||||
* Called at the start of each RAMBlock by the bitmap code.
|
||||
* 'offset' is the bitmap offset of the named RAMBlock in the migration
|
||||
* bitmap.
|
||||
* Returns a new PDS
|
||||
*/
|
||||
PostcopyDiscardState *postcopy_discard_send_init(MigrationState *ms,
|
||||
unsigned long offset,
|
||||
const char *name);
|
||||
|
||||
/*
|
||||
* Called by the bitmap code for each chunk to discard.
|
||||
* May send a discard message, may just leave it queued to
|
||||
* be sent later.
|
||||
* @start,@length: a range of pages in the migration bitmap in the
|
||||
* RAM block passed to postcopy_discard_send_init() (length=1 is one page)
|
||||
*/
|
||||
void postcopy_discard_send_range(MigrationState *ms, PostcopyDiscardState *pds,
|
||||
unsigned long start, unsigned long length);
|
||||
|
||||
/*
|
||||
* Called at the end of each RAMBlock by the bitmap code.
|
||||
* Sends any outstanding discard messages, frees the PDS.
|
||||
*/
|
||||
void postcopy_discard_send_finish(MigrationState *ms,
|
||||
PostcopyDiscardState *pds);
|
||||
|
||||
/*
|
||||
* Place a page (from) at (host) efficiently
|
||||
* There are restrictions on how 'from' must be mapped, in general best
|
||||
* to use other postcopy_ routines to allocate.
|
||||
* returns 0 on success
|
||||
*/
|
||||
int postcopy_place_page(MigrationIncomingState *mis, void *host, void *from);
|
||||
|
||||
/*
|
||||
* Place a zero page at (host) atomically
|
||||
* returns 0 on success
|
||||
*/
|
||||
int postcopy_place_page_zero(MigrationIncomingState *mis, void *host);
|
||||
|
||||
/*
|
||||
* Allocate a page of memory that can be mapped at a later point in time
|
||||
* using postcopy_place_page
|
||||
* Returns: Pointer to allocated page
|
||||
*/
|
||||
void *postcopy_get_tmp_page(MigrationIncomingState *mis);
|
||||
|
||||
#endif
|
|
@ -88,6 +88,11 @@ typedef size_t (QEMURamSaveFunc)(QEMUFile *f, void *opaque,
|
|||
size_t size,
|
||||
uint64_t *bytes_sent);
|
||||
|
||||
/*
|
||||
* Return a QEMUFile for comms in the opposite direction
|
||||
*/
|
||||
typedef QEMUFile *(QEMURetPathFunc)(void *opaque);
|
||||
|
||||
/*
|
||||
* Stop any read or write (depending on flags) on the underlying
|
||||
* transport on the QEMUFile.
|
||||
|
@ -106,6 +111,7 @@ typedef struct QEMUFileOps {
|
|||
QEMURamHookFunc *after_ram_iterate;
|
||||
QEMURamHookFunc *hook_ram_load;
|
||||
QEMURamSaveFunc *save_page;
|
||||
QEMURetPathFunc *get_return_path;
|
||||
QEMUFileShutdownFunc *shut_down;
|
||||
} QEMUFileOps;
|
||||
|
||||
|
@ -163,9 +169,11 @@ void qemu_put_be32(QEMUFile *f, unsigned int v);
|
|||
void qemu_put_be64(QEMUFile *f, uint64_t v);
|
||||
size_t qemu_peek_buffer(QEMUFile *f, uint8_t **buf, size_t size, size_t offset);
|
||||
size_t qemu_get_buffer(QEMUFile *f, uint8_t *buf, size_t size);
|
||||
size_t qemu_get_buffer_in_place(QEMUFile *f, uint8_t **buf, size_t size);
|
||||
ssize_t qemu_put_compression_data(QEMUFile *f, const uint8_t *p, size_t size,
|
||||
int level);
|
||||
int qemu_put_qemu_file(QEMUFile *f_des, QEMUFile *f_src);
|
||||
|
||||
/*
|
||||
* Note that you can only peek continuous bytes from where the current pointer
|
||||
* is; you aren't guaranteed to be able to peak to +n bytes unless you've
|
||||
|
@ -194,7 +202,9 @@ 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);
|
||||
int qemu_file_shutdown(QEMUFile *f);
|
||||
QEMUFile *qemu_file_get_return_path(QEMUFile *f);
|
||||
void qemu_fflush(QEMUFile *f);
|
||||
void qemu_file_set_blocking(QEMUFile *f, bool block);
|
||||
|
||||
static inline void qemu_put_be64s(QEMUFile *f, const uint64_t *pv)
|
||||
{
|
||||
|
|
|
@ -40,7 +40,8 @@ typedef struct SaveVMHandlers {
|
|||
SaveStateHandler *save_state;
|
||||
|
||||
void (*cleanup)(void *opaque);
|
||||
int (*save_live_complete)(QEMUFile *f, void *opaque);
|
||||
int (*save_live_complete_postcopy)(QEMUFile *f, void *opaque);
|
||||
int (*save_live_complete_precopy)(QEMUFile *f, void *opaque);
|
||||
|
||||
/* This runs both outside and inside the iothread lock. */
|
||||
bool (*is_active)(void *opaque);
|
||||
|
@ -54,8 +55,9 @@ typedef struct SaveVMHandlers {
|
|||
|
||||
/* This runs outside the iothread lock! */
|
||||
int (*save_live_setup)(QEMUFile *f, void *opaque);
|
||||
uint64_t (*save_live_pending)(QEMUFile *f, void *opaque, uint64_t max_size);
|
||||
|
||||
void (*save_live_pending)(QEMUFile *f, void *opaque, uint64_t max_size,
|
||||
uint64_t *non_postcopiable_pending,
|
||||
uint64_t *postcopiable_pending);
|
||||
LoadStateHandler *load_state;
|
||||
} SaveVMHandlers;
|
||||
|
||||
|
|
|
@ -499,5 +499,6 @@ size_t buffer_find_nonzero_offset(const void *buf, size_t len);
|
|||
int parse_debug_env(const char *name, int max, int initial);
|
||||
|
||||
const char *qemu_ether_ntoa(const MACAddr *mac);
|
||||
void page_size_init(void);
|
||||
|
||||
#endif
|
||||
|
|
|
@ -139,6 +139,8 @@ void qemu_anon_ram_free(void *ptr, size_t size);
|
|||
|
||||
#if defined(CONFIG_MADVISE)
|
||||
|
||||
#include <sys/mman.h>
|
||||
|
||||
#define QEMU_MADV_WILLNEED MADV_WILLNEED
|
||||
#define QEMU_MADV_DONTNEED MADV_DONTNEED
|
||||
#ifdef MADV_DONTFORK
|
||||
|
@ -171,6 +173,11 @@ void qemu_anon_ram_free(void *ptr, size_t size);
|
|||
#else
|
||||
#define QEMU_MADV_HUGEPAGE QEMU_MADV_INVALID
|
||||
#endif
|
||||
#ifdef MADV_NOHUGEPAGE
|
||||
#define QEMU_MADV_NOHUGEPAGE MADV_NOHUGEPAGE
|
||||
#else
|
||||
#define QEMU_MADV_NOHUGEPAGE QEMU_MADV_INVALID
|
||||
#endif
|
||||
|
||||
#elif defined(CONFIG_POSIX_MADVISE)
|
||||
|
||||
|
@ -182,6 +189,7 @@ void qemu_anon_ram_free(void *ptr, size_t size);
|
|||
#define QEMU_MADV_DODUMP QEMU_MADV_INVALID
|
||||
#define QEMU_MADV_DONTDUMP QEMU_MADV_INVALID
|
||||
#define QEMU_MADV_HUGEPAGE QEMU_MADV_INVALID
|
||||
#define QEMU_MADV_NOHUGEPAGE QEMU_MADV_INVALID
|
||||
|
||||
#else /* no-op */
|
||||
|
||||
|
@ -193,6 +201,7 @@ void qemu_anon_ram_free(void *ptr, size_t size);
|
|||
#define QEMU_MADV_DODUMP QEMU_MADV_INVALID
|
||||
#define QEMU_MADV_DONTDUMP QEMU_MADV_INVALID
|
||||
#define QEMU_MADV_HUGEPAGE QEMU_MADV_INVALID
|
||||
#define QEMU_MADV_NOHUGEPAGE QEMU_MADV_INVALID
|
||||
|
||||
#endif
|
||||
|
||||
|
|
|
@ -44,6 +44,7 @@ typedef struct MemoryRegion MemoryRegion;
|
|||
typedef struct MemoryRegionSection MemoryRegionSection;
|
||||
typedef struct MigrationIncomingState MigrationIncomingState;
|
||||
typedef struct MigrationParams MigrationParams;
|
||||
typedef struct MigrationState MigrationState;
|
||||
typedef struct Monitor Monitor;
|
||||
typedef struct MouseTransformInfo MouseTransformInfo;
|
||||
typedef struct MSIMessage MSIMessage;
|
||||
|
@ -66,6 +67,7 @@ typedef struct PCMachineState PCMachineState;
|
|||
typedef struct PCMachineClass PCMachineClass;
|
||||
typedef struct PCMCIACardState PCMCIACardState;
|
||||
typedef struct PixelFormat PixelFormat;
|
||||
typedef struct PostcopyDiscardState PostcopyDiscardState;
|
||||
typedef struct PropertyInfo PropertyInfo;
|
||||
typedef struct Property Property;
|
||||
typedef struct QEMUBH QEMUBH;
|
||||
|
@ -79,6 +81,7 @@ typedef struct QEMUSizedBuffer QEMUSizedBuffer;
|
|||
typedef struct QEMUTimerListGroup QEMUTimerListGroup;
|
||||
typedef struct QEMUTimer QEMUTimer;
|
||||
typedef struct Range Range;
|
||||
typedef struct RAMBlock RAMBlock;
|
||||
typedef struct SerialState SerialState;
|
||||
typedef struct SHPCDevice SHPCDevice;
|
||||
typedef struct SMBusDevice SMBusDevice;
|
||||
|
|
|
@ -22,5 +22,7 @@ typedef void (QEMUBalloonStatus)(void *opaque, BalloonInfo *info);
|
|||
int qemu_add_balloon_handler(QEMUBalloonEvent *event_func,
|
||||
QEMUBalloonStatus *stat_func, void *opaque);
|
||||
void qemu_remove_balloon_handler(void *opaque);
|
||||
bool qemu_balloon_is_inhibited(void);
|
||||
void qemu_balloon_inhibit(bool state);
|
||||
|
||||
#endif
|
||||
|
|
|
@ -70,6 +70,7 @@ void qemu_system_killed(int signal, pid_t pid);
|
|||
void qemu_devices_reset(void);
|
||||
void qemu_system_reset(bool report);
|
||||
void qemu_system_guest_panicked(void);
|
||||
size_t qemu_target_page_bits(void);
|
||||
|
||||
void qemu_add_exit_notifier(Notifier *notify);
|
||||
void qemu_remove_exit_notifier(Notifier *notify);
|
||||
|
@ -83,14 +84,52 @@ void hmp_info_snapshots(Monitor *mon, const QDict *qdict);
|
|||
|
||||
void qemu_announce_self(void);
|
||||
|
||||
/* Subcommands for QEMU_VM_COMMAND */
|
||||
enum qemu_vm_cmd {
|
||||
MIG_CMD_INVALID = 0, /* Must be 0 */
|
||||
MIG_CMD_OPEN_RETURN_PATH, /* Tell the dest to open the Return path */
|
||||
MIG_CMD_PING, /* Request a PONG on the RP */
|
||||
|
||||
MIG_CMD_POSTCOPY_ADVISE, /* Prior to any page transfers, just
|
||||
warn we might want to do PC */
|
||||
MIG_CMD_POSTCOPY_LISTEN, /* Start listening for incoming
|
||||
pages as it's running. */
|
||||
MIG_CMD_POSTCOPY_RUN, /* Start execution */
|
||||
|
||||
MIG_CMD_POSTCOPY_RAM_DISCARD, /* A list of pages to discard that
|
||||
were previously sent during
|
||||
precopy but are dirty. */
|
||||
MIG_CMD_PACKAGED, /* Send a wrapped stream within this stream */
|
||||
MIG_CMD_MAX
|
||||
};
|
||||
|
||||
#define MAX_VM_CMD_PACKAGED_SIZE (1ul << 24)
|
||||
|
||||
bool qemu_savevm_state_blocked(Error **errp);
|
||||
void qemu_savevm_state_begin(QEMUFile *f,
|
||||
const MigrationParams *params);
|
||||
void qemu_savevm_state_header(QEMUFile *f);
|
||||
int qemu_savevm_state_iterate(QEMUFile *f);
|
||||
void qemu_savevm_state_complete(QEMUFile *f);
|
||||
int qemu_savevm_state_iterate(QEMUFile *f, bool postcopy);
|
||||
void qemu_savevm_state_cleanup(void);
|
||||
uint64_t qemu_savevm_state_pending(QEMUFile *f, uint64_t max_size);
|
||||
void qemu_savevm_state_complete_postcopy(QEMUFile *f);
|
||||
void qemu_savevm_state_complete_precopy(QEMUFile *f);
|
||||
void qemu_savevm_state_pending(QEMUFile *f, uint64_t max_size,
|
||||
uint64_t *res_non_postcopiable,
|
||||
uint64_t *res_postcopiable);
|
||||
void qemu_savevm_command_send(QEMUFile *f, enum qemu_vm_cmd command,
|
||||
uint16_t len, uint8_t *data);
|
||||
void qemu_savevm_send_ping(QEMUFile *f, uint32_t value);
|
||||
void qemu_savevm_send_open_return_path(QEMUFile *f);
|
||||
int qemu_savevm_send_packaged(QEMUFile *f, const QEMUSizedBuffer *qsb);
|
||||
void qemu_savevm_send_postcopy_advise(QEMUFile *f);
|
||||
void qemu_savevm_send_postcopy_listen(QEMUFile *f);
|
||||
void qemu_savevm_send_postcopy_run(QEMUFile *f);
|
||||
|
||||
void qemu_savevm_send_postcopy_ram_discard(QEMUFile *f, const char *name,
|
||||
uint16_t len,
|
||||
uint64_t *start_list,
|
||||
uint64_t *length_list);
|
||||
|
||||
int qemu_loadvm_state(QEMUFile *f);
|
||||
|
||||
typedef enum DisplayType
|
||||
|
@ -133,6 +172,7 @@ extern int boot_menu;
|
|||
extern bool boot_strict;
|
||||
extern uint8_t *boot_splash_filedata;
|
||||
extern size_t boot_splash_filedata_size;
|
||||
extern bool enable_mlock;
|
||||
extern uint8_t qemu_extra_params_fw[2];
|
||||
extern QEMUClockType rtc_clock;
|
||||
extern const char *mem_path;
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue