Merge remote-tracking branch 'remotes/bonzini/tags/for-upstream' into staging

* QemuMutex tracing improvements (Alex)
* ram_addr_t optimization (David)
* SCSI fixes (Fam, Stefan, me)
* do {} while (0) fixes (Eric)
* KVM fix for PMU (Jan)
* memory leak fixes from ASAN (Marc-André)
* migration fix for HPET, icount, loadvm (Maria, Pavel)
* hflags fixes (me, Tao)
* block/iscsi uninitialized variable (Peter L.)
* full support for GMainContexts in character devices (Peter Xu)
* more boot-serial-test (Thomas)
* Memory leak fix (Zhecheng)

# gpg: Signature made Tue 16 Jan 2018 14:15:45 GMT
# gpg:                using RSA key 0xBFFBD25F78C7AE83
# gpg: Good signature from "Paolo Bonzini <bonzini@gnu.org>"
# gpg:                 aka "Paolo Bonzini <pbonzini@redhat.com>"
# Primary key fingerprint: 46F5 9FBD 57D6 12E7 BFD4  E2F7 7E15 100C CD36 69B1
#      Subkey fingerprint: F133 3857 4B66 2389 866C  7682 BFFB D25F 78C7 AE83

* remotes/bonzini/tags/for-upstream: (51 commits)
  scripts/analyse-locks-simpletrace.py: script to analyse lock times
  util/qemu-thread-*: add qemu_lock, locked and unlock trace events
  cpu: flush TB cache when loading VMState
  block/iscsi: fix initialization of iTask in iscsi_co_get_block_status
  find_ram_offset: Align ram_addr_t allocation on long boundaries
  find_ram_offset: Add comments and tracing
  cpu_physical_memory_sync_dirty_bitmap: Another alignment fix
  checkpatch: Enforce proper do/while (0) style
  maint: Fix macros with broken 'do/while(0); ' usage
  tests: Avoid 'do/while(false); ' in vhost-user-bridge
  chardev: Clean up previous patch indentation
  chardev: Use goto/label instead of do/break/while(0)
  mips: Tweak location of ';' in macros
  net: Drop unusual use of do { } while (0);
  irq: fix memory leak
  cpus: unify qemu_*_wait_io_event
  icount: fixed saving/restoring of icount warp timers
  scripts/qemu-gdb/timers.py: new helper to dump timer state
  scripts/qemu-gdb: add simple tcg lock status helper
  target-i386: update hflags on Hypervisor.framework
  ...

Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
This commit is contained in:
Peter Maydell
2018-01-16 15:45:15 +00:00
90 changed files with 900 additions and 415 deletions
+5 -2
View File
@@ -8,9 +8,12 @@ SRC_PATH=.
UNCHECKED_GOALS := %clean TAGS cscope ctags dist \
html info pdf txt \
help check-help \
help check-help print-% \
docker docker-% vm-test vm-build-%
print-%:
@echo '$*=$($*)'
# All following code might depend on configuration variables
ifneq ($(wildcard config-host.mak),)
# Put the all: rule here so that config-host.mak can contain dependencies.
@@ -277,7 +280,7 @@ else
DOCS=
endif
SUBDIR_MAKEFLAGS=$(if $(V),,--no-print-directory) BUILD_DIR=$(BUILD_DIR)
SUBDIR_MAKEFLAGS=BUILD_DIR=$(BUILD_DIR)
SUBDIR_DEVICES_MAK=$(patsubst %, %/config-devices.mak, $(TARGET_DIRS))
SUBDIR_DEVICES_MAK_DEP=$(patsubst %, %-config-devices.mak.d, $(TARGET_DIRS))
+2 -2
View File
@@ -89,7 +89,7 @@ static inline int PA_STREAM_IS_GOOD(pa_stream_state_t x)
} \
goto label; \
} \
} while (0);
} while (0)
#define CHECK_DEAD_GOTO(c, stream, rerror, label) \
do { \
@@ -107,7 +107,7 @@ static inline int PA_STREAM_IS_GOOD(pa_stream_state_t x)
} \
goto label; \
} \
} while (0);
} while (0)
static int qpa_simple_read (PAVoiceIn *p, void *data, size_t length, int *rerror)
{
+2 -1
View File
@@ -658,6 +658,8 @@ static int64_t coroutine_fn iscsi_co_get_block_status(BlockDriverState *bs,
uint64_t lba;
int64_t ret;
iscsi_co_init_iscsitask(iscsilun, &iTask);
if (!is_sector_request_lun_aligned(sector_num, nb_sectors, iscsilun)) {
ret = -EINVAL;
goto out;
@@ -675,7 +677,6 @@ static int64_t coroutine_fn iscsi_co_get_block_status(BlockDriverState *bs,
lba = sector_qemu2lun(sector_num, iscsilun);
iscsi_co_init_iscsitask(iscsilun, &iTask);
qemu_mutex_lock(&iscsilun->mutex);
retry:
if (iscsi_get_lba_status_task(iscsilun->iscsi, iscsilun->lun,
+1 -1
View File
@@ -356,7 +356,7 @@ guint qemu_chr_fe_add_watch(CharBackend *be, GIOCondition cond,
}
g_source_set_callback(src, (GSourceFunc)func, user_data, NULL);
tag = g_source_attach(src, NULL);
tag = g_source_attach(src, s->gcontext);
g_source_unref(src);
return tag;
+32 -32
View File
@@ -42,8 +42,8 @@ typedef struct {
/* Protected by the Chardev chr_write_lock. */
int connected;
guint timer_tag;
guint open_tag;
GSource *timer_src;
GSource *open_source;
} PtyChardev;
#define PTY_CHARDEV(obj) OBJECT_CHECK(PtyChardev, (obj), TYPE_CHARDEV_PTY)
@@ -57,8 +57,9 @@ static gboolean pty_chr_timer(gpointer opaque)
PtyChardev *s = PTY_CHARDEV(opaque);
qemu_mutex_lock(&chr->chr_write_lock);
s->timer_tag = 0;
s->open_tag = 0;
s->timer_src = NULL;
g_source_unref(s->open_source);
s->open_source = NULL;
if (!s->connected) {
/* Next poll ... */
pty_chr_update_read_handler_locked(chr);
@@ -67,25 +68,25 @@ static gboolean pty_chr_timer(gpointer opaque)
return FALSE;
}
static void pty_chr_timer_cancel(PtyChardev *s)
{
if (s->timer_src) {
g_source_destroy(s->timer_src);
g_source_unref(s->timer_src);
s->timer_src = NULL;
}
}
/* Called with chr_write_lock held. */
static void pty_chr_rearm_timer(Chardev *chr, int ms)
{
PtyChardev *s = PTY_CHARDEV(chr);
char *name;
if (s->timer_tag) {
g_source_remove(s->timer_tag);
s->timer_tag = 0;
}
if (ms == 1000) {
name = g_strdup_printf("pty-timer-secs-%s", chr->label);
s->timer_tag = g_timeout_add_seconds(1, pty_chr_timer, chr);
} else {
name = g_strdup_printf("pty-timer-ms-%s", chr->label);
s->timer_tag = g_timeout_add(ms, pty_chr_timer, chr);
}
g_source_set_name_by_id(s->timer_tag, name);
pty_chr_timer_cancel(s);
name = g_strdup_printf("pty-timer-%s", chr->label);
s->timer_src = qemu_chr_timeout_add_ms(chr, ms, pty_chr_timer, chr);
g_source_set_name(s->timer_src, name);
g_free(name);
}
@@ -183,7 +184,7 @@ static gboolean qemu_chr_be_generic_open_func(gpointer opaque)
Chardev *chr = CHARDEV(opaque);
PtyChardev *s = PTY_CHARDEV(opaque);
s->open_tag = 0;
s->open_source = NULL;
qemu_chr_be_event(chr, CHR_EVENT_OPENED);
return FALSE;
}
@@ -194,9 +195,10 @@ static void pty_chr_state(Chardev *chr, int connected)
PtyChardev *s = PTY_CHARDEV(chr);
if (!connected) {
if (s->open_tag) {
g_source_remove(s->open_tag);
s->open_tag = 0;
if (s->open_source) {
g_source_destroy(s->open_source);
g_source_unref(s->open_source);
s->open_source = NULL;
}
remove_fd_in_watch(chr);
s->connected = 0;
@@ -205,14 +207,15 @@ static void pty_chr_state(Chardev *chr, int connected)
* the virtual device linked to our pty. */
pty_chr_rearm_timer(chr, 1000);
} else {
if (s->timer_tag) {
g_source_remove(s->timer_tag);
s->timer_tag = 0;
}
pty_chr_timer_cancel(s);
if (!s->connected) {
g_assert(s->open_tag == 0);
g_assert(s->open_source == NULL);
s->open_source = g_idle_source_new();
s->connected = 1;
s->open_tag = g_idle_add(qemu_chr_be_generic_open_func, chr);
g_source_set_callback(s->open_source,
qemu_chr_be_generic_open_func,
chr, NULL);
g_source_attach(s->open_source, chr->gcontext);
}
if (!chr->gsource) {
chr->gsource = io_add_watch_poll(chr, s->ioc,
@@ -231,10 +234,7 @@ static void char_pty_finalize(Object *obj)
qemu_mutex_lock(&chr->chr_write_lock);
pty_chr_state(chr, 0);
object_unref(OBJECT(s->ioc));
if (s->timer_tag) {
g_source_remove(s->timer_tag);
s->timer_tag = 0;
}
pty_chr_timer_cancel(s);
qemu_mutex_unlock(&chr->chr_write_lock);
qemu_chr_be_event(chr, CHR_EVENT_CLOSED);
}
@@ -267,7 +267,7 @@ static void char_pty_open(Chardev *chr,
name = g_strdup_printf("chardev-pty-%s", chr->label);
qio_channel_set_name(QIO_CHANNEL(s->ioc), name);
g_free(name);
s->timer_tag = 0;
s->timer_src = NULL;
*be_opened = false;
}
+40 -35
View File
@@ -64,69 +64,74 @@ static void tty_serial_init(int fd, int speed,
#endif
tcgetattr(fd, &tty);
#define check_speed(val) if (speed <= val) { spd = B##val; break; }
#define check_speed(val) \
if (speed <= val) { \
spd = B##val; \
goto done; \
}
speed = speed * 10 / 11;
do {
check_speed(50);
check_speed(75);
check_speed(110);
check_speed(134);
check_speed(150);
check_speed(200);
check_speed(300);
check_speed(600);
check_speed(1200);
check_speed(1800);
check_speed(2400);
check_speed(4800);
check_speed(9600);
check_speed(19200);
check_speed(38400);
/* Non-Posix values follow. They may be unsupported on some systems. */
check_speed(57600);
check_speed(115200);
check_speed(50);
check_speed(75);
check_speed(110);
check_speed(134);
check_speed(150);
check_speed(200);
check_speed(300);
check_speed(600);
check_speed(1200);
check_speed(1800);
check_speed(2400);
check_speed(4800);
check_speed(9600);
check_speed(19200);
check_speed(38400);
/* Non-Posix values follow. They may be unsupported on some systems. */
check_speed(57600);
check_speed(115200);
#ifdef B230400
check_speed(230400);
check_speed(230400);
#endif
#ifdef B460800
check_speed(460800);
check_speed(460800);
#endif
#ifdef B500000
check_speed(500000);
check_speed(500000);
#endif
#ifdef B576000
check_speed(576000);
check_speed(576000);
#endif
#ifdef B921600
check_speed(921600);
check_speed(921600);
#endif
#ifdef B1000000
check_speed(1000000);
check_speed(1000000);
#endif
#ifdef B1152000
check_speed(1152000);
check_speed(1152000);
#endif
#ifdef B1500000
check_speed(1500000);
check_speed(1500000);
#endif
#ifdef B2000000
check_speed(2000000);
check_speed(2000000);
#endif
#ifdef B2500000
check_speed(2500000);
check_speed(2500000);
#endif
#ifdef B3000000
check_speed(3000000);
check_speed(3000000);
#endif
#ifdef B3500000
check_speed(3500000);
check_speed(3500000);
#endif
#ifdef B4000000
check_speed(4000000);
check_speed(4000000);
#endif
spd = B115200;
} while (0);
spd = B115200;
#undef check_speed
done:
cfsetispeed(&tty, spd);
cfsetospeed(&tty, spd);
+18 -10
View File
@@ -57,7 +57,7 @@ typedef struct {
bool is_telnet;
bool is_tn3270;
guint reconnect_timer;
GSource *reconnect_timer;
int64_t reconnect_time;
bool connect_err_reported;
} SocketChardev;
@@ -67,16 +67,27 @@ typedef struct {
static gboolean socket_reconnect_timeout(gpointer opaque);
static void tcp_chr_reconn_timer_cancel(SocketChardev *s)
{
if (s->reconnect_timer) {
g_source_destroy(s->reconnect_timer);
g_source_unref(s->reconnect_timer);
s->reconnect_timer = NULL;
}
}
static void qemu_chr_socket_restart_timer(Chardev *chr)
{
SocketChardev *s = SOCKET_CHARDEV(chr);
char *name;
assert(s->connected == 0);
s->reconnect_timer = g_timeout_add_seconds(s->reconnect_time,
socket_reconnect_timeout, chr);
name = g_strdup_printf("chardev-socket-reconnect-%s", chr->label);
g_source_set_name_by_id(s->reconnect_timer, name);
s->reconnect_timer = qemu_chr_timeout_add_ms(chr,
s->reconnect_time * 1000,
socket_reconnect_timeout,
chr);
g_source_set_name(s->reconnect_timer, name);
g_free(name);
}
@@ -781,11 +792,7 @@ static void char_socket_finalize(Object *obj)
SocketChardev *s = SOCKET_CHARDEV(obj);
tcp_chr_free_connection(chr);
if (s->reconnect_timer) {
g_source_remove(s->reconnect_timer);
s->reconnect_timer = 0;
}
tcp_chr_reconn_timer_cancel(s);
qapi_free_SocketAddress(s->addr);
if (s->listener) {
qio_net_listener_set_client_func(s->listener, NULL, NULL, NULL);
@@ -824,7 +831,8 @@ static gboolean socket_reconnect_timeout(gpointer opaque)
SocketChardev *s = SOCKET_CHARDEV(opaque);
QIOChannelSocket *sioc;
s->reconnect_timer = 0;
g_source_unref(s->reconnect_timer);
s->reconnect_timer = NULL;
if (chr->be_open) {
return false;
+18
View File
@@ -1084,6 +1084,24 @@ void qmp_chardev_send_break(const char *id, Error **errp)
qemu_chr_be_event(chr, CHR_EVENT_BREAK);
}
/*
* Add a timeout callback for the chardev (in milliseconds), return
* the GSource object created. Please use this to add timeout hook for
* chardev instead of g_timeout_add() and g_timeout_add_seconds(), to
* make sure the gcontext that the task bound to is correct.
*/
GSource *qemu_chr_timeout_add_ms(Chardev *chr, guint ms,
GSourceFunc func, void *private)
{
GSource *source = g_timeout_source_new(ms);
assert(func);
g_source_set_callback(source, func, private, NULL);
g_source_attach(source, chr->gcontext);
return source;
}
void qemu_chr_cleanup(void)
{
object_unparent(get_chardevs_root());
Vendored
+14 -2
View File
@@ -3464,6 +3464,7 @@ else
done
if test "$found" = "no"; then
LIBS="$pthread_lib $LIBS"
libs_qga="$pthread_lib $libs_qga"
fi
PTHREAD_LIB="$pthread_lib"
break
@@ -5193,8 +5194,19 @@ if test "$gcov" = "yes" ; then
LDFLAGS="-fprofile-arcs -ftest-coverage $LDFLAGS"
elif test "$fortify_source" = "yes" ; then
CFLAGS="-O2 -U_FORTIFY_SOURCE -D_FORTIFY_SOURCE=2 $CFLAGS"
elif test "$debug" = "no"; then
CFLAGS="-O2 $CFLAGS"
elif test "$debug" = "yes"; then
if compile_prog "-Og" ""; then
CFLAGS="-Og $CFLAGS"
elif compile_prog "-O1" ""; then
CFLAGS="-O1 $CFLAGS"
fi
# Workaround GCC false-positive Wuninitialized bugs with Og or O1:
# https://gcc.gnu.org/bugzilla/show_bug.cgi?id=24639
if cc_has_warning_flag "-Wno-maybe-uninitialized"; then
CFLAGS="-Wno-maybe-uninitialized $CFLAGS"
fi
else
CFLAGS="-O2 $CFLAGS"
fi
##########################################
+83 -51
View File
@@ -120,16 +120,11 @@ static bool all_cpu_threads_idle(void)
/* Protected by TimersState seqlock */
static bool icount_sleep = true;
static int64_t vm_clock_warp_start = -1;
/* Conversion factor from emulated instructions to virtual clock ticks. */
static int icount_time_shift;
/* Arbitrarily pick 1MIPS as the minimum allowable speed. */
#define MAX_ICOUNT_SHIFT 10
static QEMUTimer *icount_rt_timer;
static QEMUTimer *icount_vm_timer;
static QEMUTimer *icount_warp_timer;
typedef struct TimersState {
/* Protected by BQL. */
int64_t cpu_ticks_prev;
@@ -147,6 +142,11 @@ typedef struct TimersState {
int64_t qemu_icount_bias;
/* Only written by TCG thread */
int64_t qemu_icount;
/* for adjusting icount */
int64_t vm_clock_warp_start;
QEMUTimer *icount_rt_timer;
QEMUTimer *icount_vm_timer;
QEMUTimer *icount_warp_timer;
} TimersState;
static TimersState timers_state;
@@ -432,14 +432,14 @@ static void icount_adjust(void)
static void icount_adjust_rt(void *opaque)
{
timer_mod(icount_rt_timer,
timer_mod(timers_state.icount_rt_timer,
qemu_clock_get_ms(QEMU_CLOCK_VIRTUAL_RT) + 1000);
icount_adjust();
}
static void icount_adjust_vm(void *opaque)
{
timer_mod(icount_vm_timer,
timer_mod(timers_state.icount_vm_timer,
qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL) +
NANOSECONDS_PER_SECOND / 10);
icount_adjust();
@@ -460,7 +460,7 @@ static void icount_warp_rt(void)
*/
do {
seq = seqlock_read_begin(&timers_state.vm_clock_seqlock);
warp_start = vm_clock_warp_start;
warp_start = timers_state.vm_clock_warp_start;
} while (seqlock_read_retry(&timers_state.vm_clock_seqlock, seq));
if (warp_start == -1) {
@@ -473,7 +473,7 @@ static void icount_warp_rt(void)
cpu_get_clock_locked());
int64_t warp_delta;
warp_delta = clock - vm_clock_warp_start;
warp_delta = clock - timers_state.vm_clock_warp_start;
if (use_icount == 2) {
/*
* In adaptive mode, do not let QEMU_CLOCK_VIRTUAL run too
@@ -485,7 +485,7 @@ static void icount_warp_rt(void)
}
timers_state.qemu_icount_bias += warp_delta;
}
vm_clock_warp_start = -1;
timers_state.vm_clock_warp_start = -1;
seqlock_write_end(&timers_state.vm_clock_seqlock);
if (qemu_clock_expired(QEMU_CLOCK_VIRTUAL)) {
@@ -594,11 +594,13 @@ void qemu_start_warp_timer(void)
* every 100ms.
*/
seqlock_write_begin(&timers_state.vm_clock_seqlock);
if (vm_clock_warp_start == -1 || vm_clock_warp_start > clock) {
vm_clock_warp_start = clock;
if (timers_state.vm_clock_warp_start == -1
|| timers_state.vm_clock_warp_start > clock) {
timers_state.vm_clock_warp_start = clock;
}
seqlock_write_end(&timers_state.vm_clock_seqlock);
timer_mod_anticipate(icount_warp_timer, clock + deadline);
timer_mod_anticipate(timers_state.icount_warp_timer,
clock + deadline);
}
} else if (deadline == 0) {
qemu_clock_notify(QEMU_CLOCK_VIRTUAL);
@@ -623,7 +625,7 @@ static void qemu_account_warp_timer(void)
return;
}
timer_del(icount_warp_timer);
timer_del(timers_state.icount_warp_timer);
icount_warp_rt();
}
@@ -632,6 +634,45 @@ static bool icount_state_needed(void *opaque)
return use_icount;
}
static bool warp_timer_state_needed(void *opaque)
{
TimersState *s = opaque;
return s->icount_warp_timer != NULL;
}
static bool adjust_timers_state_needed(void *opaque)
{
TimersState *s = opaque;
return s->icount_rt_timer != NULL;
}
/*
* Subsection for warp timer migration is optional, because may not be created
*/
static const VMStateDescription icount_vmstate_warp_timer = {
.name = "timer/icount/warp_timer",
.version_id = 1,
.minimum_version_id = 1,
.needed = warp_timer_state_needed,
.fields = (VMStateField[]) {
VMSTATE_INT64(vm_clock_warp_start, TimersState),
VMSTATE_TIMER_PTR(icount_warp_timer, TimersState),
VMSTATE_END_OF_LIST()
}
};
static const VMStateDescription icount_vmstate_adjust_timers = {
.name = "timer/icount/timers",
.version_id = 1,
.minimum_version_id = 1,
.needed = adjust_timers_state_needed,
.fields = (VMStateField[]) {
VMSTATE_TIMER_PTR(icount_rt_timer, TimersState),
VMSTATE_TIMER_PTR(icount_vm_timer, TimersState),
VMSTATE_END_OF_LIST()
}
};
/*
* This is a subsection for icount migration.
*/
@@ -644,6 +685,11 @@ static const VMStateDescription icount_vmstate_timers = {
VMSTATE_INT64(qemu_icount_bias, TimersState),
VMSTATE_INT64(qemu_icount, TimersState),
VMSTATE_END_OF_LIST()
},
.subsections = (const VMStateDescription*[]) {
&icount_vmstate_warp_timer,
&icount_vmstate_adjust_timers,
NULL
}
};
@@ -754,7 +800,7 @@ void configure_icount(QemuOpts *opts, Error **errp)
icount_sleep = qemu_opt_get_bool(opts, "sleep", true);
if (icount_sleep) {
icount_warp_timer = timer_new_ns(QEMU_CLOCK_VIRTUAL_RT,
timers_state.icount_warp_timer = timer_new_ns(QEMU_CLOCK_VIRTUAL_RT,
icount_timer_cb, NULL);
}
@@ -788,13 +834,14 @@ void configure_icount(QemuOpts *opts, Error **errp)
the virtual time trigger catches emulated time passing too fast.
Realtime triggers occur even when idle, so use them less frequently
than VM triggers. */
icount_rt_timer = timer_new_ms(QEMU_CLOCK_VIRTUAL_RT,
timers_state.vm_clock_warp_start = -1;
timers_state.icount_rt_timer = timer_new_ms(QEMU_CLOCK_VIRTUAL_RT,
icount_adjust_rt, NULL);
timer_mod(icount_rt_timer,
timer_mod(timers_state.icount_rt_timer,
qemu_clock_get_ms(QEMU_CLOCK_VIRTUAL_RT) + 1000);
icount_vm_timer = timer_new_ns(QEMU_CLOCK_VIRTUAL,
timers_state.icount_vm_timer = timer_new_ns(QEMU_CLOCK_VIRTUAL,
icount_adjust_vm, NULL);
timer_mod(icount_vm_timer,
timer_mod(timers_state.icount_vm_timer,
qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL) +
NANOSECONDS_PER_SECOND / 10);
}
@@ -862,7 +909,8 @@ static void kick_tcg_thread(void *opaque)
static void start_tcg_kick_timer(void)
{
if (!mttcg_enabled && !tcg_kick_vcpu_timer && CPU_NEXT(first_cpu)) {
assert(!mttcg_enabled);
if (!tcg_kick_vcpu_timer && CPU_NEXT(first_cpu)) {
tcg_kick_vcpu_timer = timer_new_ns(QEMU_CLOCK_VIRTUAL,
kick_tcg_thread, NULL);
timer_mod(tcg_kick_vcpu_timer, qemu_tcg_next_kick());
@@ -871,6 +919,7 @@ static void start_tcg_kick_timer(void)
static void stop_tcg_kick_timer(void)
{
assert(!mttcg_enabled);
if (tcg_kick_vcpu_timer) {
timer_del(tcg_kick_vcpu_timer);
tcg_kick_vcpu_timer = NULL;
@@ -1090,18 +1139,9 @@ static void qemu_wait_io_event_common(CPUState *cpu)
process_queued_cpu_work(cpu);
}
static bool qemu_tcg_should_sleep(CPUState *cpu)
static void qemu_tcg_rr_wait_io_event(CPUState *cpu)
{
if (mttcg_enabled) {
return cpu_thread_is_idle(cpu);
} else {
return all_cpu_threads_idle();
}
}
static void qemu_tcg_wait_io_event(CPUState *cpu)
{
while (qemu_tcg_should_sleep(cpu)) {
while (all_cpu_threads_idle()) {
stop_tcg_kick_timer();
qemu_cond_wait(cpu->halt_cond, &qemu_global_mutex);
}
@@ -1111,20 +1151,18 @@ static void qemu_tcg_wait_io_event(CPUState *cpu)
qemu_wait_io_event_common(cpu);
}
static void qemu_kvm_wait_io_event(CPUState *cpu)
static void qemu_wait_io_event(CPUState *cpu)
{
while (cpu_thread_is_idle(cpu)) {
qemu_cond_wait(cpu->halt_cond, &qemu_global_mutex);
}
qemu_wait_io_event_common(cpu);
}
static void qemu_hvf_wait_io_event(CPUState *cpu)
{
while (cpu_thread_is_idle(cpu)) {
qemu_cond_wait(cpu->halt_cond, &qemu_global_mutex);
#ifdef _WIN32
/* Eat dummy APC queued by qemu_cpu_kick_thread. */
if (!tcg_enabled()) {
SleepEx(0, TRUE);
}
#endif
qemu_wait_io_event_common(cpu);
}
@@ -1160,7 +1198,7 @@ static void *qemu_kvm_cpu_thread_fn(void *arg)
cpu_handle_guest_debug(cpu);
}
}
qemu_kvm_wait_io_event(cpu);
qemu_wait_io_event(cpu);
} while (!cpu->unplug || cpu_can_run(cpu));
qemu_kvm_destroy_vcpu(cpu);
@@ -1206,7 +1244,7 @@ static void *qemu_dummy_cpu_thread_fn(void *arg)
exit(1);
}
qemu_mutex_lock_iothread();
qemu_wait_io_event_common(cpu);
qemu_wait_io_event(cpu);
}
return NULL;
@@ -1423,7 +1461,7 @@ static void *qemu_tcg_rr_cpu_thread_fn(void *arg)
atomic_mb_set(&cpu->exit_request, 0);
}
qemu_tcg_wait_io_event(cpu ? cpu : QTAILQ_FIRST(&cpus));
qemu_tcg_rr_wait_io_event(cpu ? cpu : QTAILQ_FIRST(&cpus));
deal_with_unplugged_cpus();
}
@@ -1454,13 +1492,7 @@ static void *qemu_hax_cpu_thread_fn(void *arg)
}
}
while (cpu_thread_is_idle(cpu)) {
qemu_cond_wait(cpu->halt_cond, &qemu_global_mutex);
}
#ifdef _WIN32
SleepEx(0, TRUE);
#endif
qemu_wait_io_event_common(cpu);
qemu_wait_io_event(cpu);
}
return NULL;
}
@@ -1497,7 +1529,7 @@ static void *qemu_hvf_cpu_thread_fn(void *arg)
cpu_handle_guest_debug(cpu);
}
}
qemu_hvf_wait_io_event(cpu);
qemu_wait_io_event(cpu);
} while (!cpu->unplug || cpu_can_run(cpu));
hvf_vcpu_destroy(cpu);
@@ -1576,7 +1608,7 @@ static void *qemu_tcg_cpu_thread_fn(void *arg)
}
atomic_mb_set(&cpu->exit_request, 0);
qemu_tcg_wait_io_event(cpu);
qemu_wait_io_event(cpu);
}
return NULL;
+1 -1
View File
@@ -79,7 +79,7 @@ static int qcrypto_ivgen_essiv_calculate(QCryptoIVGen *ivgen,
uint8_t *data = g_new(uint8_t, ndata);
sector = cpu_to_le64(sector);
memcpy(data, (uint8_t *)&sector, ndata);
memcpy(data, (uint8_t *)&sector, MIN(sizeof(sector), ndata));
if (sizeof(sector) < ndata) {
memset(data + sizeof(sector), 0, ndata - sizeof(sector));
}
+6 -10
View File
@@ -207,18 +207,14 @@ static int opc_index[256];
static void
init_disasm (struct disassemble_info *info)
{
const struct s390_opcode *opcode;
const struct s390_opcode *opcode_end;
int i;
memset (opc_index, 0, sizeof (opc_index));
opcode_end = s390_opcodes + s390_num_opcodes;
for (opcode = s390_opcodes; opcode < opcode_end; opcode++)
{
opc_index[(int) opcode->opcode[0]] = opcode - s390_opcodes;
while ((opcode < opcode_end) &&
(opcode[1].opcode[0] == opcode->opcode[0]))
opcode++;
}
/* Reverse order, such that each opc_index ends up pointing to the
first matching entry instead of the last. */
for (i = s390_num_opcodes; i--; )
opc_index[s390_opcodes[i].opcode[0]] = i;
#ifdef QEMU_DISABLE
switch (info->mach)
+13
View File
@@ -510,3 +510,16 @@ default-configs/$TARGET-NAME file as input.
This is the entrypoint used when make recurses to build a single system
or userspace emulator target. It is merely a symlink back to the
Makefile.target in the top level.
Useful make targets
===================
- help
Print a help message for the most common build targets.
- print-VAR
Print the value of the variable VAR. Useful for debugging the build
system.
+33 -7
View File
@@ -623,6 +623,13 @@ static int cpu_common_post_load(void *opaque, int version_id)
cpu->interrupt_request &= ~0x01;
tlb_flush(cpu);
/* loadvm has just updated the content of RAM, bypassing the
* usual mechanisms that ensure we flush TBs for writes to
* memory we've translated code from. So we must flush all TBs,
* which will now be stale.
*/
tb_flush(cpu);
return 0;
}
@@ -1660,7 +1667,10 @@ static void *file_ram_alloc(RAMBlock *block,
}
#endif
/* Called with the ramlist lock held. */
/* Allocate space within the ram_addr_t space that governs the
* dirty bitmaps.
* Called with the ramlist lock held.
*/
static ram_addr_t find_ram_offset(ram_addr_t size)
{
RAMBlock *block, *next_block;
@@ -1673,19 +1683,33 @@ static ram_addr_t find_ram_offset(ram_addr_t size)
}
RAMBLOCK_FOREACH(block) {
ram_addr_t end, next = RAM_ADDR_MAX;
ram_addr_t candidate, next = RAM_ADDR_MAX;
end = block->offset + block->max_length;
/* Align blocks to start on a 'long' in the bitmap
* which makes the bitmap sync'ing take the fast path.
*/
candidate = block->offset + block->max_length;
candidate = ROUND_UP(candidate, BITS_PER_LONG << TARGET_PAGE_BITS);
/* Search for the closest following block
* and find the gap.
*/
RAMBLOCK_FOREACH(next_block) {
if (next_block->offset >= end) {
if (next_block->offset >= candidate) {
next = MIN(next, next_block->offset);
}
}
if (next - end >= size && next - end < mingap) {
offset = end;
mingap = next - end;
/* If it fits remember our place and remember the size
* of gap, but keep going so that we might find a smaller
* gap to fill so avoiding fragmentation.
*/
if (next - candidate >= size && next - candidate < mingap) {
offset = candidate;
mingap = next - candidate;
}
trace_find_ram_offset_loop(size, candidate, offset, next, mingap);
}
if (offset == RAM_ADDR_MAX) {
@@ -1694,6 +1718,8 @@ static ram_addr_t find_ram_offset(ram_addr_t size)
abort();
}
trace_find_ram_offset(size, offset);
return offset;
}
+1 -1
View File
@@ -37,7 +37,7 @@
if (STM_ADC_ERR_DEBUG >= lvl) { \
qemu_log("%s: " fmt, __func__, ## args); \
} \
} while (0);
} while (0)
#define DB_PRINT(fmt, args...) DB_PRINT_L(1, fmt, ## args)
+1 -1
View File
@@ -40,7 +40,7 @@
fprintf(stderr, ": %s: ", __func__); \
fprintf(stderr, ## __VA_ARGS__); \
} \
} while (0);
} while (0)
/* Fields for FlashPartInfo->flags */
+1 -1
View File
@@ -33,7 +33,7 @@
#define DB_PRINT(...) do { \
fprintf(stderr, ": %s: ", __func__); \
fprintf(stderr, ## __VA_ARGS__); \
} while (0);
} while (0)
#else
#define DB_PRINT(...)
#endif
+1 -1
View File
@@ -34,7 +34,7 @@
if (STM_USART_ERR_DEBUG >= lvl) { \
qemu_log("%s: " fmt, __func__, ## args); \
} \
} while (0);
} while (0)
#define DB_PRINT(fmt, args...) DB_PRINT_L(1, fmt, ## args)
+16 -12
View File
@@ -31,7 +31,7 @@ typedef struct Terminal3270 {
uint8_t outv[OUTPUT_BUFFER_SIZE];
int in_len;
bool handshake_done;
guint timer_tag;
GSource *timer_src;
} Terminal3270;
#define TYPE_TERMINAL_3270 "x-terminal3270"
@@ -45,6 +45,15 @@ static int terminal_can_read(void *opaque)
return INPUT_BUFFER_SIZE - t->in_len;
}
static void terminal_timer_cancel(Terminal3270 *t)
{
if (t->timer_src) {
g_source_destroy(t->timer_src);
g_source_unref(t->timer_src);
t->timer_src = NULL;
}
}
/*
* Protocol handshake done,
* signal guest by an unsolicited DE irq.
@@ -90,12 +99,9 @@ static void terminal_read(void *opaque, const uint8_t *buf, int size)
assert(size <= (INPUT_BUFFER_SIZE - t->in_len));
if (t->timer_tag) {
g_source_remove(t->timer_tag);
t->timer_tag = 0;
}
t->timer_tag = g_timeout_add_seconds(600, send_timing_mark_cb, t);
terminal_timer_cancel(t);
t->timer_src = qemu_chr_timeout_add_ms(t->chr.chr, 600 * 1000,
send_timing_mark_cb, t);
memcpy(&t->inv[t->in_len], buf, size);
t->in_len += size;
if (t->in_len < 2) {
@@ -145,10 +151,7 @@ static void chr_event(void *opaque, int event)
/* Ensure the initial status correct, always reset them. */
t->in_len = 0;
t->handshake_done = false;
if (t->timer_tag) {
g_source_remove(t->timer_tag);
t->timer_tag = 0;
}
terminal_timer_cancel(t);
switch (event) {
case CHR_EVENT_OPENED:
@@ -157,7 +160,8 @@ static void chr_event(void *opaque, int event)
* char-socket.c. Once qemu receives the terminal-type of the
* client, mark handshake done and trigger everything rolling again.
*/
t->timer_tag = g_timeout_add_seconds(600, send_timing_mark_cb, t);
t->timer_src = qemu_chr_timeout_add_ms(t->chr.chr, 600 * 1000,
send_timing_mark_cb, t);
break;
case CHR_EVENT_CLOSED:
sch->curr_status.scsw.dstat = SCSW_DSTAT_DEVICE_END;
+1 -1
View File
@@ -63,7 +63,7 @@
if (DEBUG_CG3) { \
printf("CG3: " fmt , ## __VA_ARGS__); \
} \
} while (0);
} while (0)
#define TYPE_CG3 "cgthree"
#define CG3(obj) OBJECT_CHECK(CG3State, (obj), TYPE_CG3)

Some files were not shown because too many files have changed in this diff Show More