From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from eggs.gnu.org ([2001:4830:134:3::10]:44062) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1ZG5xb-0004Sh-ON for qemu-devel@nongnu.org; Fri, 17 Jul 2015 09:45:56 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1ZG5xX-0003lT-3j for qemu-devel@nongnu.org; Fri, 17 Jul 2015 09:45:55 -0400 Received: from mail-wg0-f45.google.com ([74.125.82.45]:33356) by eggs.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1ZG5xW-0003l1-SW for qemu-devel@nongnu.org; Fri, 17 Jul 2015 09:45:51 -0400 Received: by wgmn9 with SMTP id n9so82785984wgm.0 for ; Fri, 17 Jul 2015 06:45:50 -0700 (PDT) References: <1436516626-8322-1-git-send-email-a.rigo@virtualopensystems.com> <1436516626-8322-9-git-send-email-a.rigo@virtualopensystems.com> From: Alex =?utf-8?Q?Benn=C3=A9e?= In-reply-to: <1436516626-8322-9-git-send-email-a.rigo@virtualopensystems.com> Date: Fri, 17 Jul 2015 14:45:47 +0100 Message-ID: <878uae6gok.fsf@linaro.org> MIME-Version: 1.0 Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: 8bit Subject: Re: [Qemu-devel] [RFC v3 08/13] exec.c: introduce a simple rendezvous support List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , To: Alvise Rigo Cc: mttcg@listserver.greensocs.com, claudio.fontana@huawei.com, qemu-devel@nongnu.org, pbonzini@redhat.com, jani.kokkonen@huawei.com, tech@virtualopensystems.com Alvise Rigo writes: > When a vCPU is about to set a memory page as exclusive, it needs to wait > that all the running vCPUs finish to execute the current TB and to be aware > of the exact moment when that happens. For this, add a simple rendezvous > mechanism that will be used in softmmu_llsc_template.h to implement the > ldlink operation. > > Suggested-by: Jani Kokkonen > Suggested-by: Claudio Fontana > Signed-off-by: Alvise Rigo > --- > cpus.c | 5 +++++ > exec.c | 45 +++++++++++++++++++++++++++++++++++++++++++++ > include/qom/cpu.h | 16 ++++++++++++++++ > 3 files changed, 66 insertions(+) > > diff --git a/cpus.c b/cpus.c > index aee445a..f4d938e 100644 > --- a/cpus.c > +++ b/cpus.c > @@ -1423,6 +1423,11 @@ static int tcg_cpu_exec(CPUArchState *env) > qemu_mutex_unlock_iothread(); > ret = cpu_exec(env); > cpu->tcg_executing = 0; > + > + if (unlikely(cpu->pending_rdv)) { > + cpu_exit_do_rendezvous(cpu); > + } > + I'll ignore this stuff for now as I assume we can all use the async work patch of Fred's? > qemu_mutex_lock_iothread(); > #ifdef CONFIG_PROFILER > tcg_time += profile_getclock() - ti; > diff --git a/exec.c b/exec.c > index 964e922..51958ed 100644 > --- a/exec.c > +++ b/exec.c > @@ -746,6 +746,51 @@ void cpu_breakpoint_remove_all(CPUState *cpu, int mask) > } > } > > +/* Rendezvous implementation. > + * The corresponding definitions are in include/qom/cpu.h. */ > +CpuExitRendezvous cpu_exit_rendezvous; > +inline void cpu_exit_init_rendezvous(void) > +{ > + CpuExitRendezvous *rdv = &cpu_exit_rendezvous; > + > + rdv->attendees = 0; > +} > + > +inline void cpu_exit_rendezvous_add_attendee(CPUState *cpu) > +{ > + CpuExitRendezvous *rdv = &cpu_exit_rendezvous; > + > + if (!cpu->pending_rdv) { > + cpu->pending_rdv = 1; > + atomic_inc(&rdv->attendees); > + } > +} > + > +void cpu_exit_do_rendezvous(CPUState *cpu) > +{ > + CpuExitRendezvous *rdv = &cpu_exit_rendezvous; > + > + atomic_dec(&rdv->attendees); > + > + cpu->pending_rdv = 0; > +} > + > +void cpu_exit_rendezvous_wait_others(CPUState *cpu) > +{ > + CpuExitRendezvous *rdv = &cpu_exit_rendezvous; > + > + while (rdv->attendees) { > + g_usleep(TCG_RDV_POLLING_PERIOD); > + } > +} > + > +void cpu_exit_rendezvous_release(void) > +{ > + CpuExitRendezvous *rdv = &cpu_exit_rendezvous; > + > + rdv->attendees = 0; > +} > + > /* enable or disable single step mode. EXCP_DEBUG is returned by the > CPU loop after each instruction */ > void cpu_single_step(CPUState *cpu, int enabled) > diff --git a/include/qom/cpu.h b/include/qom/cpu.h > index 8f3fe56..8d121b3 100644 > --- a/include/qom/cpu.h > +++ b/include/qom/cpu.h > @@ -201,6 +201,20 @@ typedef struct CPUWatchpoint { > QTAILQ_ENTRY(CPUWatchpoint) entry; > } CPUWatchpoint; > > +/* Rendezvous support */ > +#define TCG_RDV_POLLING_PERIOD 10 > +typedef struct CpuExitRendezvous { > + volatile int attendees; > + QemuMutex lock; > +} CpuExitRendezvous; > + > +extern CpuExitRendezvous cpu_exit_rendezvous; > +void cpu_exit_init_rendezvous(void); > +void cpu_exit_rendezvous_add_attendee(CPUState *cpu); > +void cpu_exit_do_rendezvous(CPUState *cpu); > +void cpu_exit_rendezvous_wait_others(CPUState *cpu); > +void cpu_exit_rendezvous_release(void); > + > struct KVMState; > struct kvm_run; > > @@ -291,6 +305,8 @@ struct CPUState { > > void *opaque; > > + volatile int pending_rdv; > + I will however echo the "hmmm" on Fred's patch about the optimistic use of volatile here. As Peter mentioned it is a red flag and I would prefer explicit memory consistency behaviour used and documented. > /* In order to avoid passing too many arguments to the MMIO helpers, > * we store some rarely used information in the CPU context. > */ -- Alex Bennée