* [Qemu-devel] [PATCH 0/7] NPTL support for PPC, v2
@ 2009-08-03 15:43 Nathan Froyd
2009-08-03 15:43 ` [Qemu-devel] [PATCH 1/7] target-ppc: fix cpu_clone_regs Nathan Froyd
` (7 more replies)
0 siblings, 8 replies; 9+ messages in thread
From: Nathan Froyd @ 2009-08-03 15:43 UTC (permalink / raw)
To: qemu-devel
This patch series adds NPTL support in Linux user-mode emulation to
32-bit PowerPC targets.
The main complication comes from implementing atomic instructions
properly. We chose to implement a simplistic model:
- reserved loads record the value loaded;
- conditional stores check that the memory at the effective address
contains the value loaded by the previous reserved load, in addition
to all other checks. if so, the store succeeds; otherwise, it fails.
It is possible to implement something more sophisticated using mprotect:
- reserved loads write-protect the page from which the value is loaded;
- regular stores to the page (through SIGSEGV handling) remove the write
protection (which is roughly how the architecture really works);
- conditional stores fail if the page was not write-protected, in
addition to all other checks. If the store succeeds, then the page is
unprotected.
but the simple scheme works well enough and should be somewhat faster.
The simple scheme is what's already done for system mode, too; it's even
slightly dumber in system mode because we don't check for equality of
values.
malc asked me to compare the approach taken in this patch series versus
an mprotect-based approach. I did so, and found that there was no
difference between the two and that this approach was faster (no
surprise).
The patch series has been tested against the glibc testsuite, where it
passes a good chunk (90%+) of the testsuite. The other 10% are
basically things that are not going to work in QEMU anytime soon
(e.g. sharing futexes between multiple processes, using clone(2)
directly, etc.).
This is an update to the patch series I sent a month or so ago; the
changes are rather trivial: a formatting fix or two and a fix for a
ppc64 compilation error.
-Nathan
^ permalink raw reply [flat|nested] 9+ messages in thread
* [Qemu-devel] [PATCH 1/7] target-ppc: fix cpu_clone_regs
2009-08-03 15:43 [Qemu-devel] [PATCH 0/7] NPTL support for PPC, v2 Nathan Froyd
@ 2009-08-03 15:43 ` Nathan Froyd
2009-08-03 15:43 ` [Qemu-devel] [PATCH 2/7] target-ppc: add cpu_set_tls Nathan Froyd
` (6 subsequent siblings)
7 siblings, 0 replies; 9+ messages in thread
From: Nathan Froyd @ 2009-08-03 15:43 UTC (permalink / raw)
To: qemu-devel
We only need to make sure that the clone syscall looks like it
succeeded, not clobber 60% of the register set.
Signed-off-by: Nathan Froyd <froydnj@codesourcery.com>
---
target-ppc/cpu.h | 4 +---
1 files changed, 1 insertions(+), 3 deletions(-)
diff --git a/target-ppc/cpu.h b/target-ppc/cpu.h
index 69c1d58..148e8c3 100644
--- a/target-ppc/cpu.h
+++ b/target-ppc/cpu.h
@@ -817,11 +817,9 @@ static inline int cpu_mmu_index (CPUState *env)
#if defined(CONFIG_USER_ONLY)
static inline void cpu_clone_regs(CPUState *env, target_ulong newsp)
{
- int i;
if (newsp)
env->gpr[1] = newsp;
- for (i = 7; i < 32; i++)
- env->gpr[i] = 0;
+ env->gpr[3] = 0;
}
#endif
--
1.6.3.2
^ permalink raw reply related [flat|nested] 9+ messages in thread
* [Qemu-devel] [PATCH 2/7] target-ppc: add cpu_set_tls
2009-08-03 15:43 [Qemu-devel] [PATCH 0/7] NPTL support for PPC, v2 Nathan Froyd
2009-08-03 15:43 ` [Qemu-devel] [PATCH 1/7] target-ppc: fix cpu_clone_regs Nathan Froyd
@ 2009-08-03 15:43 ` Nathan Froyd
2009-08-03 15:43 ` [Qemu-devel] [PATCH 3/7] target-ppc: retain l{w,d}arx loaded value Nathan Froyd
` (5 subsequent siblings)
7 siblings, 0 replies; 9+ messages in thread
From: Nathan Froyd @ 2009-08-03 15:43 UTC (permalink / raw)
To: qemu-devel
Signed-off-by: Nathan Froyd <froydnj@codesourcery.com>
---
target-ppc/cpu.h | 11 +++++++++++
1 files changed, 11 insertions(+), 0 deletions(-)
diff --git a/target-ppc/cpu.h b/target-ppc/cpu.h
index 148e8c3..fe2257d 100644
--- a/target-ppc/cpu.h
+++ b/target-ppc/cpu.h
@@ -1589,4 +1589,15 @@ static inline void cpu_get_tb_cpu_state(CPUState *env, target_ulong *pc,
*flags = env->hflags;
}
+static inline void cpu_set_tls(CPUState *env, target_ulong newtls)
+{
+#if defined(TARGET_PPC64)
+ /* The kernel checks TIF_32BIT here; we don't support loading 32-bit
+ binaries on PPC64 yet. */
+ env->gpr[13] = newtls;
+#else
+ env->gpr[2] = newtls;
+#endif
+}
+
#endif /* !defined (__CPU_PPC_H__) */
--
1.6.3.2
^ permalink raw reply related [flat|nested] 9+ messages in thread
* [Qemu-devel] [PATCH 3/7] target-ppc: retain l{w,d}arx loaded value
2009-08-03 15:43 [Qemu-devel] [PATCH 0/7] NPTL support for PPC, v2 Nathan Froyd
2009-08-03 15:43 ` [Qemu-devel] [PATCH 1/7] target-ppc: fix cpu_clone_regs Nathan Froyd
2009-08-03 15:43 ` [Qemu-devel] [PATCH 2/7] target-ppc: add cpu_set_tls Nathan Froyd
@ 2009-08-03 15:43 ` Nathan Froyd
2009-08-03 15:43 ` [Qemu-devel] [PATCH 4/7] target-ppc: add exceptions for conditional stores Nathan Froyd
` (4 subsequent siblings)
7 siblings, 0 replies; 9+ messages in thread
From: Nathan Froyd @ 2009-08-03 15:43 UTC (permalink / raw)
To: qemu-devel
We do this so we can check on the corresponding stc{w,d}x. whether the
value has changed. It's a poor man's form of implementing atomic
operations and is valid only for NPTL usermode Linux emulation.
Signed-off-by: Nathan Froyd <froydnj@codesourcery.com>
---
target-ppc/cpu.h | 4 +++-
target-ppc/helper.c | 2 +-
target-ppc/machine.c | 4 ++--
target-ppc/op_helper.c | 4 ++--
target-ppc/translate.c | 13 +++++++++----
5 files changed, 17 insertions(+), 10 deletions(-)
diff --git a/target-ppc/cpu.h b/target-ppc/cpu.h
index fe2257d..7935fcd 100644
--- a/target-ppc/cpu.h
+++ b/target-ppc/cpu.h
@@ -561,7 +561,9 @@ struct CPUPPCState {
/* XER */
target_ulong xer;
/* Reservation address */
- target_ulong reserve;
+ target_ulong reserve_addr;
+ /* Reservation value */
+ target_ulong reserve_val;
/* Those ones are used in supervisor mode only */
/* machine state register */
diff --git a/target-ppc/helper.c b/target-ppc/helper.c
index b7162df..6eca2e5 100644
--- a/target-ppc/helper.c
+++ b/target-ppc/helper.c
@@ -2805,7 +2805,7 @@ void cpu_ppc_reset (void *opaque)
env->msr |= (1ULL << MSR_SF);
#endif
hreg_compute_hflags(env);
- env->reserve = (target_ulong)-1ULL;
+ env->reserve_addr = (target_ulong)-1ULL;
/* Be sure no exception or interrupt is pending */
env->pending_interrupts = 0;
env->exception_index = POWERPC_EXCP_NONE;
diff --git a/target-ppc/machine.c b/target-ppc/machine.c
index 99ba3eb..deb2e2d 100644
--- a/target-ppc/machine.c
+++ b/target-ppc/machine.c
@@ -20,7 +20,7 @@ void cpu_save(QEMUFile *f, void *opaque)
for (i = 0; i < 8; i++)
qemu_put_be32s(f, &env->crf[i]);
qemu_put_betls(f, &env->xer);
- qemu_put_betls(f, &env->reserve);
+ qemu_put_betls(f, &env->reserve_addr);
qemu_put_betls(f, &env->msr);
for (i = 0; i < 4; i++)
qemu_put_betls(f, &env->tgpr[i]);
@@ -107,7 +107,7 @@ int cpu_load(QEMUFile *f, void *opaque, int version_id)
for (i = 0; i < 8; i++)
qemu_get_be32s(f, &env->crf[i]);
qemu_get_betls(f, &env->xer);
- qemu_get_betls(f, &env->reserve);
+ qemu_get_betls(f, &env->reserve_addr);
qemu_get_betls(f, &env->msr);
for (i = 0; i < 4; i++)
qemu_get_betls(f, &env->tgpr[i]);
diff --git a/target-ppc/op_helper.c b/target-ppc/op_helper.c
index ad6d8ee..812282c 100644
--- a/target-ppc/op_helper.c
+++ b/target-ppc/op_helper.c
@@ -329,8 +329,8 @@ static void do_dcbz(target_ulong addr, int dcache_line_size)
for (i = 0 ; i < dcache_line_size ; i += 4) {
stl(addr + i , 0);
}
- if (env->reserve == addr)
- env->reserve = (target_ulong)-1ULL;
+ if (env->reserve_addr == addr)
+ env->reserve_addr = (target_ulong)-1ULL;
}
void helper_dcbz(target_ulong addr)
diff --git a/target-ppc/translate.c b/target-ppc/translate.c
index 58818c2..06282b6 100644
--- a/target-ppc/translate.c
+++ b/target-ppc/translate.c
@@ -158,7 +158,8 @@ void ppc_translate_init(void)
offsetof(CPUState, xer), "xer");
cpu_reserve = tcg_global_mem_new(TCG_AREG0,
- offsetof(CPUState, reserve), "reserve");
+ offsetof(CPUState, reserve_addr),
+ "reserve_addr");
cpu_fpscr = tcg_global_mem_new_i32(TCG_AREG0,
offsetof(CPUState, fpscr), "fpscr");
@@ -3006,12 +3007,14 @@ static void gen_isync(DisasContext *ctx)
static void gen_lwarx(DisasContext *ctx)
{
TCGv t0;
+ TCGv gpr = cpu_gpr[rD(ctx->opcode)];
gen_set_access_type(ctx, ACCESS_RES);
t0 = tcg_temp_local_new();
gen_addr_reg_index(ctx, t0);
gen_check_align(ctx, t0, 0x03);
- gen_qemu_ld32u(ctx, cpu_gpr[rD(ctx->opcode)], t0);
+ gen_qemu_ld32u(ctx, gpr, t0);
tcg_gen_mov_tl(cpu_reserve, t0);
+ tcg_gen_st_tl(gpr, cpu_env, offsetof(CPUState, reserve_val));
tcg_temp_free(t0);
}
@@ -3041,12 +3044,14 @@ static void gen_stwcx_(DisasContext *ctx)
static void gen_ldarx(DisasContext *ctx)
{
TCGv t0;
+ TCGv gpr = cpu_gpr[rD(ctx->opcode)];
gen_set_access_type(ctx, ACCESS_RES);
t0 = tcg_temp_local_new();
gen_addr_reg_index(ctx, t0);
gen_check_align(ctx, t0, 0x07);
- gen_qemu_ld64(ctx, cpu_gpr[rD(ctx->opcode)], t0);
+ gen_qemu_ld64(ctx, gpr, t0);
tcg_gen_mov_tl(cpu_reserve, t0);
+ tcg_gen_st_tl(gpr, cpu_env, offsetof(CPUState, reserve_val));
tcg_temp_free(t0);
}
@@ -8834,7 +8839,7 @@ void cpu_dump_state (CPUState *env, FILE *f,
a = 'E';
cpu_fprintf(f, " %c%c", a, env->crf[i] & 0x01 ? 'O' : ' ');
}
- cpu_fprintf(f, " ] RES " ADDRX "\n", env->reserve);
+ cpu_fprintf(f, " ] RES " ADDRX "\n", env->reserve_addr);
for (i = 0; i < 32; i++) {
if ((i & (RFPL - 1)) == 0)
cpu_fprintf(f, "FPR%02d", i);
--
1.6.3.2
^ permalink raw reply related [flat|nested] 9+ messages in thread
* [Qemu-devel] [PATCH 4/7] target-ppc: add exceptions for conditional stores
2009-08-03 15:43 [Qemu-devel] [PATCH 0/7] NPTL support for PPC, v2 Nathan Froyd
` (2 preceding siblings ...)
2009-08-03 15:43 ` [Qemu-devel] [PATCH 3/7] target-ppc: retain l{w,d}arx loaded value Nathan Froyd
@ 2009-08-03 15:43 ` Nathan Froyd
2009-08-03 15:43 ` [Qemu-devel] [PATCH 5/7] linux-user: handle POWERPC_EXCP_STCX Nathan Froyd
` (3 subsequent siblings)
7 siblings, 0 replies; 9+ messages in thread
From: Nathan Froyd @ 2009-08-03 15:43 UTC (permalink / raw)
To: qemu-devel
Signed-off-by: Nathan Froyd <froydnj@codesourcery.com>
---
target-ppc/cpu.h | 5 +++
target-ppc/translate.c | 71 ++++++++++++++++++++++++++++++++++-------------
2 files changed, 56 insertions(+), 20 deletions(-)
diff --git a/target-ppc/cpu.h b/target-ppc/cpu.h
index 7935fcd..8c1029e 100644
--- a/target-ppc/cpu.h
+++ b/target-ppc/cpu.h
@@ -218,6 +218,7 @@ enum {
/* Qemu exceptions: special cases we want to stop translation */
POWERPC_EXCP_SYNC = 0x202, /* context synchronizing instruction */
POWERPC_EXCP_SYSCALL_USER = 0x203, /* System call in user mode only */
+ POWERPC_EXCP_STCX = 0x204 /* Conditional stores in user mode */
};
/* Exceptions error codes */
@@ -564,6 +565,10 @@ struct CPUPPCState {
target_ulong reserve_addr;
/* Reservation value */
target_ulong reserve_val;
+ /* Reservation store address */
+ target_ulong reserve_ea;
+ /* Reserved store source register and size */
+ target_ulong reserve_info;
/* Those ones are used in supervisor mode only */
/* machine state register */
diff --git a/target-ppc/translate.c b/target-ppc/translate.c
index 06282b6..f82c6e5 100644
--- a/target-ppc/translate.c
+++ b/target-ppc/translate.c
@@ -3018,24 +3018,49 @@ static void gen_lwarx(DisasContext *ctx)
tcg_temp_free(t0);
}
+#if defined(CONFIG_USER_ONLY)
+static void gen_conditional_store (DisasContext *ctx, TCGv EA,
+ int reg, int size)
+{
+ TCGv t0 = tcg_temp_new();
+ uint32_t save_exception = ctx->exception;
+
+ tcg_gen_st_tl(EA, cpu_env, offsetof(CPUState, reserve_ea));
+ tcg_gen_movi_tl(t0, (size << 5) | reg);
+ tcg_gen_st_tl(t0, cpu_env, offsetof(CPUState, reserve_info));
+ tcg_temp_free(t0);
+ gen_update_nip(ctx, ctx->nip-4);
+ ctx->exception = POWERPC_EXCP_BRANCH;
+ gen_exception(ctx, POWERPC_EXCP_STCX);
+ ctx->exception = save_exception;
+}
+#endif
+
/* stwcx. */
static void gen_stwcx_(DisasContext *ctx)
{
- int l1;
TCGv t0;
gen_set_access_type(ctx, ACCESS_RES);
t0 = tcg_temp_local_new();
gen_addr_reg_index(ctx, t0);
gen_check_align(ctx, t0, 0x03);
- tcg_gen_trunc_tl_i32(cpu_crf[0], cpu_xer);
- tcg_gen_shri_i32(cpu_crf[0], cpu_crf[0], XER_SO);
- tcg_gen_andi_i32(cpu_crf[0], cpu_crf[0], 1);
- l1 = gen_new_label();
- tcg_gen_brcond_tl(TCG_COND_NE, t0, cpu_reserve, l1);
- tcg_gen_ori_i32(cpu_crf[0], cpu_crf[0], 1 << CRF_EQ);
- gen_qemu_st32(ctx, cpu_gpr[rS(ctx->opcode)], t0);
- gen_set_label(l1);
- tcg_gen_movi_tl(cpu_reserve, -1);
+#if defined(CONFIG_USER_ONLY)
+ gen_conditional_store(ctx, t0, rS(ctx->opcode), 4);
+#else
+ {
+ int l1;
+
+ tcg_gen_trunc_tl_i32(cpu_crf[0], cpu_xer);
+ tcg_gen_shri_i32(cpu_crf[0], cpu_crf[0], XER_SO);
+ tcg_gen_andi_i32(cpu_crf[0], cpu_crf[0], 1);
+ l1 = gen_new_label();
+ tcg_gen_brcond_tl(TCG_COND_NE, t0, cpu_reserve, l1);
+ tcg_gen_ori_i32(cpu_crf[0], cpu_crf[0], 1 << CRF_EQ);
+ gen_qemu_st32(ctx, cpu_gpr[rS(ctx->opcode)], t0);
+ gen_set_label(l1);
+ tcg_gen_movi_tl(cpu_reserve, -1);
+ }
+#endif
tcg_temp_free(t0);
}
@@ -3058,21 +3083,27 @@ static void gen_ldarx(DisasContext *ctx)
/* stdcx. */
static void gen_stdcx_(DisasContext *ctx)
{
- int l1;
TCGv t0;
gen_set_access_type(ctx, ACCESS_RES);
t0 = tcg_temp_local_new();
gen_addr_reg_index(ctx, t0);
gen_check_align(ctx, t0, 0x07);
- tcg_gen_trunc_tl_i32(cpu_crf[0], cpu_xer);
- tcg_gen_shri_i32(cpu_crf[0], cpu_crf[0], XER_SO);
- tcg_gen_andi_i32(cpu_crf[0], cpu_crf[0], 1);
- l1 = gen_new_label();
- tcg_gen_brcond_tl(TCG_COND_NE, t0, cpu_reserve, l1);
- tcg_gen_ori_i32(cpu_crf[0], cpu_crf[0], 1 << CRF_EQ);
- gen_qemu_st64(ctx, cpu_gpr[rS(ctx->opcode)], t0);
- gen_set_label(l1);
- tcg_gen_movi_tl(cpu_reserve, -1);
+#if defined(CONFIG_USER_ONLY)
+ gen_conditional_store(ctx, t0, rS(ctx->opcode), 8);
+#else
+ {
+ int l1;
+ tcg_gen_trunc_tl_i32(cpu_crf[0], cpu_xer);
+ tcg_gen_shri_i32(cpu_crf[0], cpu_crf[0], XER_SO);
+ tcg_gen_andi_i32(cpu_crf[0], cpu_crf[0], 1);
+ l1 = gen_new_label();
+ tcg_gen_brcond_tl(TCG_COND_NE, t0, cpu_reserve, l1);
+ tcg_gen_ori_i32(cpu_crf[0], cpu_crf[0], 1 << CRF_EQ);
+ gen_qemu_st64(ctx, cpu_gpr[rS(ctx->opcode)], t0);
+ gen_set_label(l1);
+ tcg_gen_movi_tl(cpu_reserve, -1);
+ }
+#endif
tcg_temp_free(t0);
}
#endif /* defined(TARGET_PPC64) */
--
1.6.3.2
^ permalink raw reply related [flat|nested] 9+ messages in thread
* [Qemu-devel] [PATCH 5/7] linux-user: handle POWERPC_EXCP_STCX
2009-08-03 15:43 [Qemu-devel] [PATCH 0/7] NPTL support for PPC, v2 Nathan Froyd
` (3 preceding siblings ...)
2009-08-03 15:43 ` [Qemu-devel] [PATCH 4/7] target-ppc: add exceptions for conditional stores Nathan Froyd
@ 2009-08-03 15:43 ` Nathan Froyd
2009-08-03 15:43 ` [Qemu-devel] [PATCH 6/7] enable NPTL for ppc-linux-user targets in configure Nathan Froyd
` (2 subsequent siblings)
7 siblings, 0 replies; 9+ messages in thread
From: Nathan Froyd @ 2009-08-03 15:43 UTC (permalink / raw)
To: qemu-devel
We handle conditional stores as an exception so we can ensure that no
other thread is changing memory out from underneath us.
Signed-off-by: Nathan Froyd <froydnj@codesourcery.com>
---
linux-user/main.c | 68 +++++++++++++++++++++++++++++++++++++++++++++++++++++
1 files changed, 68 insertions(+), 0 deletions(-)
diff --git a/linux-user/main.c b/linux-user/main.c
index 20a2576..bc903de 100644
--- a/linux-user/main.c
+++ b/linux-user/main.c
@@ -1060,6 +1060,63 @@ do { \
log_cpu_state(env, 0); \
} while (0)
+static int do_store_exclusive(CPUPPCState *env)
+{
+ target_ulong addr;
+ target_ulong page_addr;
+ target_ulong val;
+ int flags;
+ int segv = 0;
+
+ addr = env->reserve_ea;
+ page_addr = addr & TARGET_PAGE_MASK;
+ start_exclusive();
+ mmap_lock();
+ flags = page_get_flags(page_addr);
+ if ((flags & PAGE_READ) == 0) {
+ segv = 1;
+ } else {
+ int reg = env->reserve_info & 0x1f;
+ int size = (env->reserve_info >> 5) & 0xf;
+ int stored = 0;
+
+ if (addr == env->reserve_addr) {
+ switch (size) {
+ case 1: segv = get_user_u8(val, addr); break;
+ case 2: segv = get_user_u16(val, addr); break;
+ case 4: segv = get_user_u32(val, addr); break;
+#if defined(TARGET_PPC64)
+ case 8: segv = get_user_u64(val, addr); break;
+#endif
+ default: abort();
+ }
+ if (!segv && val == env->reserve_val) {
+ val = env->gpr[reg];
+ switch (size) {
+ case 1: segv = put_user_u8(val, addr); break;
+ case 2: segv = put_user_u16(val, addr); break;
+ case 4: segv = put_user_u32(val, addr); break;
+#if defined(TARGET_PPC64)
+ case 8: segv = put_user_u64(val, addr); break;
+#endif
+ default: abort();
+ }
+ if (!segv) {
+ stored = 1;
+ }
+ }
+ }
+ env->crf[0] = (stored << 1) | xer_so;
+ env->reserve_addr = (target_ulong)-1;
+ }
+ if (!segv) {
+ env->nip += 4;
+ }
+ mmap_unlock();
+ end_exclusive();
+ return segv;
+}
+
void cpu_loop(CPUPPCState *env)
{
target_siginfo_t info;
@@ -1067,7 +1124,9 @@ void cpu_loop(CPUPPCState *env)
uint32_t ret;
for(;;) {
+ cpu_exec_start(env);
trapnr = cpu_ppc_exec(env);
+ cpu_exec_end(env);
switch(trapnr) {
case POWERPC_EXCP_NONE:
/* Just go on */
@@ -1447,6 +1506,15 @@ void cpu_loop(CPUPPCState *env)
printf("syscall returned 0x%08x (%d)\n", ret, ret);
#endif
break;
+ case POWERPC_EXCP_STCX:
+ if (do_store_exclusive(env)) {
+ info.si_signo = TARGET_SIGSEGV;
+ info.si_errno = 0;
+ info.si_code = TARGET_SEGV_MAPERR;
+ info._sifields._sigfault._addr = env->nip;
+ queue_signal(env, info.si_signo, &info);
+ }
+ break;
case EXCP_DEBUG:
{
int sig;
--
1.6.3.2
^ permalink raw reply related [flat|nested] 9+ messages in thread
* [Qemu-devel] [PATCH 6/7] enable NPTL for ppc-linux-user targets in configure
2009-08-03 15:43 [Qemu-devel] [PATCH 0/7] NPTL support for PPC, v2 Nathan Froyd
` (4 preceding siblings ...)
2009-08-03 15:43 ` [Qemu-devel] [PATCH 5/7] linux-user: handle POWERPC_EXCP_STCX Nathan Froyd
@ 2009-08-03 15:43 ` Nathan Froyd
2009-08-03 15:43 ` [Qemu-devel] [PATCH 7/7] linux-user: make FUTEX_* calls honor timeout parameter Nathan Froyd
2009-08-04 16:19 ` [Qemu-devel] [PATCH 0/7] NPTL support for PPC, v2 Martin Mohring
7 siblings, 0 replies; 9+ messages in thread
From: Nathan Froyd @ 2009-08-03 15:43 UTC (permalink / raw)
To: qemu-devel
Enabling support for ppc64-linux-user should be easy enough to do later.
Signed-off-by: Nathan Froyd <froydnj@codesourcery.com>
---
configure | 2 ++
1 files changed, 2 insertions(+), 0 deletions(-)
diff --git a/configure b/configure
index 36db3b2..def8948 100755
--- a/configure
+++ b/configure
@@ -1921,12 +1921,14 @@ case "$target_arch2" in
ppc)
gdb_xml_files="power-core.xml power-fpu.xml power-altivec.xml power-spe.xml"
target_phys_bits=32
+ target_nptl="yes"
;;
ppcemb)
TARGET_BASE_ARCH=ppc
TARGET_ABI_DIR=ppc
gdb_xml_files="power-core.xml power-fpu.xml power-altivec.xml power-spe.xml"
target_phys_bits=64
+ target_nptl="yes"
;;
ppc64)
TARGET_BASE_ARCH=ppc
--
1.6.3.2
^ permalink raw reply related [flat|nested] 9+ messages in thread
* [Qemu-devel] [PATCH 7/7] linux-user: make FUTEX_* calls honor timeout parameter
2009-08-03 15:43 [Qemu-devel] [PATCH 0/7] NPTL support for PPC, v2 Nathan Froyd
` (5 preceding siblings ...)
2009-08-03 15:43 ` [Qemu-devel] [PATCH 6/7] enable NPTL for ppc-linux-user targets in configure Nathan Froyd
@ 2009-08-03 15:43 ` Nathan Froyd
2009-08-04 16:19 ` [Qemu-devel] [PATCH 0/7] NPTL support for PPC, v2 Martin Mohring
7 siblings, 0 replies; 9+ messages in thread
From: Nathan Froyd @ 2009-08-03 15:43 UTC (permalink / raw)
To: qemu-devel
Signed-off-by: Nathan Froyd <froydnj@codesourcery.com>
---
linux-user/syscall.c | 24 ++++++++++++++++--------
1 files changed, 16 insertions(+), 8 deletions(-)
diff --git a/linux-user/syscall.c b/linux-user/syscall.c
index b5f669e..673eed4 100644
--- a/linux-user/syscall.c
+++ b/linux-user/syscall.c
@@ -4026,14 +4026,16 @@ static int do_futex(target_ulong uaddr, int op, int val, target_ulong timeout,
target_ulong uaddr2, int val3)
{
struct timespec ts, *pts;
+ int base_op;
/* ??? We assume FUTEX_* constants are the same on both host
and target. */
#ifdef FUTEX_CMD_MASK
- switch ((op&FUTEX_CMD_MASK)) {
+ base_op = op & FUTEX_CMD_MASK;
#else
- switch (op) {
+ base_op = op;
#endif
+ switch (base_op) {
case FUTEX_WAIT:
if (timeout) {
pts = &ts;
@@ -4045,16 +4047,22 @@ static int do_futex(target_ulong uaddr, int op, int val, target_ulong timeout,
pts, NULL, 0));
case FUTEX_WAKE:
return get_errno(sys_futex(g2h(uaddr), op, val, NULL, NULL, 0));
- case FUTEX_WAKE_OP:
- return get_errno(sys_futex(g2h(uaddr), op, val, NULL, g2h(uaddr2), val3 ));
case FUTEX_FD:
return get_errno(sys_futex(g2h(uaddr), op, val, NULL, NULL, 0));
case FUTEX_REQUEUE:
- return get_errno(sys_futex(g2h(uaddr), op, val,
- NULL, g2h(uaddr2), 0));
case FUTEX_CMP_REQUEUE:
- return get_errno(sys_futex(g2h(uaddr), op, val,
- NULL, g2h(uaddr2), tswap32(val3)));
+ case FUTEX_WAKE_OP:
+ /* For FUTEX_REQUEUE, FUTEX_CMP_REQUEUE, and FUTEX_WAKE_OP, the
+ TIMEOUT parameter is interpreted as a uint32_t by the kernel.
+ But the prototype takes a `struct timespec *'; insert casts
+ to satisfy the compiler. We do not need to tswap TIMEOUT
+ since it's not compared to guest memory. */
+ pts = (struct timespec *)(uintptr_t) timeout;
+ return get_errno(sys_futex(g2h(uaddr), op, val, pts,
+ g2h(uaddr2),
+ (base_op == FUTEX_CMP_REQUEUE
+ ? tswap32(val3)
+ : val3)));
default:
return -TARGET_ENOSYS;
}
--
1.6.3.2
^ permalink raw reply related [flat|nested] 9+ messages in thread
* Re: [Qemu-devel] [PATCH 0/7] NPTL support for PPC, v2
2009-08-03 15:43 [Qemu-devel] [PATCH 0/7] NPTL support for PPC, v2 Nathan Froyd
` (6 preceding siblings ...)
2009-08-03 15:43 ` [Qemu-devel] [PATCH 7/7] linux-user: make FUTEX_* calls honor timeout parameter Nathan Froyd
@ 2009-08-04 16:19 ` Martin Mohring
7 siblings, 0 replies; 9+ messages in thread
From: Martin Mohring @ 2009-08-04 16:19 UTC (permalink / raw)
To: Nathan Froyd; +Cc: qemu-devel
[-- Attachment #1: Type: text/plain, Size: 2091 bytes --]
Nathan Froyd wrote:
> This patch series adds NPTL support in Linux user-mode emulation to
> 32-bit PowerPC targets.
>
> The main complication comes from implementing atomic instructions
> properly. We chose to implement a simplistic model:
>
> - reserved loads record the value loaded;
>
> - conditional stores check that the memory at the effective address
> contains the value loaded by the previous reserved load, in addition
> to all other checks. if so, the store succeeds; otherwise, it fails.
>
> It is possible to implement something more sophisticated using mprotect:
>
> - reserved loads write-protect the page from which the value is loaded;
>
> - regular stores to the page (through SIGSEGV handling) remove the write
> protection (which is roughly how the architecture really works);
>
> - conditional stores fail if the page was not write-protected, in
> addition to all other checks. If the store succeeds, then the page is
> unprotected.
>
> but the simple scheme works well enough and should be somewhat faster.
> The simple scheme is what's already done for system mode, too; it's even
> slightly dumber in system mode because we don't check for equality of
> values.
>
> malc asked me to compare the approach taken in this patch series versus
> an mprotect-based approach. I did so, and found that there was no
> difference between the two and that this approach was faster (no
> surprise).
>
> The patch series has been tested against the glibc testsuite, where it
> passes a good chunk (90%+) of the testsuite. The other 10% are
> basically things that are not going to work in QEMU anytime soon
> (e.g. sharing futexes between multiple processes, using clone(2)
> directly, etc.).
>
> This is an update to the patch series I sent a month or so ago; the
> changes are rather trivial: a formatting fix or two and a fix for a
> ppc64 compilation error.
>
> -Nathan
>
>
>
Attached you will find an addon patch to activate uid16 also for powerpc
user mode linux.
It is needed because many distros i found use uid16 calls also on powerpc.
Cheers, Martin
[-- Attachment #2: qemu-0.11-git-user-linux-ppc-uid16_fix.patch --]
[-- Type: text/x-patch, Size: 4815 bytes --]
diff -r -u qemu-0.11git2009.06.04.1212.orig/linux-user/ppc/syscall_nr.h qemu-0.11git2009.06.04.1212/linux-user/ppc/syscall_nr.h
--- qemu-0.11git2009.06.04.1212.orig/linux-user/ppc/syscall_nr.h 2009-04-25 15:24:45.000000000 +0200
+++ qemu-0.11git2009.06.04.1212/linux-user/ppc/syscall_nr.h 2009-06-05 20:15:32.047746675 +0200
@@ -17,15 +17,15 @@
#define TARGET_NR_time 13
#define TARGET_NR_mknod 14
#define TARGET_NR_chmod 15
-#define TARGET_NR_lchown32 16
+#define TARGET_NR_lchown 16
#define TARGET_NR_break 17
#define TARGET_NR_oldstat 18
#define TARGET_NR_lseek 19
#define TARGET_NR_getpid 20
#define TARGET_NR_mount 21
#define TARGET_NR_umount 22
-#define TARGET_NR_setuid32 23
-#define TARGET_NR_getuid32 24
+#define TARGET_NR_setuid 23
+#define TARGET_NR_getuid 24
#define TARGET_NR_stime 25
#define TARGET_NR_ptrace 26
#define TARGET_NR_alarm 27
@@ -47,11 +47,11 @@
#define TARGET_NR_times 43
#define TARGET_NR_prof 44
#define TARGET_NR_brk 45
-#define TARGET_NR_setgid32 46
-#define TARGET_NR_getgid32 47
+#define TARGET_NR_setgid 46
+#define TARGET_NR_getgid 47
#define TARGET_NR_signal 48
-#define TARGET_NR_geteuid32 49
-#define TARGET_NR_getegid32 50
+#define TARGET_NR_geteuid 49
+#define TARGET_NR_getegid 50
#define TARGET_NR_acct 51
#define TARGET_NR_umount2 52
#define TARGET_NR_lock 53
@@ -71,8 +71,8 @@
#define TARGET_NR_sigaction 67
#define TARGET_NR_sgetmask 68
#define TARGET_NR_ssetmask 69
-#define TARGET_NR_setreuid32 70
-#define TARGET_NR_setregid32 71
+#define TARGET_NR_setreuid 70
+#define TARGET_NR_setregid 71
#define TARGET_NR_sigsuspend 72
#define TARGET_NR_sigpending 73
#define TARGET_NR_sethostname 74
@@ -81,8 +81,8 @@
#define TARGET_NR_getrusage 77
#define TARGET_NR_gettimeofday 78
#define TARGET_NR_settimeofday 79
-#define TARGET_NR_getgroups32 80
-#define TARGET_NR_setgroups32 81
+#define TARGET_NR_getgroups 80
+#define TARGET_NR_setgroups 81
#define TARGET_NR_select 82
#define TARGET_NR_symlink 83
#define TARGET_NR_oldlstat 84
@@ -96,7 +96,7 @@
#define TARGET_NR_truncate 92
#define TARGET_NR_ftruncate 93
#define TARGET_NR_fchmod 94
-#define TARGET_NR_fchown32 95
+#define TARGET_NR_fchown 95
#define TARGET_NR_getpriority 96
#define TARGET_NR_setpriority 97
#define TARGET_NR_profil 98
@@ -139,8 +139,8 @@
#define TARGET_NR_sysfs 135
#define TARGET_NR_personality 136
#define TARGET_NR_afs_syscall 137 /* Syscall for Andrew File System */
-#define TARGET_NR_setfsuid32 138
-#define TARGET_NR_setfsgid32 139
+#define TARGET_NR_setfsuid 138
+#define TARGET_NR_setfsgid 139
#define TARGET_NR__llseek 140
#define TARGET_NR_getdents 141
#define TARGET_NR__newselect 142
@@ -182,7 +182,7 @@
#define TARGET_NR_rt_sigsuspend 178
#define TARGET_NR_pread64 179
#define TARGET_NR_pwrite64 180
-#define TARGET_NR_chown32 181
+#define TARGET_NR_chown 181
#define TARGET_NR_getcwd 182
#define TARGET_NR_capget 183
#define TARGET_NR_capset 184
diff -r -u qemu-0.11git2009.06.16.1935/linux-user/syscall_defs.h qemu-0.11git2009.06.16.1935.new/linux-user/syscall_defs.h
--- qemu-0.11git2009.06.16.1935/linux-user/syscall_defs.h 2009-06-17 00:35:05.000000000 +0200
+++ qemu-0.11git2009.06.16.1935.new/linux-user/syscall_defs.h 2009-06-17 01:28:28.000000000 +0200
@@ -49,7 +49,7 @@
#define TARGET_IOC_TYPEBITS 8
#if defined(TARGET_I386) || defined(TARGET_ARM) || defined(TARGET_SPARC) \
- || defined(TARGET_M68K) || defined(TARGET_SH4) || defined(TARGET_CRIS)
+ || defined(TARGET_M68K) || defined(TARGET_SH4) || defined(TARGET_CRIS) || defined(TARGET_PPC)
/* 16 bit uid wrappers emulation */
#define USE_UID16
#endif
^ permalink raw reply [flat|nested] 9+ messages in thread
end of thread, other threads:[~2009-08-04 16:19 UTC | newest]
Thread overview: 9+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2009-08-03 15:43 [Qemu-devel] [PATCH 0/7] NPTL support for PPC, v2 Nathan Froyd
2009-08-03 15:43 ` [Qemu-devel] [PATCH 1/7] target-ppc: fix cpu_clone_regs Nathan Froyd
2009-08-03 15:43 ` [Qemu-devel] [PATCH 2/7] target-ppc: add cpu_set_tls Nathan Froyd
2009-08-03 15:43 ` [Qemu-devel] [PATCH 3/7] target-ppc: retain l{w,d}arx loaded value Nathan Froyd
2009-08-03 15:43 ` [Qemu-devel] [PATCH 4/7] target-ppc: add exceptions for conditional stores Nathan Froyd
2009-08-03 15:43 ` [Qemu-devel] [PATCH 5/7] linux-user: handle POWERPC_EXCP_STCX Nathan Froyd
2009-08-03 15:43 ` [Qemu-devel] [PATCH 6/7] enable NPTL for ppc-linux-user targets in configure Nathan Froyd
2009-08-03 15:43 ` [Qemu-devel] [PATCH 7/7] linux-user: make FUTEX_* calls honor timeout parameter Nathan Froyd
2009-08-04 16:19 ` [Qemu-devel] [PATCH 0/7] NPTL support for PPC, v2 Martin Mohring
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).