Re: [Qemu-devel] [PATCH v4 0/4] MIPS64 user mode emulation in QEMU
Ping? On Tue, Jan 3, 2012 at 9:54 AM, kha...@kics.edu.pk wrote: From: Khansa Butt kha...@kics.edu.pk [sorry version missed in previous set] This is the team work of Ehsan-ul-Haq, Abdul Qadeer, Abdul Waheed, Khansa Butt from HPCN Lab KICS UET Lahore. In previous patch set we were including Cavium specific instructions along with Cavium specifc registers in UME. Because of these register fields we had to bump the cpu version up but I noticed that cpu_save() and cpu_load() are not called in UME so we decided to postpone Octeon specific changes ( registers and instructions) and will include them in our SME Patches. MIPS64el is included in Andreas Färber patch series so I have not include it in our patches (we are working on mips64el but mips64el binary is needed) v3--v4 1)Drop Cavium specific instructions and save/load of Cavium's registers 2) signal handling of mips64 has been changed according to Andreas Färber and Richard Henderson v2--v3 1)SEQI and SEQ related changes 2)Cavium specific change in set_thread_area syscall has been removed as it corresponds to modified libc and kernel. v1--v2 1)Fix issues related to coding style, typos and misleading comments 2)Addition of helper functions for sum of Cavium specific instructions v1 contains 1)MIPS64 user mode emulation in QEMU 2) Octeon CPU definition + Cavium Specific Instructions linux-user: Add support for MIPS64 target-mips: Enable 64 bit user mode target-mips: Fix FPU reset linux-user: Implement signal handling for mips64 configure | 1 + default-configs/mips64-linux-user.mak | 1 + linux-user/main.c | 21 +++- linux-user/mips64/syscall.h | 2 + linux-user/signal.c | 272 + target-mips/translate.c | 4 + 6 files changed, 169 insertions(+), 132 deletions(-) create mode 100644 default-configs/mips64-linux-user.mak -- 1.7.3.4
Re: [Qemu-devel] [PATCH 2/3] target-mips:enabling of 64 bit user mode and floating point operations MIPS_HFLAG_UX is included in env-hflags so that the address computation for LD instruction does not
On Wed, Dec 14, 2011 at 10:05 PM, Richard Henderson r...@twiddle.net wrote: On 12/08/2011 04:04 PM, Andreas Färber wrote: + /* if cpu has FPU, MIPS_HFLAG_F64 must be included in env-hflags + so that floating point operations can be emulated */ + env-active_fpu.fcr0 = env-cpu_model-CP1_fcr0; if (env-active_fpu.fcr0 (1 FCR0_F64)) { env-hflags |= MIPS_HFLAG_F64; } Nack. env-active_fpu.fcr0 gets initialized in translate_init.c based on cpu_model-CR1_fcr0, where FCR0_F64 is set only for 24Kf, 34Kf, MIPS64R2-generic. TARGET_ABI_MIPSN64 linux-user defaults to 20Kc. So it seems to rather be an issue of using the right -cpu parameter or changing the default for n64. [cc'ing Nathan, who introduced the if] That said, there's still something missing, e.g. MIPS_HFLAG_COP1X. My first guess is simply if (env-insn_flags (ISA_MIPS32 | ISA_MIPS4)) { env-hflags |= MIPS_HFLAG_COP1X; } I don't understand why we add above lines. I think this issue is some what related to cpu_model not with ISA I've explained why I add env-active_fpu.fcr0 = env-cpu_model-CP1_fcr0; line in reply to this patch to Andreas Färber and cc'ed you as well immediately after this MIPS64 hunk. r~
Re: [Qemu-devel] [PATCH 3/3] linux-user:Signal handling for MIPS64
On Wed, Dec 14, 2011 at 9:20 PM, Richard Henderson r...@twiddle.net wrote: On 12/07/2011 09:25 PM, kha...@kics.edu.pk wrote: +#if defined(TARGET_MIPS64) + /* tswapal() do 64 bit swap in case of MIPS64 but + we need 32 bit swap as sa_flags is 32 bit */ + k-sa_flags = bswap32(act-sa_flags); +#else k-sa_flags = tswapal(act-sa_flags); +#endif The condition in syscall_defs.h is TARGET_MIPS, not TARGET_MIPS64. They should match, despite the fact that it doesn't actually matter for the 32-bit abis. #elif defined(TARGET_ABI_MIPSN64) -# warning signal handling not implemented +struct target_sigcontext { + uint32_t sc_regmask; /* Unused */ + uint32_t sc_status; There's no reason to duplicate all this code. Yes, when someone wrote this in the first place, they wrote separate sectons for each mips abi. However, as you can see that huge portions of this block are identical, this was obviously a mistake. Start by changing the original section to #elif defined(TARGET_MIPS) and see what needs changing specifically for the ABIs. I'm not even sure there are any differences at all. The difference lies in setup_frame(). the trampoline function needs syscall number install_sigtramp(frame-sf_code, TARGET_NR_sigreturn); sigreturn is not defined for MIPS64 instead it has only rt_sigreturn. I tried with #elif defined(TARGET_MIPS). cross compile the following small program and run it on qemu-mips64 #include stdio.h #include signal.h #include string.h #include unistd.h struct sigaction act; void sighandler(int signum, siginfo_t *info, void *ptr) { printf(Received signal %d\n, signum); printf(Signal originates from process %lu\n,(unsigned long)info-si_pid); } int main() { printf(I am %lu\n, (unsigned long)getpid()); memset(act, 0, sizeof(act)); act.sa_sigaction = sighandler; act.sa_flags = SA_SIGINFO; sigaction(SIGILL, act, NULL); // Waiting sleep(100); return 0; } and again I found that only install_sigtramp line is needed to be changed. keeping #elif defined(TARGET_MIPS) above signal handling portion, can i use #if defined(TARGET_MIPS64) #else for install_sigtramp() difference r~
[Qemu-devel] [PATCH 2/3] target-mips:enabling of 64 bit user mode and floating point operations MIPS_HFLAG_UX is included in env-hflags so that the address computation for LD instruction does not tre
On Thu, Dec 29, 2011 at 4:17 PM, Andreas Färber andreas.faer...@web.de wrote: Am 29.12.2011 08:55, schrieb Khansa Butt: On Fri, Dec 9, 2011 at 5:04 AM, Andreas Färber andreas.faer...@web.de wrote: + /* if cpu has FPU, MIPS_HFLAG_F64 must be included in env-hflags + so that floating point operations can be emulated */ + env-active_fpu.fcr0 = env-cpu_model-CP1_fcr0; if (env-active_fpu.fcr0 (1 FCR0_F64)) { env-hflags |= MIPS_HFLAG_F64; } Nack. env-active_fpu.fcr0 gets initialized in translate_init.c based on cpu_model-CR1_fcr0, where FCR0_F64 is set only for 24Kf, 34Kf, MIPS64R2-generic. TARGET_ABI_MIPSN64 linux-user defaults to 20Kc. So it seems to rather be an issue of using the right -cpu parameter or changing the default for n64. [cc'ing Nathan, who introduced the if] The reason why I add this line env-active_fpu.fcr0 = env-cpu_model-CP1_fcr0 is as follows in translate_init.c fpu_init() initializes active_fpu for given cpu model afterwards cpu_reset() reset the values to zero using this memset(env, 0, offsetof(CPUMIPSState, breakpoints)); so whatever the value of cpu_model-CR1_fcr0 was , the value of env-active_fpu.fcr0 will be zero now thats why I add above line to retrieve the correct env-active_fpu.fcr0 value according to CPU model( whether it is 24Kf or 20Kc or something else) During the development of mips64-linux-user I observed this issue. I gave qemu-mips64 command with -cpu option equal to MIPS64R2-generic and an illegal instruction error occurred, so I used above hunk. Well, that sounds like a different and more generic problem that shouldn't be fixed inside CONFIG_USER_ONLY TARGET_MIPS64. And your reasoning should've definitely been in the commit message! The problem here is not whether the patches observably work for you but whether it's the correct way to fix it. We did this because it works for us is never a convincing justification of a change. If it doesn't work for you in linux-user it won't work in softmmu either, so doing that before #if defined(CONFIG_USER_ONLY) where lots of env-cpu_model stuff is being copyied (esp. before env-HABITS to honor mips_def_t order) seems better. Also, given your observation, does it even make sense for cpu_mips_init() to call fpu_init() when all CPUState members it initializes get cleared in cpu_reset()? Maybe just move that call into cpu_reset() and rename it to fpu_reset()? mmu_init() and mvp_init() seem okay by contrast. why cpu_reset() calls memset? it does not reset all the members of CPUState only those which are in the range of offsetof(CPUMIPSState, breakpoints). what if I remove memset line? When you've figured this out, please again put it into a separate patch titled, e.g., target-mips: Fix FPU reset with appropriate explanation. Andreas
Re: [Qemu-devel] [PATCH 3/3] linux-user:Signal handling for MIPS64
On Wed, Dec 14, 2011 at 9:20 PM, Richard Henderson r...@twiddle.net wrote: On 12/07/2011 09:25 PM, kha...@kics.edu.pk wrote: +#if defined(TARGET_MIPS64) + /* tswapal() do 64 bit swap in case of MIPS64 but + we need 32 bit swap as sa_flags is 32 bit */ + k-sa_flags = bswap32(act-sa_flags); +#else k-sa_flags = tswapal(act-sa_flags); +#endif The condition in syscall_defs.h is TARGET_MIPS, not TARGET_MIPS64. They should match, despite the fact that it doesn't actually matter for the 32-bit abis. actually sa_flags is 32 bit for MIPS64 but tswapal calls tswap64() as TARGET_LONG_SIZE != 4 in case of MIPS64( see cpu-all.h) hence sa_flags has wrong value at the end so I used above hunk #elif defined(TARGET_ABI_MIPSN64) -# warning signal handling not implemented +struct target_sigcontext { + uint32_t sc_regmask; /* Unused */ + uint32_t sc_status; There's no reason to duplicate all this code. Yes, when someone wrote this in the first place, they wrote separate sectons for each mips abi. However, as you can see that huge portions of this block are identical, this was obviously a mistake. Start by changing the original section to #elif defined(TARGET_MIPS) and see what needs changing specifically for the ABIs. I'm not even sure there are any differences at all. r~
Re: [Qemu-devel] [PATCH 2/3] target-mips:enabling of 64 bit user mode and floating point operations MIPS_HFLAG_UX is included in env-hflags so that the address computation for LD instruction does not
On Fri, Dec 9, 2011 at 5:04 AM, Andreas Färber andreas.faer...@web.de wrote: Thanks for extending the commit description. Please see this for a template though: http://live.gnome.org/Git/CommitMessages Looks like there's an empty line missing between subject and description (and the space after target-mips:). Am 08.12.2011 06:25, schrieb kha...@kics.edu.pk: From: Khansa Butt kha...@kics.edu.pk Signed-off-by: Abdul Qadeer qad...@kics.edu.pk --- target-mips/translate.c | 4 1 files changed, 4 insertions(+), 0 deletions(-) diff --git a/target-mips/translate.c b/target-mips/translate.c index d5b1c76..452a63b 100644 --- a/target-mips/translate.c +++ b/target-mips/translate.c @@ -12779,6 +12779,10 @@ void cpu_reset (CPUMIPSState *env) env-hflags |= MIPS_HFLAG_FPU; } #ifdef TARGET_MIPS64 + env-hflags |= MIPS_HFLAG_UX; So for those of us not knowing mips, it's defined as: #define MIPS_HFLAG_UX 0x00200 /* 64-bit user mode */ The code above is inside CONFIG_USER_ONLY, so this looks right for n64 but not for n32 ABI. If you put this into its own patch with a description of ---8--- target-mips: Enable 64 bit user mode for n64 For user mode n64 ABI emulation, MIPS_HFLAG_UX is included in env-hflags so that the address computation for LD instruction does not get treated as 32 bit code, see gen_op_addr_add() in translate.c. Signed-off-by: Abdul Qadeer qad...@kics.edu.pk Signed-off-by: (you) ---8--- and make it depend on TARGET_ABI_MIPSN64 then I will happily add my Acked-by. + /* if cpu has FPU, MIPS_HFLAG_F64 must be included in env-hflags + so that floating point operations can be emulated */ + env-active_fpu.fcr0 = env-cpu_model-CP1_fcr0; if (env-active_fpu.fcr0 (1 FCR0_F64)) { env-hflags |= MIPS_HFLAG_F64; } Nack. env-active_fpu.fcr0 gets initialized in translate_init.c based on cpu_model-CR1_fcr0, where FCR0_F64 is set only for 24Kf, 34Kf, MIPS64R2-generic. TARGET_ABI_MIPSN64 linux-user defaults to 20Kc. So it seems to rather be an issue of using the right -cpu parameter or changing the default for n64. [cc'ing Nathan, who introduced the if] The reason why I add this line env-active_fpu.fcr0 = env-cpu_model-CP1_fcr0 is as follows in translate_init.c fpu_init() initializes active_fpu for given cpu model afterwards cpu_reset() reset the values to zero using this memset(env, 0, offsetof(CPUMIPSState, breakpoints)); so whatever the value of cpu_model-CR1_fcr0 was , the value of env-active_fpu.fcr0 will be zero now thats why I add above line to retrieve the correct env-active_fpu.fcr0 value according to CPU model( whether it is 24Kf or 20Kc or something else) During the development of mips64-linux-user I observed this issue. I gave qemu-mips64 command with -cpu option equal to MIPS64R2-generic and an illegal instruction error occurred, so I used above hunk. Andreas
[Qemu-devel] MIIPS64el compiler
hi any one of you know about MIPS64el cross compiler? I would appreciate your response.. Thanks
Re: [Qemu-devel] [PATCH v3 5/6] target-mips: Adding support for Cavium specific instructions
On Wed, Nov 30, 2011 at 4:54 PM, Andreas Färber andreas.faer...@web.de wrote: Am 22.11.2011 09:31, schrieb Khansa Butt: On Tue, Nov 1, 2011 at 1:24 AM, Andreas Färber andreas.faer...@web.de wrote: Am 28.10.2011 06:42, schrieb Khansa Butt: On Sat, Oct 22, 2011 at 4:36 PM, Andreas Färber andreas.faer...@web.de mailto:andreas.faer...@web.de wrote: Am 22.10.2011 12:11, schrieb kha...@kics.edu.pk mailto:kha...@kics.edu.pk: diff --git a/target-mips/machine.c b/target-mips/machine.c index be72b36..a274ce2 100644 --- a/target-mips/machine.c +++ b/target-mips/machine.c @@ -173,6 +179,12 @@ static void load_tc(QEMUFile *f, TCState *tc) qemu_get_betls(f, tc-CP0_TCSchedule); qemu_get_betls(f, tc-CP0_TCScheFBack); qemu_get_sbe32s(f, tc-CP0_Debug_tcstatus); + qemu_get_betls(f, tc-MPL0); + qemu_get_betls(f, tc-MPL1); + qemu_get_betls(f, tc-MPL2); + qemu_get_betls(f, tc-P0); + qemu_get_betls(f, tc-P1); + qemu_get_betls(f, tc-P2); } static void load_fpu(QEMUFile *f, CPUMIPSFPUContext *fpu) You're saving new fields, so you'll need to bump the version somewhere. For loading, since you're adding at the end, you might be able to make your additions conditional on the to-be-bumped version. I 'm not able to understand bump the version somewhere kindly explain this. Somewhere indicates I don't know the exact line for mips. Compare the recent patch to arm_gic. The general idea is that QEMU needs to be able to load files saved with an older version, the file format is therefore versioned. If you unconditionally try to load your new registers, you break loading older files that don't include them. Thanks for your response. As I can't see any example of bumping the version of registers in mips ( 32 or 64) so i'm in a bit difficult situation From arm_gic what i understand is that version_id is related to devices which are specific to some board as gic is related to RealView board. considering that i'm in user mode, can i do the same thing with Cavium's registers as these are related to multiplier unit? No, this is not board- or device-specific, it's CPU-specific. Cf. target-mips/cpu.h:CPU_SAVE_VERSION target-mips/savevm.c:cpu_load() My suggestion was to bump CPU_SAVE_VERSION to 4, change the error check to if (version_id 3) and to enclose your cpuo_load() additions in if (version_id = 4) { ... }. Thanks for your response! Here is a confusion. I found that cpu_save() and cpu_load() are not called in user mode emulation, here is the code from exec.c #if defined(CPU_SAVE_VERSION) !defined(CONFIG_USER_ONLY) vmstate_register(NULL, cpu_index, vmstate_cpu_common, env); register_savevm(NULL, cpu, cpu_index, CPU_SAVE_VERSION, cpu_save, cpu_load, env); #endif As these patches are related to UME so we decided to postpone Octeon specific changes ( registers and instructions) and will include them in our SME work( we are currently working on system mode emulation of Octeon board) that's why yesterday I sent only MIPS64 user mode emulation patches here is the link http://lists.gnu.org/archive/html/qemu-devel/2011-11/msg03527.html Please review them I'm sorry, the words with Cavium specific instruction support are mistakenly added into subject line. Please guide me towards the right track. should we stick to are old patches or submit MIPS64 UME patches only(which are without Cavium's Instruction support) Depending how long you need to resend, note that Juan is working on a VMState refactoring of machine.c, which will make it more like devices. Andreas
Re: [Qemu-devel] [PATCH v3 5/6] target-mips: Adding support for Cavium specific instructions
On Tue, Nov 1, 2011 at 1:24 AM, Andreas Färber andreas.faer...@web.de wrote: Am 28.10.2011 06:42, schrieb Khansa Butt: On Sat, Oct 22, 2011 at 4:36 PM, Andreas Färber andreas.faer...@web.de mailto:andreas.faer...@web.de wrote: Am 22.10.2011 12:11, schrieb kha...@kics.edu.pk mailto:kha...@kics.edu.pk: HTML again :( From: Khansa Butt kha...@kics.edu.pk mailto:kha...@kics.edu.pk Commit message should mention here at least that new registers are introduced and that load/save format is being changed. Signed-off-by: Khansa Butt kha...@kics.edu.pk mailto:kha...@kics.edu.pk Signed-off-by: Ehsan Ul Haq ehsan.ul...@kics.edu.pk mailto:ehsan.ul...@kics.edu.pk Signed-off-by: Abdul Qadeer qad...@kics.edu.pk mailto:qad...@kics.edu.pk Signed-off-by: Abdul Waheed awah...@kics.edu.pk mailto:awah...@kics.edu.pk --- diff --git a/target-mips/cpu.h b/target-mips/cpu.h index 79e2558..9180ee9 100644 --- a/target-mips/cpu.h +++ b/target-mips/cpu.h @@ -173,6 +173,13 @@ struct TCState { target_ulong CP0_TCSchedule; target_ulong CP0_TCScheFBack; int32_t CP0_Debug_tcstatus; + /* Multiplier registers for Octeon */ + target_ulong MPL0; + target_ulong MPL1; + target_ulong MPL2; + target_ulong P0; + target_ulong P1; + target_ulong P2; }; typedef struct CPUMIPSState CPUMIPSState; diff --git a/target-mips/machine.c b/target-mips/machine.c index be72b36..a274ce2 100644 --- a/target-mips/machine.c +++ b/target-mips/machine.c @@ -25,6 +25,12 @@ static void save_tc(QEMUFile *f, TCState *tc) qemu_put_betls(f, tc-CP0_TCSchedule); qemu_put_betls(f, tc-CP0_TCScheFBack); qemu_put_sbe32s(f, tc-CP0_Debug_tcstatus); + qemu_put_betls(f, tc-MPL0); + qemu_put_betls(f, tc-MPL1); MPL2 is not being saved but loaded below. + qemu_put_betls(f, tc-P0); + qemu_put_betls(f, tc-P1); + qemu_put_betls(f, tc-P2); + } static void save_fpu(QEMUFile *f, CPUMIPSFPUContext *fpu) @@ -173,6 +179,12 @@ static void load_tc(QEMUFile *f, TCState *tc) qemu_get_betls(f, tc-CP0_TCSchedule); qemu_get_betls(f, tc-CP0_TCScheFBack); qemu_get_sbe32s(f, tc-CP0_Debug_tcstatus); + qemu_get_betls(f, tc-MPL0); + qemu_get_betls(f, tc-MPL1); + qemu_get_betls(f, tc-MPL2); + qemu_get_betls(f, tc-P0); + qemu_get_betls(f, tc-P1); + qemu_get_betls(f, tc-P2); } static void load_fpu(QEMUFile *f, CPUMIPSFPUContext *fpu) You're saving new fields, so you'll need to bump the version somewhere. For loading, since you're adding at the end, you might be able to make your additions conditional on the to-be-bumped version. I 'm not able to understand bump the version somewhere kindly explain this. Somewhere indicates I don't know the exact line for mips. Compare the recent patch to arm_gic. The general idea is that QEMU needs to be able to load files saved with an older version, the file format is therefore versioned. If you unconditionally try to load your new registers, you break loading older files that don't include them. Thanks for your response. As I can't see any example of bumping the version of registers in mips ( 32 or 64) so i'm in a bit difficult situation From arm_gic what i understand is that version_id is related to devices which are specific to some board as gic is related to RealView board. considering that i'm in user mode, can i do the same thing with Cavium's registers as these are related to multiplier unit? Also please tell me about mips maintainer, Aurelien Jarno. I think he is not active in developer list for a while. I'm wondering whether those register and serialization additions could and should be limited to TARGET_MIPS64. you want me to limit these registers to TARGET_OCTEON No, there shouldn't be a TARGET_OCTEON, there's no Octeon-specific executable. My point is, IIUC, qemu-system-mips will never have Octeon registers because they're in qemu-system-mips64 only. So without #ifdef it would save and load unused registers. Andreas
Re: [Qemu-devel] [PATCH v3 5/6] target-mips: Adding support for Cavium specific instructions
On Sat, Oct 22, 2011 at 4:36 PM, Andreas Färber andreas.faer...@web.dewrote: Am 22.10.2011 12:11, schrieb kha...@kics.edu.pk: From: Khansa Butt kha...@kics.edu.pk Commit message should mention here at least that new registers are introduced and that load/save format is being changed. Signed-off-by: Khansa Butt kha...@kics.edu.pk Signed-off-by: Ehsan Ul Haq ehsan.ul...@kics.edu.pk Signed-off-by: Abdul Qadeer qad...@kics.edu.pk Signed-off-by: Abdul Waheed awah...@kics.edu.pk --- diff --git a/target-mips/cpu.h b/target-mips/cpu.h index 79e2558..9180ee9 100644 --- a/target-mips/cpu.h +++ b/target-mips/cpu.h @@ -173,6 +173,13 @@ struct TCState { target_ulong CP0_TCSchedule; target_ulong CP0_TCScheFBack; int32_t CP0_Debug_tcstatus; +/* Multiplier registers for Octeon */ +target_ulong MPL0; +target_ulong MPL1; +target_ulong MPL2; +target_ulong P0; +target_ulong P1; +target_ulong P2; }; typedef struct CPUMIPSState CPUMIPSState; diff --git a/target-mips/machine.c b/target-mips/machine.c index be72b36..a274ce2 100644 --- a/target-mips/machine.c +++ b/target-mips/machine.c @@ -25,6 +25,12 @@ static void save_tc(QEMUFile *f, TCState *tc) qemu_put_betls(f, tc-CP0_TCSchedule); qemu_put_betls(f, tc-CP0_TCScheFBack); qemu_put_sbe32s(f, tc-CP0_Debug_tcstatus); +qemu_put_betls(f, tc-MPL0); +qemu_put_betls(f, tc-MPL1); MPL2 is not being saved but loaded below. +qemu_put_betls(f, tc-P0); +qemu_put_betls(f, tc-P1); +qemu_put_betls(f, tc-P2); + } static void save_fpu(QEMUFile *f, CPUMIPSFPUContext *fpu) @@ -173,6 +179,12 @@ static void load_tc(QEMUFile *f, TCState *tc) qemu_get_betls(f, tc-CP0_TCSchedule); qemu_get_betls(f, tc-CP0_TCScheFBack); qemu_get_sbe32s(f, tc-CP0_Debug_tcstatus); +qemu_get_betls(f, tc-MPL0); +qemu_get_betls(f, tc-MPL1); +qemu_get_betls(f, tc-MPL2); +qemu_get_betls(f, tc-P0); +qemu_get_betls(f, tc-P1); +qemu_get_betls(f, tc-P2); } static void load_fpu(QEMUFile *f, CPUMIPSFPUContext *fpu) You're saving new fields, so you'll need to bump the version somewhere. For loading, since you're adding at the end, you might be able to make your additions conditional on the to-be-bumped version. I 'm not able to understand bump the version somewhere kindly explain this. I'm wondering whether those register and serialization additions could and should be limited to TARGET_MIPS64. you want me to limit these registers to TARGET_OCTEON
[Qemu-devel] cross compiler for MIPS64
Hi I'm working on MIPS64 emulation and I need cross compiler for MIPS64. would you please guide me in this regard?. Is there any cross compiler exist or I have to make it from scratch? thanks
Re: [Qemu-devel] [PATCH 4/4] Addition of Cavium instruction in disassembler
On Mon, Aug 15, 2011 at 9:37 PM, Richard Henderson r...@twiddle.net wrote: On 08/15/2011 04:25 AM, kha...@kics.edu.pk wrote: index 1334b8e..0137657 100644 --- a/disas.c +++ b/disas.c @@ -140,6 +140,7 @@ print_insn_thumb1(bfd_vma pc, disassemble_info *info) i386 - nonzero means 16 bit code arm - nonzero means thumb code ppc - nonzero means little endian +mips64 - zero means standard MIPS ISA, 1 means Octeon CPU. ... +++ b/target-mips/translate.c @@ -12860,6 +12860,9 @@ done_generating: LOG_DISAS(\n); if (qemu_loglevel_mask(CPU_LOG_TB_IN_ASM)) { qemu_log(IN: %s\n, lookup_symbol(pc_start)); +if (env-insn_flags CPU_OCTEON) +log_target_disas(pc_start, ctx.pc - pc_start, 1); +else log_target_disas(pc_start, ctx.pc - pc_start, 0); disas.c has access to cpu.h. You'd do well to avoid a magic number here and pass along env-insn_flags right from the beginning, and... @@ -196,6 +197,9 @@ void target_disas(FILE *out, target_ulong code, target_ulong size, int flags) print_insn = print_insn_m68k; #elif defined(TARGET_MIPS) #ifdef TARGET_WORDS_BIGENDIAN +if (flags) +disasm_info.flags = flags 16; +print_insn = print_insn_big_mips; print_insn = print_insn_big_mips; Notice anything funny here in the last two lines? I 'm sorry for this stupid thing as I was in a hurry because of lot of things. Notice anything incorrect about the coding style? It's a bit sad that we're limited to pre-GPLv3, because we're going to get more and more out of sync with the binutils disassembler. But that said, let's not go out of our way to totally change the style. If I pass env-insn_flags to target_disas() how can I pass this flag info from disas.c to mips-dis.c. can i do following thing for MIPS in disas.c if (flags 0x) { disasm_info.mach = flags 0x; Give mips-dis.c access to target-mips/mips-defs.h. Map between that and the existing membership field in struct mips_opcode. Put some real code back into OPCODE_IS_MEMBER. how can I make mips-defs.h 's definitions visible to mips-dis.c? there are lot of similar definitions in both so will it not create problem. Actually some of Cavium 's instructions have same Opcode field as Loongson and COP2 instructions. whenever Cavium 's instruction comes, there is a need to pass info from translate.c to mips-dis.c so that correct instruction would be selected. but at the same time other MIPS standard instructions should also print in the log as Cavium 's ISA includes MIPS64r2. I'm sorry i'm bothering you for this. But i'm stuck with this how to correctly print Cavium instructions instead of Loongson , A workaround that is acceptable to mips maintainer as well. r~
Re: [Qemu-devel] [PATCH 2/4] Octeon cpu definitions in target-mips and Octeon specific changes in set_thread_area syscall
On Mon, Aug 15, 2011 at 8:43 PM, Richard Henderson r...@twiddle.net wrote: On 08/15/2011 04:25 AM, kha...@kics.edu.pk wrote: ((CPUMIPSState *) cpu_env)-tls_value = arg1; + if (((CPUMIPSState *) cpu_env)-insn_flags CPU_OCTEON) { + /* tls entry is moved to k0 so that this can be used later + currently this thing is tested only for Octeon */ + ((CPUMIPSState *) cpu_env)-active_tc.gpr[26] = arg1; + } You wanted INSN_OCTEON, not CPU_OCTEON, which includes CPU_MIPS64R2. That said, this is *not* in the current linux kernel. And I question the wisdom of changing the user-space ABI for TLS for a single CPU. I think you'd better leave this out until it's actually accepted upstream. with out above fix Octeon user mode binary can not be correctly run on QEMU. This was the behavior on actual hardware which we noticed when we were debugging the user mode binary on Octeon board. (there are instructions in user mode ELF of Octeon which read k0 and k1 values) r~
Re: [Qemu-devel] [PATCH 3/3] target-mips:Support for Cavium specific instructions
On Thu, Aug 4, 2011 at 4:22 PM, Peter Maydell peter.mayd...@linaro.orgwrote: On 5 July 2011 10:19, kha...@kics.edu.pk wrote: --- host-utils.c|1 + target-mips/cpu.h |7 + target-mips/helper.h|5 + target-mips/op_helper.c | 67 +++ target-mips/translate.c | 443 ++- 5 files changed, 514 insertions(+), 9 deletions(-) Don't you also need to add support for the new instructions to the disassembler in mips-dis.c ? The ISA for Cavium Networks Octeon Processor consist of MIPS64r2+Cavium specific instructions. These are 27 usermode instructions which we implemented. some of its instructions have some conflicts with mips and LoongSon instructions. for example Branch on bit clear/set instructions (these are 4 instructions) consumes major opcodes of MIPS COP2 instructions (e.g, LWC2 etc). and V3MULU, VMM0 have same opcode and function fields as two of Loongson 's Instructions. To detect correct instruction in disassembling process can I add a CPU specific Flag in DisasContext so that I can pass this to log_target_disas()/disas.c and set some of top 16 bits in disassemble_info 's flags. On the basis of which I can pick correct instruction in print_insn_mips()/mips-dis.c. In future this Flag can be used for other vendor specific instruction as well. Please guide me in this regard. If I make a separate print function for Cavium, this will not suitable for me as Cavium includes all instructions in MIPS64r2 so there will be lot of repetition. Thanks.
Re: [Qemu-devel] Looking for MIPS Maintainer
For Cavium Specific instructions, please see notes in patch 0 and give your comments on target-mips patches. Thanks. On Wed, Aug 3, 2011 at 6:20 PM, Rhonda Wittels rho...@codesourcery.comwrote: On 8/3/2011 6:20 AM, Khansa Butt wrote: Hi! we are waiting for approval of our Patches for MIPS64 user mode emulation. Patch 1(linux-user) has already been reviewed by Riku Voipio but target-mips part is waiting forMIPS maintainer. Please review target-mips patches so that we'll be able to continue our contribution in mips world. here are the Patches in waiting queue. [Qemu-devel] [PATCH 2/3] target-mips:Adding Octeon cpu definitions http://lists.nongnu.org/**archive/html/qemu-devel/2011-** 07/msg00310.htmlhttp://lists.nongnu.org/archive/html/qemu-devel/2011-07/msg00310.html [Qemu-devel] [PATCH 3/3] target-mips:Support for Cavium specific instructions http://lists.nongnu.org/**archive/html/qemu-devel/2011-** 07/msg00311.htmlhttp://lists.nongnu.org/archive/html/qemu-devel/2011-07/msg00311.html sent on Jul 5. Thanks. Nathan Froyd is no longer with CodeSourcery so he will not see mail sent to his old email address.
Re: [Qemu-devel] [PATCH 0/3] MIPS64 user mode emulation in QEMU with Cavium specific instruction support
Hi We have developed Mips64 user mode emulation. In addition we implemented Cavium specific instruction along with octeon CPU definition. We need your support to make our contribution public ally available via making it open source. I tried to resolve the issues pointed out by Aurelien Jarno, Riku, Nathan and other friends and send the patches on Jul 5. Please review the patch series and give your feedback in the form of comments and suggestions Thanks On Tue, Jul 5, 2011 at 2:19 PM, kha...@kics.edu.pk wrote: From: Khansa Butt kha...@kics.edu.pk This is the team work of Ehsan-ul-Haq, Abdul Qadeer, Abdul Waheed, Khansa Butt from HPCN Lab KICS UET Lahore. Cavium Networks's Octeon processors are based on MIPS64r2 We have Implemented 27 user mode Cavium specific instructions. Richard Henderson told me that QEMU does not support 64-bit address spaces in user mode from a 32-bit host. so this code will work only on 64 bit host. Although we did some workaround to run MIPS64 on 32 x86 and it can be generlized for other architectures. We will submit that after this submission. This development work is tested for 64 bit X86 and working fine all Cavium specific instructions are also tested. teast cases can be provided if required. Octeon binaries (ELF) can be downloaded from below links 1)http://dl.dropbox.com/u/19530066/hw_mips 2)http://dl.dropbox.com/u/19530066/matmul If you have any objection regarding the Implementation of Cavium instructions please read following notes. Notes * The detail of some instructions are as follows 1)seq rd,rs,rt seq--rd = 1 if rs = rt is equivalent to xor rd,rs,rt sltiu rd,rd,1 2)exts rt,rs,p,lenm1 rt = sign-extend(rsp+lenm1:p,lenm1) From reference manual of Cavium Networks Bit locations p + lenm1 to p are extracted from rs and the result is written into the lowest bits of destination register rt. The remaining bits in rt are a sign-extension of the most-significant bit of the bit field (i.e. rt63:lenm1 are all duplicates of the source-register bit rsp+lenm1). so we can't use any of 8,16 or 32 bit sign extention tcg function. To sign extend according to msb of bit field we have our own implementation 3)dmul rd,rs,rt This instruction is included in gen_arith() because it is three operand double word multiply instruction. -- 1.7.3.4
Re: [Qemu-devel] [PATCH 1/2] Support for MIPS64 user mode emulation
This is the case for 64 bit guest user mode static binary on 32 bit host. Dynamically linked binary has not this problem see in elfload.c:load_elf_image() for (i = 0; i ehdr-e_phnum; ++i) { if(phdr[i].p_type == PT_INTERP) dyn_link = 1; if (phdr[i].p_type == PT_LOAD) { abi_ulong a = phdr[i].p_vaddr; if (a loaddr) { loaddr = a; } a += phdr[i].p_memsz; if (a hiaddr) { hiaddr = a; } #ifdef CONFIG_USE_FDPIC ++info-nsegs; #endif } } load_addr = loaddr; at this point load_addr has 64 bit value. if (!have_guest_base !reserved_va) { unsigned long host_start, real_start, host_size; /* Round addresses to page boundaries. */ loaddr = qemu_host_page_mask; hiaddr = HOST_PAGE_ALIGN(hiaddr); because of above loaddr is rounded to 32 bit value and load_bias = load_addr - loaddr; now load_addr has a big value which is added to entry point address which causes problem. for my MIPS64 bit statically linked ELF the variables loaddr and hiaddr have 36 bit values. for probing guest_base these values are rounded to 32 bit as my underlying OS is 32 bit Fedore13 because of this load_bais has value = 0x1 this load_bias is then added to entry point address and mem and file size of the segment. and the addresses which are starting from 0x12000 are now changed to 0x22000. because of this when lladdr comes to SCD instruction in do_store_exclusive() it does not get valid l1_map entry. and because of which we made a fake page which was not correct way to do although it was working. so we did another workaround as follows linux-user/elfload.c |6 +- 1 files changed, 5 insertions(+), 1 deletions(-) diff --git a/linux-user/elfload.c b/linux-user/elfload.c index dcfeb7a..9ab3296 100644 --- a/linux-user/elfload.c +++ b/linux-user/elfload.c @@ -1307,7 +1307,7 @@ static void load_elf_image(const char *image_name, int image_fd, struct elfhdr *ehdr = (struct elfhdr *)bprm_buf; struct elf_phdr *phdr; abi_ulong load_addr, load_bias, loaddr, hiaddr, error; -int i, retval; +int i, retval, dyn_link; const char *errmsg; /* First of all, some simple consistency checks */ @@ -1341,6 +1341,8 @@ static void load_elf_image(const char *image_name, int image_fd, amount of memory to handle that. */ loaddr = -1, hiaddr = 0; for (i = 0; i ehdr-e_phnum; ++i) { +if(phdr[i].p_type == PT_INTERP) /* Is the ELF dynamically linked? +dyn_link = 1; if (phdr[i].p_type == PT_LOAD) { abi_ulong a = phdr[i].p_vaddr; if (a loaddr) { @@ -1395,6 +1397,8 @@ static void load_elf_image(const char *image_name, int image_fd, } } host_size = hiaddr - loaddr; +if (!dyn_link) +/* ELF is statically linked */ +load_addr = loaddr; while (1) { /* Do not use mmap_find_vma here because that is limited to the guest address space. We are going to make the -- 1.7.0.1 please give some comments regarding this workaround
[Qemu-devel] [Bug 796480] [NEW] Addresses with 4GB differences are consider as one single address in QEMU
Public bug reported: THIS IS THE ISSUE OF USER MODE EMULATION Information about guest and host ** guest: 64 bit x86 user mode binary host: 32 bit Linux OS uname -a :Linux KICS-HPCNL-32blue 2.6.33.3-85.fc13.i686.PAE #1 SMP architecture: intel64 Bug Description for memory reference instructions, suppose I have two addresses in guest address space(64 bit) 0x22000 0x32000 as lower 32 bit part of both addresses are same, when particular instructions are translated into host code(32 bit) in both above cases the value is loaded from same memory and we get same value. where actual behaviour was to get two different values. here is the program which i used to test: #include stdio.h #include stdlib.h #include limits.h #define SIZE 4294967298 /* 4Gib*/ int main() { char *array; unsigned int i; array = malloc(sizeof(char) * SIZE); if(array == NULL){ fprintf(stderr, Could not allocate that much memory); return 1;} array[0] = 'a'; array[SIZE-2] = 'z'; printf(array[SIZE-2] = %c array[0] = %c\n,array[SIZE-2], array[0]); return 0; } I have 8 gib RAM I compiled this program on 64 bit linux and run this on 32 bit linux with qemu QEMU command line and output ** $x86_64-linux-user/qemu-x86_64 ~/ar_x86 output: array[SIZE-1] = z,array[0] = z Release information x86_64 binary is tested with latest release : qemu-0.14.1 and with current development tree as well( live code of QEMU using git) ** Affects: qemu Importance: Undecided Status: New -- You received this bug notification because you are a member of qemu- devel-ml, which is subscribed to QEMU. https://bugs.launchpad.net/bugs/796480 Title: Addresses with 4GB differences are consider as one single address in QEMU Status in QEMU: New Bug description: THIS IS THE ISSUE OF USER MODE EMULATION Information about guest and host ** guest: 64 bit x86 user mode binary host: 32 bit Linux OS uname -a :Linux KICS-HPCNL-32blue 2.6.33.3-85.fc13.i686.PAE #1 SMP architecture: intel64 Bug Description for memory reference instructions, suppose I have two addresses in guest address space(64 bit) 0x22000 0x32000 as lower 32 bit part of both addresses are same, when particular instructions are translated into host code(32 bit) in both above cases the value is loaded from same memory and we get same value. where actual behaviour was to get two different values. here is the program which i used to test: #include stdio.h #include stdlib.h #include limits.h #define SIZE 4294967298 /* 4Gib*/ int main() { char *array; unsigned int i; array = malloc(sizeof(char) * SIZE); if(array == NULL){ fprintf(stderr, Could not allocate that much memory); return 1;} array[0] = 'a'; array[SIZE-2] = 'z'; printf(array[SIZE-2] = %c array[0] = %c\n,array[SIZE-2], array[0]); return 0; } I have 8 gib RAM I compiled this program on 64 bit linux and run this on 32 bit linux with qemu QEMU command line and output ** $x86_64-linux-user/qemu-x86_64 ~/ar_x86 output: array[SIZE-1] = z,array[0] = z Release information x86_64 binary is tested with latest release : qemu-0.14.1 and with current development tree as well( live code of QEMU using git) To manage notifications about this bug go to: https://bugs.launchpad.net/qemu/+bug/796480/+subscriptions
[Qemu-devel] [Bug 796480] Re: Addresses with 4GB differences are consider as one single address in QEMU
** Description changed: THIS IS THE ISSUE OF USER MODE EMULATION Information about guest and host ** guest: 64 bit x86 user mode binary host: 32 bit Linux OS uname -a :Linux KICS-HPCNL-32blue 2.6.33.3-85.fc13.i686.PAE #1 SMP architecture: intel64 Bug Description for memory reference instructions, suppose I have two addresses in guest address space(64 bit) 0x22000 0x32000 as lower 32 bit part of both addresses are same, when particular instructions are translated into host code(32 bit) in both above cases the value is loaded from same memory and we get same value. where actual behaviour was to get two different values. here is the program which i used to test: #include stdio.h #include stdlib.h #include limits.h - #define SIZE 4294967298 /* 4Gib*/ + #define SIZE 4294967297 /* 4Gib*/ int main() { char *array; unsigned int i; array = malloc(sizeof(char) * SIZE); if(array == NULL){ fprintf(stderr, Could not allocate that much memory); return 1;} array[0] = 'a'; array[SIZE-2] = 'z'; printf(array[SIZE-2] = %c array[0] = %c\n,array[SIZE-2], array[0]); return 0; } I have 8 gib RAM I compiled this program on 64 bit linux and run this on 32 bit linux with qemu QEMU command line and output ** $x86_64-linux-user/qemu-x86_64 ~/ar_x86 output: array[SIZE-1] = z,array[0] = z Release information x86_64 binary is tested with latest release : qemu-0.14.1 and with current development tree as well( live code of QEMU using git) ** Description changed: THIS IS THE ISSUE OF USER MODE EMULATION Information about guest and host ** guest: 64 bit x86 user mode binary host: 32 bit Linux OS uname -a :Linux KICS-HPCNL-32blue 2.6.33.3-85.fc13.i686.PAE #1 SMP architecture: intel64 Bug Description for memory reference instructions, suppose I have two addresses in guest address space(64 bit) 0x22000 0x32000 as lower 32 bit part of both addresses are same, when particular instructions are translated into host code(32 bit) in both above cases the value is loaded from same memory and we get same value. where actual behaviour was to get two different values. here is the program which i used to test: #include stdio.h #include stdlib.h #include limits.h #define SIZE 4294967297 /* 4Gib*/ int main() { char *array; unsigned int i; array = malloc(sizeof(char) * SIZE); if(array == NULL){ fprintf(stderr, Could not allocate that much memory); return 1;} array[0] = 'a'; -array[SIZE-2] = 'z'; -printf(array[SIZE-2] = %c array[0] = %c\n,array[SIZE-2], array[0]); +array[SIZE-1] = 'z'; +printf(array[SIZE-1] = %c array[0] = %c\n,array[SIZE-1], array[0]); return 0; } I have 8 gib RAM I compiled this program on 64 bit linux and run this on 32 bit linux with qemu QEMU command line and output ** $x86_64-linux-user/qemu-x86_64 ~/ar_x86 output: array[SIZE-1] = z,array[0] = z Release information x86_64 binary is tested with latest release : qemu-0.14.1 and with current development tree as well( live code of QEMU using git) -- You received this bug notification because you are a member of qemu- devel-ml, which is subscribed to QEMU. https://bugs.launchpad.net/bugs/796480 Title: Addresses with 4GB differences are consider as one single address in QEMU Status in QEMU: New Bug description: THIS IS THE ISSUE OF USER MODE EMULATION Information about guest and host ** guest: 64 bit x86 user mode binary host: 32 bit Linux OS uname -a :Linux KICS-HPCNL-32blue 2.6.33.3-85.fc13.i686.PAE #1 SMP architecture: intel64 Bug Description for memory reference instructions, suppose I have two addresses in guest address space(64 bit) 0x22000 0x32000 as lower 32 bit part of both addresses are same, when particular instructions are translated into host code(32 bit) in both above cases the value is loaded from same memory and we get same value. where actual behaviour was to get two different values. here is the program which i used to test: #include stdio.h #include stdlib.h #include limits.h #define SIZE 4294967297 /* 4Gib*/ int main() { char *array; unsigned int i; array = malloc(sizeof(char) * SIZE); if(array == NULL){ fprintf(stderr, Could not allocate that much memory); return 1;} array[0] = 'a'; array[SIZE-1] = 'z'; printf(array[SIZE-1] = %c array[0] = %c\n,array[SIZE-1], array[0]); return 0; } I have 8 gib RAM I compiled this program on 64 bit linux and run this on 32 bit linux with qemu QEMU command
Re: [Qemu-devel] [PATCH 1/2] Support for MIPS64 user mode emulation
please see inline comments at the end. On Fri, Apr 29, 2011 at 2:01 PM, Aurelien Jarno aurel...@aurel32.netwrote: On Mon, Apr 25, 2011 at 04:54:19PM +0500, Khansa Butt wrote: please see inline comments highlighted in red color. On Wed, Apr 13, 2011 at 2:32 AM, Aurelien Jarno aurel...@aurel32.net wrote: [I don't know very well linux-user, it would be nice to Cc: Riku Voipio, the linux-user maintainer for the next version.] On Sat, Apr 09, 2011 at 04:02:31PM +0500, Khansa Butt wrote: From e96e20e50cada1c9e1b65de5925281cdd5659746 Mon Sep 17 00:00:00 2001 From: Ehsan-ul-Haq Khansa Butt kha...@kics.edu.pk Date: Sat, 9 Apr 2011 10:51:22 +0500 Subject: [PATCH 1/2] Support for MIPS64 user mode emulation Signed-off-by: Ehsan-ul-Haq, Abdul Qadeer, Abdul Waheed, Khansa Butt kha...@kics.edu.pk --- configure |1 + default-configs/mips64-linux-user.mak |1 + linux-user/elfload.c |2 +- linux-user/main.c | 29 +++-- linux-user/mips64/syscall.h |3 +++ linux-user/signal.c |3 ++- target-mips/translate.c |1 + 7 files changed, 36 insertions(+), 4 deletions(-) create mode 100644 default-configs/mips64-linux-user.mak diff --git a/configure b/configure index ae97e11..d1f7867 100755 --- a/configure +++ b/configure @@ -1039,6 +1039,7 @@ m68k-linux-user \ microblaze-linux-user \ microblazeel-linux-user \ mips-linux-user \ +mips64-linux-user \ mipsel-linux-user \ ppc-linux-user \ ppc64-linux-user \ diff --git a/default-configs/mips64-linux-user.mak b/default-configs/mips64-linux-user.mak new file mode 100644 index 000..1598bfc --- /dev/null +++ b/default-configs/mips64-linux-user.mak @@ -0,0 +1 @@ +# Default configuration for mips64-linux-user diff --git a/linux-user/elfload.c b/linux-user/elfload.c index fe5410e..2832a33 100644 --- a/linux-user/elfload.c +++ b/linux-user/elfload.c @@ -1384,7 +1384,7 @@ static void load_elf_image(const char *image_name, int image_fd, vaddr_po = TARGET_ELF_PAGEOFFSET(vaddr); vaddr_ps = TARGET_ELF_PAGESTART(vaddr); -error = target_mmap(vaddr_ps, eppnt-p_filesz + vaddr_po, +error = target_mmap(vaddr_ps, eppnt-p_memsz + vaddr_po, What is the goal of this change? If the mmapped aread is bigger than the file size rounded up to te page size, it will cause a SIGBUS. elf_prot, MAP_PRIVATE | MAP_FIXED, image_fd, eppnt-p_offset - vaddr_po); if (error == -1) { diff --git a/linux-user/main.c b/linux-user/main.c index e651bfd..a7f4955 100644 --- a/linux-user/main.c +++ b/linux-user/main.c @@ -1937,6 +1937,14 @@ static int do_store_exclusive(CPUMIPSState *env) int d; addr = env-lladdr; +#if defined(TARGET_MIPS64) +/* For MIPS64 on 32 bit host there is a need to make +* the page accessible to which the above 'addr' is belonged */ +#if HOST_LONG_BITS == 32 +int flag = PAGE_VALID | PAGE_READ | PAGE_WRITE | PAGE_WRITE_ORG; +page_set_flags(addr, addr + 4096, flag); +#endif +#endif I don't really see the reason why this should be done that way. Are you trying to run MIPS32 binaries compiled for 8kB page size? this change is needed when we run MIPS64 ELF on 32 bit x86 host. MIPS64 ELF contains 36 bit address. Actually it can contains up to 62-bit address there (all the user mapped space). load_elf_image() at /home/khansa/testpatch/qemu/linux-user/elfload.c: QEMU contains these lines /* Round addresses to page boundaries. */ loaddr = qemu_host_page_mask; hiaddr = HOST_PAGE_ALIGN(hiaddr); when QEMU run on 32 bit x86 the above two variables are rounded to 32 bit value while these should be 36 bits as these come from MIPS64 ELF.and then It is correct to truncate them, as the address space of the host is smaller. It's just based on the fact that programs only need a subset of the 62 bit address space. for these rounded address l1_map is initialized in page_find_alloc(). in case of SCD(store condition double ) instruction of MIPS64r2 when we have to check load linked address its again 36 bit so it will make an index(addr TARGET_PAGE_BITS) for which l1_map is no valid entry, returning 0 value and we got segmentation fault. this is the reason we did following changes in main.c do_store_exclusive() No, the load linked address register size, as well as the shift is actually implementation dependent. On old 64-bit MIPS implementation and MIPS32 core it is a 32-bit register and a 4-bit shift
[Qemu-devel] Cavium-Octeon support in QEMU
hi I have sent corrected patches regarding MIPS64 user mode emulation with Octeon support. But i got no further review on these Patches the date of mailed patches is 29th of April. the subjects of my mails are as follow *[PATCH 1/3](Corrected version) linux-user:Support for MIPS64 user mode emulation in QEMUhttp://lists.gnu.org/archive/html/qemu-devel/2011-04/msg02545.html * *[PATCH 2/3] target-mips:Support for Cavium-Octeon specific instructionshttp://lists.gnu.org/archive/html/qemu-devel/2011-04/msg02543.html * please give comments on these patches
Re: [Qemu-devel] [PATCH 1/2] Support for MIPS64 user mode emulation
I have made following changes addr = env-lladdr; addr = qemu_host_page_mask; page_addr = addr TARGET_PAGE_MASK; start_exclusive(); mmap_lock(); flags = page_get_flags(page_addr); now return to elfload.c I have a simple hello world mips64 binary for which I have two loadable segments so following rounded off address ranges passed to page_set_flags() in target_mmap() 1) 0x2000 - 0x2008d000 2) 0x2009c000 - 0x200a6000 the last addresses of these ranges are not included in l1_map because of the for loop condition in page_set_flags() for (addr = start, len = end - start; len != 0; len -= TARGET_PAGE_SIZE, addr += TARGET_PAGE_SIZE) { while env-lladdr after rounding off belong to 0x200a6000 so in order to include last address of above range i made following change error = target_mmap(vaddr_ps, eppnt-p_memsz + v addr_po, elf_prot, MAP_PRIVATE | MAP_FIXED, image_fd, eppnt-p_offset - vaddr_po); as mem size of a segment is greater than its file size but you told me that it will cause SIGBUS please suggest some solution for me in order to avoid target_mmap() change(i.e. filesz to memsz) or can I change condition of for loop some how so that one more iteration will run for the last address. On Fri, Apr 29, 2011 at 2:01 PM, Aurelien Jarno aurel...@aurel32.netwrote: On Mon, Apr 25, 2011 at 04:54:19PM +0500, Khansa Butt wrote: please see inline comments highlighted in red color. On Wed, Apr 13, 2011 at 2:32 AM, Aurelien Jarno aurel...@aurel32.net wrote: [I don't know very well linux-user, it would be nice to Cc: Riku Voipio, the linux-user maintainer for the next version.] On Sat, Apr 09, 2011 at 04:02:31PM +0500, Khansa Butt wrote: From e96e20e50cada1c9e1b65de5925281cdd5659746 Mon Sep 17 00:00:00 2001 From: Ehsan-ul-Haq Khansa Butt kha...@kics.edu.pk Date: Sat, 9 Apr 2011 10:51:22 +0500 Subject: [PATCH 1/2] Support for MIPS64 user mode emulation Signed-off-by: Ehsan-ul-Haq, Abdul Qadeer, Abdul Waheed, Khansa Butt kha...@kics.edu.pk --- configure |1 + default-configs/mips64-linux-user.mak |1 + linux-user/elfload.c |2 +- linux-user/main.c | 29 +++-- linux-user/mips64/syscall.h |3 +++ linux-user/signal.c |3 ++- target-mips/translate.c |1 + 7 files changed, 36 insertions(+), 4 deletions(-) create mode 100644 default-configs/mips64-linux-user.mak diff --git a/configure b/configure index ae97e11..d1f7867 100755 --- a/configure +++ b/configure @@ -1039,6 +1039,7 @@ m68k-linux-user \ microblaze-linux-user \ microblazeel-linux-user \ mips-linux-user \ +mips64-linux-user \ mipsel-linux-user \ ppc-linux-user \ ppc64-linux-user \ diff --git a/default-configs/mips64-linux-user.mak b/default-configs/mips64-linux-user.mak new file mode 100644 index 000..1598bfc --- /dev/null +++ b/default-configs/mips64-linux-user.mak @@ -0,0 +1 @@ +# Default configuration for mips64-linux-user diff --git a/linux-user/elfload.c b/linux-user/elfload.c index fe5410e..2832a33 100644 --- a/linux-user/elfload.c +++ b/linux-user/elfload.c @@ -1384,7 +1384,7 @@ static void load_elf_image(const char *image_name, int image_fd, vaddr_po = TARGET_ELF_PAGEOFFSET(vaddr); vaddr_ps = TARGET_ELF_PAGESTART(vaddr); -error = target_mmap(vaddr_ps, eppnt-p_filesz + vaddr_po, +error = target_mmap(vaddr_ps, eppnt-p_memsz + vaddr_po, What is the goal of this change? If the mmapped aread is bigger than the file size rounded up to te page size, it will cause a SIGBUS. elf_prot, MAP_PRIVATE | MAP_FIXED, image_fd, eppnt-p_offset - vaddr_po); if (error == -1) { diff --git a/linux-user/main.c b/linux-user/main.c index e651bfd..a7f4955 100644 --- a/linux-user/main.c +++ b/linux-user/main.c @@ -1937,6 +1937,14 @@ static int do_store_exclusive(CPUMIPSState *env) int d; addr = env-lladdr; +#if defined(TARGET_MIPS64) +/* For MIPS64 on 32 bit host there is a need to make +* the page accessible to which the above 'addr' is belonged */ +#if HOST_LONG_BITS == 32 +int flag = PAGE_VALID | PAGE_READ | PAGE_WRITE | PAGE_WRITE_ORG; +page_set_flags(addr, addr + 4096, flag); +#endif +#endif I don't really see the reason why this should be done that way. Are you trying to run MIPS32 binaries compiled for 8kB page size? this change is needed when we run MIPS64 ELF on 32 bit x86 host. MIPS64 ELF contains 36 bit address. Actually it can contains up
[Qemu-devel] [PATCH 1/3] linux-user:Support for MIPS64 user mode emulation in QEMU
From fbd2b81503b1f55368b83903ded723f60de8aea7 Mon Sep 17 00:00:00 2001 From: Ehsan-ul-Haq, Abdul Qadeer, Abdul Waheed, Khansa Butt kha...@kics.edu.pk Date: Fri, 29 Apr 2011 11:17:56 +0500 Subject: [PATCH 1/3] linux-user:Support for MIPS64 user mode emulation in QEMU Signed-off-by: Khansa Butt kha...@kics.edu.pk --- configure|1 + linux-user/main.c| 26 +- linux-user/mips64/syscall.h |3 +++ linux-user/signal.c |2 -- linux-user/syscall.c |5 + target-mips/mips-defs.h |2 ++ target-mips/translate.c |1 + target-mips/translate_init.c | 26 ++ 8 files changed, 63 insertions(+), 3 deletions(-) diff --git a/configure b/configure index de44bac..631417b 100755 --- a/configure +++ b/configure @@ -1043,6 +1043,7 @@ m68k-linux-user \ microblaze-linux-user \ microblazeel-linux-user \ mips-linux-user \ +mips64-linux-user \ mipsel-linux-user \ ppc-linux-user \ ppc64-linux-user \ diff --git a/linux-user/main.c b/linux-user/main.c index a1e37e4..253e796 100644 --- a/linux-user/main.c +++ b/linux-user/main.c @@ -2014,6 +2014,14 @@ static int do_store_exclusive(CPUMIPSState *env) int d; addr = env-lladdr; +#if defined(TARGET_MIPS64) +/* For MIPS64 on 32 bit host there is a need to make +* the page accessible to which the above 'addr' is belonged */ +#if HOST_LONG_BITS == 32 +int flag = PAGE_VALID | PAGE_READ | PAGE_WRITE | PAGE_WRITE_ORG; +page_set_flags(addr, addr + 4096, flag); +#endif +#endif page_addr = addr TARGET_PAGE_MASK; start_exclusive(); mmap_lock(); @@ -2055,7 +2063,8 @@ static int do_store_exclusive(CPUMIPSState *env) void cpu_loop(CPUMIPSState *env) { target_siginfo_t info; -int trapnr, ret; +int trapnr; +abi_long ret; unsigned int syscall_num; for(;;) { @@ -2064,6 +2073,20 @@ void cpu_loop(CPUMIPSState *env) cpu_exec_end(env); switch(trapnr) { case EXCP_SYSCALL: +#if defined(TARGET_MIPS64) +syscall_num = env-active_tc.gpr[2] - 5000; +env-active_tc.PC += 4; +/* MIPS64 has eight argument registers so there is + * no need to get arguments from stack + */ +ret = do_syscall(env, env-active_tc.gpr[2], + env-active_tc.gpr[4], + env-active_tc.gpr[5], + env-active_tc.gpr[6], + env-active_tc.gpr[7], + env-active_tc.gpr[8], + env-active_tc.gpr[9]); +#else syscall_num = env-active_tc.gpr[2] - 4000; env-active_tc.PC += 4; if (syscall_num = sizeof(mips_syscall_args)) { @@ -2092,6 +2115,7 @@ void cpu_loop(CPUMIPSState *env) env-active_tc.gpr[7], arg5, arg6/*, arg7, arg8*/); } +#endif if (ret == -TARGET_QEMU_ESIGRETURN) { /* Returning from a successful sigreturn syscall. Avoid clobbering register state. */ diff --git a/linux-user/mips64/syscall.h b/linux-user/mips64/syscall.h index 668a2b9..ec65653 100644 --- a/linux-user/mips64/syscall.h +++ b/linux-user/mips64/syscall.h @@ -218,4 +218,7 @@ struct target_pt_regs { +/* Nasty hack: define a fake errno value for use by sigreturn. */ +#define TARGET_QEMU_ESIGRETURN 255 + #define UNAME_MACHINE mips64 diff --git a/linux-user/signal.c b/linux-user/signal.c index ce033e9..66786db 100644 --- a/linux-user/signal.c +++ b/linux-user/signal.c @@ -2413,8 +2413,6 @@ void sparc64_get_context(CPUSPARCState *env) #endif #elif defined(TARGET_ABI_MIPSN64) -# warning signal handling not implemented - static void setup_frame(int sig, struct target_sigaction *ka, target_sigset_t *set, CPUState *env) { diff --git a/linux-user/syscall.c b/linux-user/syscall.c index bb0999d..cfa925e 100644 --- a/linux-user/syscall.c +++ b/linux-user/syscall.c @@ -7320,6 +7320,11 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1, case TARGET_NR_set_thread_area: #if defined(TARGET_MIPS) ((CPUMIPSState *) cpu_env)-tls_value = arg1; + if (((CPUMIPSState *) cpu_env)-insn_flags CPU_OCTEON) { + /* tls entry is moved to k0 so that this can be used later + currently this thing is tested only for Octeon */ + ((CPUMIPSState *) cpu_env)-active_tc.gpr[26] = arg1; + } ret = 0; break; #elif defined(TARGET_CRIS) diff --git a/target-mips/mips-defs.h b/target-mips/mips-defs.h index bf094a3..a93e863 100644 --- a/target-mips/mips-defs.h +++ b/target-mips/mips-defs.h @@ -44,6 +44,7 @@ #define INSN_LOONGSON2E 0x2000 #define INSN_LOONGSON2F 0x4000 #define INSN_VR54XX 0x8000 +#define INSN_OCTEON 0x1000 /* MIPS CPU defines. */ #define CPU_MIPS1 (ISA_MIPS1) @@ -53,6 +54,7 @@ #define
[Qemu-devel] [PATCH 3/3] linux-user:Signal handling for MIPS64
From 1ab1973118d9e676fcaaf234d153c8c7056aa82a Mon Sep 17 00:00:00 2001 From: Ehsan-ul-Haq, Abdul Qadeer, Abdul Waheed, Khansa Butt kha...@kics.edu.pk Date: Fri, 29 Apr 2011 10:52:38 +0500 Subject: [PATCH 3/3] linux-user:Signal handling for MIPS64 Signed-off-by: Khansa Butt kha...@kics.edu.pk --- linux-user/signal.c | 331 +++-- linux-user/syscall_defs.h |4 + 2 files changed, 325 insertions(+), 10 deletions(-) diff --git a/linux-user/signal.c b/linux-user/signal.c index 66786db..e387a5b 100644 --- a/linux-user/signal.c +++ b/linux-user/signal.c @@ -221,7 +221,11 @@ static inline void host_to_target_siginfo_noswap(target_siginfo_t *tinfo, /* XXX: potential problem if 64 bit */ tinfo-_sifields._rt._sigval.sival_ptr = (abi_ulong)(unsigned long)info-si_value.sival_ptr; +} else { +tinfo-_sifields._kill._pid = info-si_pid; +tinfo-_sifields._kill._uid = info-si_uid; } + } static void tswap_siginfo(target_siginfo_t *tinfo, @@ -243,6 +247,9 @@ static void tswap_siginfo(target_siginfo_t *tinfo, tinfo-_sifields._rt._uid = tswap32(info-_sifields._rt._uid); tinfo-_sifields._rt._sigval.sival_ptr = tswapl(info-_sifields._rt._sigval.sival_ptr); +} else { +tinfo-_sifields._kill._pid = tswap32(info-_sifields._kill._pid); +tinfo-_sifields._kill._uid = tswap32(info-_sifields._kill._uid); } } @@ -2413,28 +2420,332 @@ void sparc64_get_context(CPUSPARCState *env) #endif #elif defined(TARGET_ABI_MIPSN64) -static void setup_frame(int sig, struct target_sigaction *ka, - target_sigset_t *set, CPUState *env) +struct target_sigcontext { +uint32_t sc_regmask; /* Unused */ +uint32_t sc_status; +uint64_t sc_pc; +uint64_t sc_regs[32]; +uint64_t sc_fpregs[32]; +uint32_t sc_ownedfp; /* Unused */ +uint32_t sc_fpc_csr; +uint32_t sc_fpc_eir; /* Unused */ +uint32_t sc_used_math; +uint32_t sc_dsp; /* dsp status, was sc_ssflags */ +uint32_t pad0; +uint64_t sc_mdhi; +uint64_t sc_mdlo; +target_ulong sc_hi1; /* Was sc_cause */ +target_ulong sc_lo1; /* Was sc_badvaddr */ +target_ulong sc_hi2; /* Was sc_sigset[4] */ +target_ulong sc_lo2; +target_ulong sc_hi3; +target_ulong sc_lo3; +}; + +struct target_ucontext { +target_ulong tuc_flags; +target_ulong tuc_link; +target_stack_t tuc_stack; +struct target_sigcontext tuc_mcontext; +target_sigset_t tuc_sigmask; +}; + +struct target_rt_sigframe { +uint64_t rs_ass[8]; /* argument save space for n64 */ +uint32_t rs_code[2]; /* signal trampoline */ +struct target_siginfo rs_info; +struct target_ucontext rs_uc; +}; + +/* Install trampoline to jump back from signal handler */ +static inline int install_sigtramp(unsigned int *tramp, unsigned int syscall) { -fprintf(stderr, setup_frame: not implemented\n); +int err; + +/* +* Set up the return code ... +* +* li v0, __NR__foo_sigreturn +* syscall +*/ + +err = __put_user(0x2402 + syscall, tramp + 0); +err |= __put_user(0x000c , tramp + 1); +/* flush_cache_sigtramp((unsigned long) tramp); */ +return err; +} + +static inline int +setup_sigcontext(CPUState *regs, struct target_sigcontext *sc) +{ +int err = 0; + +err |= __put_user(regs-active_tc.PC, sc-sc_pc); + +#define save_gp_reg(i) do { \ +err |= __put_user(regs-active_tc.gpr[i], sc-sc_regs[i]); \ +} while (0) +__put_user(0, sc-sc_regs[0]); save_gp_reg(1); save_gp_reg(2); +save_gp_reg(3); save_gp_reg(4); save_gp_reg(5); save_gp_reg(6); +save_gp_reg(7); save_gp_reg(8); save_gp_reg(9); save_gp_reg(10); +save_gp_reg(11); save_gp_reg(12); save_gp_reg(13); save_gp_reg(14); +save_gp_reg(15); save_gp_reg(16); save_gp_reg(17); save_gp_reg(18); +save_gp_reg(19); save_gp_reg(20); save_gp_reg(21); save_gp_reg(22); +save_gp_reg(23); save_gp_reg(24); save_gp_reg(25); save_gp_reg(26); +save_gp_reg(27); save_gp_reg(28); save_gp_reg(29); save_gp_reg(30); +save_gp_reg(31); +#undef save_gp_reg + +err |= __put_user(regs-active_tc.HI[0], sc-sc_mdhi); +err |= __put_user(regs-active_tc.LO[0], sc-sc_mdlo); + +/* Not used yet, but might be useful if we ever have DSP suppport */ +#if 0 +if (cpu_has_dsp) { +err |= __put_user(mfhi1(), sc-sc_hi1); +err |= __put_user(mflo1(), sc-sc_lo1); +err |= __put_user(mfhi2(), sc-sc_hi2); +err |= __put_user(mflo2(), sc-sc_lo2); +err |= __put_user(mfhi3(), sc-sc_hi3); +err |= __put_user(mflo3(), sc-sc_lo3); +err |= __put_user(rddsp(DSP_MASK), sc-sc_dsp); +} +/* same with 64 bit */ +#ifdef CONFIG_64BIT +err |= __put_user(regs-hi, sc-sc_hi[0]); +err |= __put_user(regs-lo, sc-sc_lo[0
[Qemu-devel] [PATCH 1/3](Corrected version) linux-user:Support for MIPS64 user mode emulation in QEMU
From 52cca3fab46f65b493cd21096389ee459279cbb2 Mon Sep 17 00:00:00 2001 From: Ehsan-ul-Haq, Abdul Qadeer, Abdul Waheed, Khansa Butt kha...@kics.edu.pk Date: Fri, 29 Apr 2011 11:48:54 +0500 Subject: [PATCH 1/3] linux-user:Support for MIPS64 user mode emulation in QEMU Signed-off-by: Khansa Butt kha...@kics.edu.pk --- configure |1 + default-configs/mips64-linux-user.mak |1 + linux-user/main.c | 26 +- linux-user/mips64/syscall.h |3 +++ linux-user/signal.c |2 -- linux-user/syscall.c |5 + target-mips/mips-defs.h |2 ++ target-mips/translate.c |1 + target-mips/translate_init.c | 26 ++ 9 files changed, 64 insertions(+), 3 deletions(-) create mode 100644 default-configs/mips64-linux-user.mak diff --git a/configure b/configure index de44bac..631417b 100755 --- a/configure +++ b/configure @@ -1043,6 +1043,7 @@ m68k-linux-user \ microblaze-linux-user \ microblazeel-linux-user \ mips-linux-user \ +mips64-linux-user \ mipsel-linux-user \ ppc-linux-user \ ppc64-linux-user \ diff --git a/default-configs/mips64-linux-user.mak b/default-configs/mips64-linux-user.mak new file mode 100644 index 000..1598bfc --- /dev/null +++ b/default-configs/mips64-linux-user.mak @@ -0,0 +1 @@ +# Default configuration for mips64-linux-user diff --git a/linux-user/main.c b/linux-user/main.c index a1e37e4..253e796 100644 --- a/linux-user/main.c +++ b/linux-user/main.c @@ -2014,6 +2014,14 @@ static int do_store_exclusive(CPUMIPSState *env) int d; addr = env-lladdr; +#if defined(TARGET_MIPS64) +/* For MIPS64 on 32 bit host there is a need to make +* the page accessible to which the above 'addr' is belonged */ +#if HOST_LONG_BITS == 32 +int flag = PAGE_VALID | PAGE_READ | PAGE_WRITE | PAGE_WRITE_ORG; +page_set_flags(addr, addr + 4096, flag); +#endif +#endif page_addr = addr TARGET_PAGE_MASK; start_exclusive(); mmap_lock(); @@ -2055,7 +2063,8 @@ static int do_store_exclusive(CPUMIPSState *env) void cpu_loop(CPUMIPSState *env) { target_siginfo_t info; -int trapnr, ret; +int trapnr; +abi_long ret; unsigned int syscall_num; for(;;) { @@ -2064,6 +2073,20 @@ void cpu_loop(CPUMIPSState *env) cpu_exec_end(env); switch(trapnr) { case EXCP_SYSCALL: +#if defined(TARGET_MIPS64) +syscall_num = env-active_tc.gpr[2] - 5000; +env-active_tc.PC += 4; +/* MIPS64 has eight argument registers so there is + * no need to get arguments from stack + */ +ret = do_syscall(env, env-active_tc.gpr[2], + env-active_tc.gpr[4], + env-active_tc.gpr[5], + env-active_tc.gpr[6], + env-active_tc.gpr[7], + env-active_tc.gpr[8], + env-active_tc.gpr[9]); +#else syscall_num = env-active_tc.gpr[2] - 4000; env-active_tc.PC += 4; if (syscall_num = sizeof(mips_syscall_args)) { @@ -2092,6 +2115,7 @@ void cpu_loop(CPUMIPSState *env) env-active_tc.gpr[7], arg5, arg6/*, arg7, arg8*/); } +#endif if (ret == -TARGET_QEMU_ESIGRETURN) { /* Returning from a successful sigreturn syscall. Avoid clobbering register state. */ diff --git a/linux-user/mips64/syscall.h b/linux-user/mips64/syscall.h index 668a2b9..ec65653 100644 --- a/linux-user/mips64/syscall.h +++ b/linux-user/mips64/syscall.h @@ -218,4 +218,7 @@ struct target_pt_regs { +/* Nasty hack: define a fake errno value for use by sigreturn. */ +#define TARGET_QEMU_ESIGRETURN 255 + #define UNAME_MACHINE mips64 diff --git a/linux-user/signal.c b/linux-user/signal.c index ce033e9..66786db 100644 --- a/linux-user/signal.c +++ b/linux-user/signal.c @@ -2413,8 +2413,6 @@ void sparc64_get_context(CPUSPARCState *env) #endif #elif defined(TARGET_ABI_MIPSN64) -# warning signal handling not implemented - static void setup_frame(int sig, struct target_sigaction *ka, target_sigset_t *set, CPUState *env) { diff --git a/linux-user/syscall.c b/linux-user/syscall.c index bb0999d..cfa925e 100644 --- a/linux-user/syscall.c +++ b/linux-user/syscall.c @@ -7320,6 +7320,11 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1, case TARGET_NR_set_thread_area: #if defined(TARGET_MIPS) ((CPUMIPSState *) cpu_env)-tls_value = arg1; + if (((CPUMIPSState *) cpu_env)-insn_flags CPU_OCTEON) { + /* tls entry is moved to k0 so that this can be used later + currently this thing is tested only for Octeon */ + ((CPUMIPSState *) cpu_env)-active_tc.gpr[26] = arg1; + } ret = 0
Re: [Qemu-devel] [PATCH 1/2] Support for MIPS64 user mode emulation
Please see comments highlighted in green. On Fri, Apr 29, 2011 at 2:01 PM, Aurelien Jarno aurel...@aurel32.netwrote: On Mon, Apr 25, 2011 at 04:54:19PM +0500, Khansa Butt wrote: please see inline comments highlighted in red color. On Wed, Apr 13, 2011 at 2:32 AM, Aurelien Jarno aurel...@aurel32.net wrote: [I don't know very well linux-user, it would be nice to Cc: Riku Voipio, the linux-user maintainer for the next version.] On Sat, Apr 09, 2011 at 04:02:31PM +0500, Khansa Butt wrote: From e96e20e50cada1c9e1b65de5925281cdd5659746 Mon Sep 17 00:00:00 2001 From: Ehsan-ul-Haq Khansa Butt kha...@kics.edu.pk Date: Sat, 9 Apr 2011 10:51:22 +0500 Subject: [PATCH 1/2] Support for MIPS64 user mode emulation Signed-off-by: Ehsan-ul-Haq, Abdul Qadeer, Abdul Waheed, Khansa Butt kha...@kics.edu.pk --- configure |1 + default-configs/mips64-linux-user.mak |1 + linux-user/elfload.c |2 +- linux-user/main.c | 29 +++-- linux-user/mips64/syscall.h |3 +++ linux-user/signal.c |3 ++- target-mips/translate.c |1 + 7 files changed, 36 insertions(+), 4 deletions(-) create mode 100644 default-configs/mips64-linux-user.mak diff --git a/configure b/configure index ae97e11..d1f7867 100755 --- a/configure +++ b/configure @@ -1039,6 +1039,7 @@ m68k-linux-user \ microblaze-linux-user \ microblazeel-linux-user \ mips-linux-user \ +mips64-linux-user \ mipsel-linux-user \ ppc-linux-user \ ppc64-linux-user \ diff --git a/default-configs/mips64-linux-user.mak b/default-configs/mips64-linux-user.mak new file mode 100644 index 000..1598bfc --- /dev/null +++ b/default-configs/mips64-linux-user.mak @@ -0,0 +1 @@ +# Default configuration for mips64-linux-user diff --git a/linux-user/elfload.c b/linux-user/elfload.c index fe5410e..2832a33 100644 --- a/linux-user/elfload.c +++ b/linux-user/elfload.c @@ -1384,7 +1384,7 @@ static void load_elf_image(const char *image_name, int image_fd, vaddr_po = TARGET_ELF_PAGEOFFSET(vaddr); vaddr_ps = TARGET_ELF_PAGESTART(vaddr); -error = target_mmap(vaddr_ps, eppnt-p_filesz + vaddr_po, +error = target_mmap(vaddr_ps, eppnt-p_memsz + vaddr_po, What is the goal of this change? If the mmapped aread is bigger than the file size rounded up to te page size, it will cause a SIGBUS. elf_prot, MAP_PRIVATE | MAP_FIXED, image_fd, eppnt-p_offset - vaddr_po); if (error == -1) { diff --git a/linux-user/main.c b/linux-user/main.c index e651bfd..a7f4955 100644 --- a/linux-user/main.c +++ b/linux-user/main.c @@ -1937,6 +1937,14 @@ static int do_store_exclusive(CPUMIPSState *env) int d; addr = env-lladdr; +#if defined(TARGET_MIPS64) +/* For MIPS64 on 32 bit host there is a need to make +* the page accessible to which the above 'addr' is belonged */ +#if HOST_LONG_BITS == 32 +int flag = PAGE_VALID | PAGE_READ | PAGE_WRITE | PAGE_WRITE_ORG; +page_set_flags(addr, addr + 4096, flag); +#endif +#endif I don't really see the reason why this should be done that way. Are you trying to run MIPS32 binaries compiled for 8kB page size? this change is needed when we run MIPS64 ELF on 32 bit x86 host. MIPS64 ELF contains 36 bit address. Actually it can contains up to 62-bit address there (all the user mapped space). load_elf_image() at /home/khansa/testpatch/qemu/linux-user/elfload.c: QEMU contains these lines /* Round addresses to page boundaries. */ loaddr = qemu_host_page_mask; hiaddr = HOST_PAGE_ALIGN(hiaddr); when QEMU run on 32 bit x86 the above two variables are rounded to 32 bit value while these should be 36 bits as these come from MIPS64 ELF.and then It is correct to truncate them, as the address space of the host is smaller. It's just based on the fact that programs only need a subset of the 62 bit address space. for these rounded address l1_map is initialized in page_find_alloc(). in case of SCD(store condition double ) instruction of MIPS64r2 when we have to check load linked address its again 36 bit so it will make an index(addr TARGET_PAGE_BITS) for which l1_map is no valid entry, returning 0 value and we got segmentation fault. this is the reason we did following changes in main.c do_store_exclusive() No, the load linked address register size, as well as the shift is actually implementation dependent. On old 64-bit MIPS implementation and MIPS32 core it is a 32-bit register and a 4-bit
Re: [Qemu-devel] [PATCH 1/2] Support for MIPS64 user mode emulation
please see inline comments highlighted in red color. On Wed, Apr 13, 2011 at 2:32 AM, Aurelien Jarno aurel...@aurel32.netwrote: [I don't know very well linux-user, it would be nice to Cc: Riku Voipio, the linux-user maintainer for the next version.] On Sat, Apr 09, 2011 at 04:02:31PM +0500, Khansa Butt wrote: From e96e20e50cada1c9e1b65de5925281cdd5659746 Mon Sep 17 00:00:00 2001 From: Ehsan-ul-Haq Khansa Butt kha...@kics.edu.pk Date: Sat, 9 Apr 2011 10:51:22 +0500 Subject: [PATCH 1/2] Support for MIPS64 user mode emulation Signed-off-by: Ehsan-ul-Haq, Abdul Qadeer, Abdul Waheed, Khansa Butt kha...@kics.edu.pk --- configure |1 + default-configs/mips64-linux-user.mak |1 + linux-user/elfload.c |2 +- linux-user/main.c | 29 +++-- linux-user/mips64/syscall.h |3 +++ linux-user/signal.c |3 ++- target-mips/translate.c |1 + 7 files changed, 36 insertions(+), 4 deletions(-) create mode 100644 default-configs/mips64-linux-user.mak diff --git a/configure b/configure index ae97e11..d1f7867 100755 --- a/configure +++ b/configure @@ -1039,6 +1039,7 @@ m68k-linux-user \ microblaze-linux-user \ microblazeel-linux-user \ mips-linux-user \ +mips64-linux-user \ mipsel-linux-user \ ppc-linux-user \ ppc64-linux-user \ diff --git a/default-configs/mips64-linux-user.mak b/default-configs/mips64-linux-user.mak new file mode 100644 index 000..1598bfc --- /dev/null +++ b/default-configs/mips64-linux-user.mak @@ -0,0 +1 @@ +# Default configuration for mips64-linux-user diff --git a/linux-user/elfload.c b/linux-user/elfload.c index fe5410e..2832a33 100644 --- a/linux-user/elfload.c +++ b/linux-user/elfload.c @@ -1384,7 +1384,7 @@ static void load_elf_image(const char *image_name, int image_fd, vaddr_po = TARGET_ELF_PAGEOFFSET(vaddr); vaddr_ps = TARGET_ELF_PAGESTART(vaddr); -error = target_mmap(vaddr_ps, eppnt-p_filesz + vaddr_po, +error = target_mmap(vaddr_ps, eppnt-p_memsz + vaddr_po, What is the goal of this change? If the mmapped aread is bigger than the file size rounded up to te page size, it will cause a SIGBUS. elf_prot, MAP_PRIVATE | MAP_FIXED, image_fd, eppnt-p_offset - vaddr_po); if (error == -1) { diff --git a/linux-user/main.c b/linux-user/main.c index e651bfd..a7f4955 100644 --- a/linux-user/main.c +++ b/linux-user/main.c @@ -1937,6 +1937,14 @@ static int do_store_exclusive(CPUMIPSState *env) int d; addr = env-lladdr; +#if defined(TARGET_MIPS64) +/* For MIPS64 on 32 bit host there is a need to make +* the page accessible to which the above 'addr' is belonged */ +#if HOST_LONG_BITS == 32 +int flag = PAGE_VALID | PAGE_READ | PAGE_WRITE | PAGE_WRITE_ORG; +page_set_flags(addr, addr + 4096, flag); +#endif +#endif I don't really see the reason why this should be done that way. Are you trying to run MIPS32 binaries compiled for 8kB page size? this change is needed when we run MIPS64 ELF on 32 bit x86 host. MIPS64 ELF contains 36 bit address. load_elf_image() at /home/khansa/testpatch/qemu/linux-user/elfload.c: QEMU contains these lines /* Round addresses to page boundaries. */ loaddr = qemu_host_page_mask; hiaddr = HOST_PAGE_ALIGN(hiaddr); when QEMU run on 32 bit x86 the above two variables are rounded to 32 bit value while these should be 36 bits as these come from MIPS64 ELF.and then for these rounded address l1_map is initialized in page_find_alloc(). in case of SCD(store condition double ) instruction of MIPS64r2 when we have to check load linked address its again 36 bit so it will make an index(addr TARGET_PAGE_BITS) for which l1_map is no valid entry, returning 0 value and we got segmentation fault. this is the reason we did following changes in main.c do_store_exclusive() +#if HOST_LONG_BITS == 32 +int flag = PAGE_VALID | PAGE_READ | PAGE_WRITE | PAGE_WRITE_ORG; +page_set_flags(addr, addr + 4096, flag); +#endif Please give comments on this page_addr = addr TARGET_PAGE_MASK; start_exclusive(); mmap_lock(); @@ -1978,7 +1986,8 @@ static int do_store_exclusive(CPUMIPSState *env) void cpu_loop(CPUMIPSState *env) { target_siginfo_t info; -int trapnr, ret; +int trapnr; +abi_long ret; unsigned int syscall_num; for(;;) { @@ -1987,7 +1996,11 @@ void cpu_loop(CPUMIPSState *env) cpu_exec_end(env); switch(trapnr) { case EXCP_SYSCALL: +#if defined(TARGET_MIPS64) +syscall_num = env-active_tc.gpr[2] - 5000; +#else syscall_num = env-active_tc.gpr[2] - 4000; +#endif
Re: [Qemu-devel] [PATCH 2/2] Support for Cavium-Octeon specific instruction
We ported MIPS64 r2 user mode emulation. When a binary is given to qemu-mips64, our code first check whether it is Octeon binary or not if yes it enable Octeon specific Instructions for. The following code snippet do this job: diff --git a/linux-user/elfload.c b/linux-user/elfload.c index 2832a33..9399e44 100644 --- a/linux-user/elfload.c +++ b/linux-user/elfload.c @@ -1662,6 +1662,11 @@ int load_elf_binary(struct linux_binprm * bprm, struct target_pt_regs * regs, when we load the interpreter. */ elf_ex = *(struct elfhdr *)bprm-buf; +#if defined(TARGET_MIPS64) +if ((elf_ex.e_flags EF_MIPS_MARCH) == E_MIPS_MACH_OCTEON) { +info-elf_arch = 1; +} +#endif +++ b/linux-user/main.c @@ -3348,6 +3348,11 @@ int main(int argc, char **argv, char **envp) if (regs-cp0_epc 1) { env-hflags |= MIPS_HFLAG_M16; } +#if defined(TARGET_MIPS64) +if (info-elf_arch) { +env-insn_flags |= INSN_OCTEON; +} +#endif } where we put elf_arch in image_info and INSN_OCTEON is in target_mips/mips-defs.h as follows #define INSN_LOONGSON2E 0x2000 #define INSN_LOONGSON2F 0x4000 #define INSN_VR54XX 0x8000 +#defineINSN_OCTEON 0x1000 Is this solution acceptable for you?
[Qemu-devel] Patch1 for Mips64 usermode
*commands for patch apply* git apply --ignore-whitespace --ignore-space-change --check ~/patch1 git am --ignore-whitespace --ignore-space-change ~/patch1 *Patch* From e96e20e50cada1c9e1b65de5925281cdd5659746 Mon Sep 17 00:00:00 2001 From: Ehsan-ul-Haq Khansa Butt kha...@kics.edu.pk Date: Sat, 9 Apr 2011 10:51:22 +0500 Subject: [PATCH 1/2] Support for MIPS64 user mode emulation Signed-off-by: Ehsan-ul-Haq, Abdul Qadeer, Abdul Waheed, Khansa Butt kha...@kics.edu.pk --- configure |1 + default-configs/mips64-linux-user.mak |1 + linux-user/elfload.c |2 +- linux-user/main.c | 29 +++-- linux-user/mips64/syscall.h |3 +++ linux-user/signal.c |3 ++- target-mips/translate.c |1 + 7 files changed, 36 insertions(+), 4 deletions(-) create mode 100644 default-configs/mips64-linux-user.mak diff --git a/configure b/configure index ae97e11..d1f7867 100755 --- a/configure +++ b/configure @@ -1039,6 +1039,7 @@ m68k-linux-user \ microblaze-linux-user \ microblazeel-linux-user \ mips-linux-user \ +mips64-linux-user \ mipsel-linux-user \ ppc-linux-user \ ppc64-linux-user \ diff --git a/default-configs/mips64-linux-user.mak b/default-configs/mips64-linux-user.mak new file mode 100644 index 000..1598bfc --- /dev/null +++ b/default-configs/mips64-linux-user.mak @@ -0,0 +1 @@ +# Default configuration for mips64-linux-user diff --git a/linux-user/elfload.c b/linux-user/elfload.c index fe5410e..2832a33 100644 --- a/linux-user/elfload.c +++ b/linux-user/elfload.c @@ -1384,7 +1384,7 @@ static void load_elf_image(const char *image_name, int image_fd, vaddr_po = TARGET_ELF_PAGEOFFSET(vaddr); vaddr_ps = TARGET_ELF_PAGESTART(vaddr); -error = target_mmap(vaddr_ps, eppnt-p_filesz + vaddr_po, +error = target_mmap(vaddr_ps, eppnt-p_memsz + vaddr_po, elf_prot, MAP_PRIVATE | MAP_FIXED, image_fd, eppnt-p_offset - vaddr_po); if (error == -1) { diff --git a/linux-user/main.c b/linux-user/main.c index e651bfd..a7f4955 100644 --- a/linux-user/main.c +++ b/linux-user/main.c @@ -1937,6 +1937,14 @@ static int do_store_exclusive(CPUMIPSState *env) int d; addr = env-lladdr; +#if defined(TARGET_MIPS64) +/* For MIPS64 on 32 bit host there is a need to make +* the page accessible to which the above 'addr' is belonged */ +#if HOST_LONG_BITS == 32 +int flag = PAGE_VALID | PAGE_READ | PAGE_WRITE | PAGE_WRITE_ORG; +page_set_flags(addr, addr + 4096, flag); +#endif +#endif page_addr = addr TARGET_PAGE_MASK; start_exclusive(); mmap_lock(); @@ -1978,7 +1986,8 @@ static int do_store_exclusive(CPUMIPSState *env) void cpu_loop(CPUMIPSState *env) { target_siginfo_t info; -int trapnr, ret; +int trapnr; +abi_long ret; unsigned int syscall_num; for(;;) { @@ -1987,7 +1996,11 @@ void cpu_loop(CPUMIPSState *env) cpu_exec_end(env); switch(trapnr) { case EXCP_SYSCALL: +#if defined(TARGET_MIPS64) +syscall_num = env-active_tc.gpr[2] - 5000; +#else syscall_num = env-active_tc.gpr[2] - 4000; +#endif env-active_tc.PC += 4; if (syscall_num = sizeof(mips_syscall_args)) { ret = -ENOSYS; @@ -2008,12 +2021,22 @@ void cpu_loop(CPUMIPSState *env) default: break; } +#if defined(TARGET_MIPS64) +ret = do_syscall(env, env-active_tc.gpr[2], + env-active_tc.gpr[4], + env-active_tc.gpr[5], + env-active_tc.gpr[6], + env-active_tc.gpr[7], + env-active_tc.gpr[8], + env-active_tc.gpr[9]); +#else ret = do_syscall(env, env-active_tc.gpr[2], env-active_tc.gpr[4], env-active_tc.gpr[5], env-active_tc.gpr[6], env-active_tc.gpr[7], arg5, arg6/*, arg7, arg8*/); +#endif } if (ret == -TARGET_QEMU_ESIGRETURN) { /* Returning from a successful sigreturn syscall. @@ -2935,7 +2958,9 @@ int main(int argc, char **argv, char **envp) #endif #elif defined(TARGET_MIPS) #if defined(TARGET_ABI_MIPSN32) || defined(TARGET_ABI_MIPSN64) -cpu_model = 20Kc; +/* we use this model so that we can decode MIPS64r2 + reserved instruction */ +cpu_model = MIPS64R2-generic; #else cpu_model = 24Kf; #endif diff --git a/linux-user/mips64/syscall.h b/linux-user/mips64/syscall.h index 668a2b9..ec65653 100644 --- a/linux-user/mips64/syscall.h +++ b
Re: [Qemu-devel] MIPS64 user mode emulation Patch
Please see the online comments highlighted in red. I'll be sending corrected Patches to the mailing list. On Wed, Mar 30, 2011 at 9:38 PM, Nathan Froyd froy...@codesourcery.comwrote: On Sat, Mar 26, 2011 at 11:58:37AM +0500, Khansa Butt wrote: Subject: [PATCH] MIPS64 user mode emulation in QEMU This patch adds support for Cavium Network's Octeon 57XX user mode instructions. Octeon 57xx is based on MIPS64. So this patch is the first MIPS64 User Mode Emulation in QEMU This is the team(Khansa Butt, Ehsan-ul-Haq, Abdul Qadeer, Abdul Waheed) work of HPCNL Lab at KICS-UET Lahore. Thanks for doing this. As already noted, this patch should be split into at least two patches: one to add Octeon-specific instructions in target-mips/ and one adding the necessary linux-user bits. +extern int TARGET_OCTEON; I don't think a global like this is the right way to go. Perhaps the elfload.c code should set a flag in image_info , which can then be used to set a flag in CPUMIPSState later on. A variable is declared in image_info to set a flag in CPUMIPSState and discarded a global variable @@ -51,6 +51,7 @@ struct image_info { abi_ulong arg_start; abi_ulong arg_end; int personality; + int elf_arch; If we must use a global variable, it should be declared in target-mips/cpu.h. @@ -2013,7 +2024,8 @@ void cpu_loop(CPUMIPSState *env) env-active_tc.gpr[5], env-active_tc.gpr[6], env-active_tc.gpr[7], - arg5, arg6/*, arg7, arg8*/); + env-active_tc.gpr[8], + env-active_tc.gpr[9]/*, arg7, arg8*/); } if (ret == -TARGET_QEMU_ESIGRETURN) { /* Returning from a successful sigreturn syscall. This change breaks O32 binaries; it needs to be done in a different way. The above line has been changed with following code snippet +#if defined(TARGET_MIPS64) +ret = do_syscall(env, env-active_tc.gpr[2], + env-active_tc.gpr[4], + env-active_tc.gpr[5], + env-active_tc.gpr[6], + env-active_tc.gpr[7], + env-active_tc.gpr[8], + env-active_tc.gpr[9]); +#else ret = do_syscall(env, env-active_tc.gpr[2], env-active_tc.gpr[4], env-active_tc.gpr[5], env-active_tc.gpr[6], env-active_tc.gpr[7], arg5, arg6/*, arg7, arg8*/); +#endif diff --git a/linux-user/syscall.c b/linux-user/syscall.c index 499c4d7..47fef05 100644 --- a/linux-user/syscall.c +++ b/linux-user/syscall.c @@ -7195,6 +7195,8 @@ abi_long do_syscall(void *cpu_env, int num, abi_long arg1, case TARGET_NR_set_thread_area: #if defined(TARGET_MIPS) ((CPUMIPSState *) cpu_env)-tls_value = arg1; + /*tls entry is moved to k0 so that this can be used later*/ + ((CPUMIPSState *) cpu_env)-active_tc.gpr[26] = arg1; ret = 0; break; #elif defined(TARGET_CRIS) I believe this is only correct for Octeon binaries; it's not how the rest of the MIPS world works. It therefore needs to be conditional on Octeon-ness. The above thing has been made octeon specific --- a/target-mips/cpu.h +++ b/target-mips/cpu.h @@ -140,6 +140,20 @@ typedef struct mips_def_t mips_def_t; #define MIPS_FPU_MAX 1 #define MIPS_DSP_ACC 4 +typedef struct cavium_mul cavium_mul; +struct cavium_mul { + target_ulong MPL0; + target_ulong MPL1; + target_ulong MPL2; + target_ulong P0; + target_ulong P1; + target_ulong P2; +}; +typedef struct cvmctl_register cvmctl_register; +struct cvmctl_register { + target_ulong cvmctl; +}; The indentation here needs to be fixed. I don't think there's any reason why these need to be defined outside TCState, either. Octeon register in TCState as follows @@ -171,6 +176,15 @@ struct TCState { target_ulong CP0_TCSchedule; target_ulong CP0_TCScheFBack; int32_t CP0_Debug_tcstatus; +/* Multiplier registers for Octeon */ +target_ulong MPL0; +target_ulong MPL1; +target_ulong MPL2; +target_ulong P0; +target_ulong P1; +target_ulong P2; +/* Octeon specific Coprocessor 0 register */ +target_ulong cvmctl; }; diff --git a/target-mips/translate.c b/target-mips/translate.c index cce77be..9c3d772 100644 --- a/target-mips/translate.c +++ b/target-mips/translate.c @@ -36,6 +36,15 @@ #define GEN_HELPER 1 #include helper.h +int TARGET_OCTEON; +#if defined(TARGET_MIPS64) +/*Macros for setting values of cvmctl registers
Re: [Qemu-devel] QEMU development for MIPS64 user mode
Please see inline comments highlighted in red. On Wed, Mar 30, 2011 at 12:04 AM, Andreas Färber andreas.faer...@web.dewrote: Hi, Am 29.03.2011 um 08:49 schrieb Khansa Butt: I have added support for MIPS64 user mode emulation in QEMU and email git patch to the qemu-devel mailing list but I got no any response yet. My Patch mail has the following subject line MIPS64 user mode emulation Patch please verify that this patch mail is not neglected or guide me towards the proper way of patch submitting. You should use git-send-email to submit it (marking it as [PATCH]) so that it can be applied with git-am, see http://wiki.qemu.org/Contribute/SubmitAPatch and the list archives. Also don't forget to cc the maintainer(s) - Aurelien for mips and Riku for linux-user IIRC. A description of how to test it may be helpful. Maybe you have links to mips64 binaries that work? Usually, the subject line of the commit message is prefixed with the topic (linux-user) or architecture (mips). If all the people you name contributed to this patch, you should probably add their SoBs before yours. The patch is rather large - is it possible to split it up into a patch series with at least a linux-user and a (target-)mips part? TARGET_OCTEON looks rather uncommon to me... Your patch contains a Nasty hack. Please elaborate on that - what's the problem, do you intend to fix it later, etc. linux-user/mips64/syscall.h +/* Nasty hack: define a fake errno value for use by sigreturn. */ +#define TARGET_QEMU_ESIGRETURN 255 + The above lines has been copied from linux-user/mips32/syscall.h, in order to define the constant TARGET_QEMU_ESIGRETURN(as it is needed in main.c:cpu_loop()) You simply comment out a #warning that signal handling is not implemented for mipsn64. Why didn't you implement it? Don't you need it? The signal handling for Mips64 is same as for other architectures. qemu handles signals which comes from a program and actual handling is done by host operating system. we follow the same convention. why this warning is generated initially? Similarly you comment out a sign extension. Please elaborate. If it's a bug and definitely wrong, it should be moved to its own patch, explaining what goes wrong and fully removing it instead. resolved this sign extension problem In CPUMIPSState, the surrounding struct members use lowercase characters. Some spaces missing after if. Thanks for your contribution and for taking the time to go through the review process. Regards, Andreas
[Qemu-devel] [PATCH 1/2] Support for MIPS64 user mode emulation
From e96e20e50cada1c9e1b65de5925281cdd5659746 Mon Sep 17 00:00:00 2001 From: Ehsan-ul-Haq Khansa Butt kha...@kics.edu.pk Date: Sat, 9 Apr 2011 10:51:22 +0500 Subject: [PATCH 1/2] Support for MIPS64 user mode emulation Signed-off-by: Ehsan-ul-Haq, Abdul Qadeer, Abdul Waheed, Khansa Butt kha...@kics.edu.pk --- configure |1 + default-configs/mips64-linux-user.mak |1 + linux-user/elfload.c |2 +- linux-user/main.c | 29 +++-- linux-user/mips64/syscall.h |3 +++ linux-user/signal.c |3 ++- target-mips/translate.c |1 + 7 files changed, 36 insertions(+), 4 deletions(-) create mode 100644 default-configs/mips64-linux-user.mak diff --git a/configure b/configure index ae97e11..d1f7867 100755 --- a/configure +++ b/configure @@ -1039,6 +1039,7 @@ m68k-linux-user \ microblaze-linux-user \ microblazeel-linux-user \ mips-linux-user \ +mips64-linux-user \ mipsel-linux-user \ ppc-linux-user \ ppc64-linux-user \ diff --git a/default-configs/mips64-linux-user.mak b/default-configs/mips64-linux-user.mak new file mode 100644 index 000..1598bfc --- /dev/null +++ b/default-configs/mips64-linux-user.mak @@ -0,0 +1 @@ +# Default configuration for mips64-linux-user diff --git a/linux-user/elfload.c b/linux-user/elfload.c index fe5410e..2832a33 100644 --- a/linux-user/elfload.c +++ b/linux-user/elfload.c @@ -1384,7 +1384,7 @@ static void load_elf_image(const char *image_name, int image_fd, vaddr_po = TARGET_ELF_PAGEOFFSET(vaddr); vaddr_ps = TARGET_ELF_PAGESTART(vaddr); -error = target_mmap(vaddr_ps, eppnt-p_filesz + vaddr_po, +error = target_mmap(vaddr_ps, eppnt-p_memsz + vaddr_po, elf_prot, MAP_PRIVATE | MAP_FIXED, image_fd, eppnt-p_offset - vaddr_po); if (error == -1) { diff --git a/linux-user/main.c b/linux-user/main.c index e651bfd..a7f4955 100644 --- a/linux-user/main.c +++ b/linux-user/main.c @@ -1937,6 +1937,14 @@ static int do_store_exclusive(CPUMIPSState *env) int d; addr = env-lladdr; +#if defined(TARGET_MIPS64) +/* For MIPS64 on 32 bit host there is a need to make +* the page accessible to which the above 'addr' is belonged */ +#if HOST_LONG_BITS == 32 +int flag = PAGE_VALID | PAGE_READ | PAGE_WRITE | PAGE_WRITE_ORG; +page_set_flags(addr, addr + 4096, flag); +#endif +#endif page_addr = addr TARGET_PAGE_MASK; start_exclusive(); mmap_lock(); @@ -1978,7 +1986,8 @@ static int do_store_exclusive(CPUMIPSState *env) void cpu_loop(CPUMIPSState *env) { target_siginfo_t info; -int trapnr, ret; +int trapnr; +abi_long ret; unsigned int syscall_num; for(;;) { @@ -1987,7 +1996,11 @@ void cpu_loop(CPUMIPSState *env) cpu_exec_end(env); switch(trapnr) { case EXCP_SYSCALL: +#if defined(TARGET_MIPS64) +syscall_num = env-active_tc.gpr[2] - 5000; +#else syscall_num = env-active_tc.gpr[2] - 4000; +#endif env-active_tc.PC += 4; if (syscall_num = sizeof(mips_syscall_args)) { ret = -ENOSYS; @@ -2008,12 +2021,22 @@ void cpu_loop(CPUMIPSState *env) default: break; } +#if defined(TARGET_MIPS64) +ret = do_syscall(env, env-active_tc.gpr[2], + env-active_tc.gpr[4], + env-active_tc.gpr[5], + env-active_tc.gpr[6], + env-active_tc.gpr[7], + env-active_tc.gpr[8], + env-active_tc.gpr[9]); +#else ret = do_syscall(env, env-active_tc.gpr[2], env-active_tc.gpr[4], env-active_tc.gpr[5], env-active_tc.gpr[6], env-active_tc.gpr[7], arg5, arg6/*, arg7, arg8*/); +#endif } if (ret == -TARGET_QEMU_ESIGRETURN) { /* Returning from a successful sigreturn syscall. @@ -2935,7 +2958,9 @@ int main(int argc, char **argv, char **envp) #endif #elif defined(TARGET_MIPS) #if defined(TARGET_ABI_MIPSN32) || defined(TARGET_ABI_MIPSN64) -cpu_model = 20Kc; +/* we use this model so that we can decode MIPS64r2 + reserved instruction */ +cpu_model = MIPS64R2-generic; #else cpu_model = 24Kf; #endif diff --git a/linux-user/mips64/syscall.h b/linux-user/mips64/syscall.h index 668a2b9..ec65653 100644 --- a/linux-user/mips64/syscall.h +++ b/linux-user/mips64/syscall.h @@ -218,4 +218,7 @@ struct target_pt_regs { +/* Nasty hack: define a fake errno value for use by sigreturn. */ +#define
[Qemu-devel] QEMU development for MIPS64 user mode
hi I have added support for MIPS64 user mode emulation in QEMU and email git patch to the qemu-devel mailing list but I got no any response yet. My Patch mail has the following subject line MIPS64 user mode emulation Patch please verify that this patch mail is not neglected or guide me towards the proper way of patch submitting.