aboutsummaryrefslogtreecommitdiffstats
path: root/arch/mips
diff options
context:
space:
mode:
authorSanjay Lal <sanjayl@kymasys.com>2012-11-21 21:34:03 -0500
committerRalf Baechle <ralf@linux-mips.org>2013-05-07 21:55:35 -0400
commit9843b030cc951bce4a4d9bec38b5155c96eb1740 (patch)
treedd219e76dce1e1b92e6f5fc19e8767b60827c7ee /arch/mips
parent669e846e6c4e13f16d7418973609931e362cb16a (diff)
KVM/MIPS32: KVM Guest kernel support.
Both Guest kernel and Guest Userspace execute in UM. The memory map is as follows: Guest User address space: 0x00000000 -> 0x40000000 Guest Kernel Unmapped: 0x40000000 -> 0x60000000 Guest Kernel Mapped: 0x60000000 -> 0x80000000 - Guest Usermode virtual memory is limited to 1GB. Signed-off-by: Sanjay Lal <sanjayl@kymasys.com> Cc: kvm@vger.kernel.org Cc: linux-mips@linux-mips.org Signed-off-by: Ralf Baechle <ralf@linux-mips.org>
Diffstat (limited to 'arch/mips')
-rw-r--r--arch/mips/include/asm/mach-generic/spaces.h9
-rw-r--r--arch/mips/include/asm/processor.h5
-rw-r--r--arch/mips/include/asm/uaccess.h11
-rw-r--r--arch/mips/kernel/binfmt_elfo32.c4
-rw-r--r--arch/mips/kernel/cevt-r4k.c4
-rw-r--r--arch/mips/kernel/traps.c7
-rw-r--r--arch/mips/mti-malta/malta-time.c15
7 files changed, 52 insertions, 3 deletions
diff --git a/arch/mips/include/asm/mach-generic/spaces.h b/arch/mips/include/asm/mach-generic/spaces.h
index 73d717a75cb0..5b2f2e68e57f 100644
--- a/arch/mips/include/asm/mach-generic/spaces.h
+++ b/arch/mips/include/asm/mach-generic/spaces.h
@@ -20,14 +20,21 @@
20#endif 20#endif
21 21
22#ifdef CONFIG_32BIT 22#ifdef CONFIG_32BIT
23 23#ifdef CONFIG_KVM_GUEST
24#define CAC_BASE _AC(0x40000000, UL)
25#else
24#define CAC_BASE _AC(0x80000000, UL) 26#define CAC_BASE _AC(0x80000000, UL)
27#endif
25#define IO_BASE _AC(0xa0000000, UL) 28#define IO_BASE _AC(0xa0000000, UL)
26#define UNCAC_BASE _AC(0xa0000000, UL) 29#define UNCAC_BASE _AC(0xa0000000, UL)
27 30
28#ifndef MAP_BASE 31#ifndef MAP_BASE
32#ifdef CONFIG_KVM_GUEST
33#define MAP_BASE _AC(0x60000000, UL)
34#else
29#define MAP_BASE _AC(0xc0000000, UL) 35#define MAP_BASE _AC(0xc0000000, UL)
30#endif 36#endif
37#endif
31 38
32/* 39/*
33 * Memory above this physical address will be considered highmem. 40 * Memory above this physical address will be considered highmem.
diff --git a/arch/mips/include/asm/processor.h b/arch/mips/include/asm/processor.h
index 2a5fa7abb346..71686c897dea 100644
--- a/arch/mips/include/asm/processor.h
+++ b/arch/mips/include/asm/processor.h
@@ -44,11 +44,16 @@ extern unsigned int vced_count, vcei_count;
44#define SPECIAL_PAGES_SIZE PAGE_SIZE 44#define SPECIAL_PAGES_SIZE PAGE_SIZE
45 45
46#ifdef CONFIG_32BIT 46#ifdef CONFIG_32BIT
47#ifdef CONFIG_KVM_GUEST
48/* User space process size is limited to 1GB in KVM Guest Mode */
49#define TASK_SIZE 0x3fff8000UL
50#else
47/* 51/*
48 * User space process size: 2GB. This is hardcoded into a few places, 52 * User space process size: 2GB. This is hardcoded into a few places,
49 * so don't change it unless you know what you are doing. 53 * so don't change it unless you know what you are doing.
50 */ 54 */
51#define TASK_SIZE 0x7fff8000UL 55#define TASK_SIZE 0x7fff8000UL
56#endif
52 57
53#ifdef __KERNEL__ 58#ifdef __KERNEL__
54#define STACK_TOP_MAX TASK_SIZE 59#define STACK_TOP_MAX TASK_SIZE
diff --git a/arch/mips/include/asm/uaccess.h b/arch/mips/include/asm/uaccess.h
index bd87e36bf26a..b46caab453a5 100644
--- a/arch/mips/include/asm/uaccess.h
+++ b/arch/mips/include/asm/uaccess.h
@@ -23,7 +23,11 @@
23 */ 23 */
24#ifdef CONFIG_32BIT 24#ifdef CONFIG_32BIT
25 25
26#define __UA_LIMIT 0x80000000UL 26#ifdef CONFIG_KVM_GUEST
27#define __UA_LIMIT 0x40000000UL
28#else
29#define __UA_LIMIT 0x80000000UL
30#endif
27 31
28#define __UA_ADDR ".word" 32#define __UA_ADDR ".word"
29#define __UA_LA "la" 33#define __UA_LA "la"
@@ -55,8 +59,13 @@ extern u64 __ua_limit;
55 * address in this range it's the process's problem, not ours :-) 59 * address in this range it's the process's problem, not ours :-)
56 */ 60 */
57 61
62#ifdef CONFIG_KVM_GUEST
63#define KERNEL_DS ((mm_segment_t) { 0x80000000UL })
64#define USER_DS ((mm_segment_t) { 0xC0000000UL })
65#else
58#define KERNEL_DS ((mm_segment_t) { 0UL }) 66#define KERNEL_DS ((mm_segment_t) { 0UL })
59#define USER_DS ((mm_segment_t) { __UA_LIMIT }) 67#define USER_DS ((mm_segment_t) { __UA_LIMIT })
68#endif
60 69
61#define VERIFY_READ 0 70#define VERIFY_READ 0
62#define VERIFY_WRITE 1 71#define VERIFY_WRITE 1
diff --git a/arch/mips/kernel/binfmt_elfo32.c b/arch/mips/kernel/binfmt_elfo32.c
index 556a4357d7fc..97c5a1668e53 100644
--- a/arch/mips/kernel/binfmt_elfo32.c
+++ b/arch/mips/kernel/binfmt_elfo32.c
@@ -48,7 +48,11 @@ typedef elf_fpreg_t elf_fpregset_t[ELF_NFPREG];
48 __res; \ 48 __res; \
49}) 49})
50 50
51#ifdef CONFIG_KVM_GUEST
52#define TASK32_SIZE 0x3fff8000UL
53#else
51#define TASK32_SIZE 0x7fff8000UL 54#define TASK32_SIZE 0x7fff8000UL
55#endif
52#undef ELF_ET_DYN_BASE 56#undef ELF_ET_DYN_BASE
53#define ELF_ET_DYN_BASE (TASK32_SIZE / 3 * 2) 57#define ELF_ET_DYN_BASE (TASK32_SIZE / 3 * 2)
54 58
diff --git a/arch/mips/kernel/cevt-r4k.c b/arch/mips/kernel/cevt-r4k.c
index 07b847d77f5d..fd75d7144524 100644
--- a/arch/mips/kernel/cevt-r4k.c
+++ b/arch/mips/kernel/cevt-r4k.c
@@ -118,6 +118,10 @@ int c0_compare_int_usable(void)
118 unsigned int delta; 118 unsigned int delta;
119 unsigned int cnt; 119 unsigned int cnt;
120 120
121#ifdef CONFIG_KVM_GUEST
122 return 1;
123#endif
124
121 /* 125 /*
122 * IP7 already pending? Try to clear it by acking the timer. 126 * IP7 already pending? Try to clear it by acking the timer.
123 */ 127 */
diff --git a/arch/mips/kernel/traps.c b/arch/mips/kernel/traps.c
index a200b5bdbb87..59351e5d0591 100644
--- a/arch/mips/kernel/traps.c
+++ b/arch/mips/kernel/traps.c
@@ -1713,7 +1713,12 @@ void __init trap_init(void)
1713 ebase = (unsigned long) 1713 ebase = (unsigned long)
1714 __alloc_bootmem(size, 1 << fls(size), 0); 1714 __alloc_bootmem(size, 1 << fls(size), 0);
1715 } else { 1715 } else {
1716 ebase = CKSEG0; 1716#ifdef CONFIG_KVM_GUEST
1717#define KVM_GUEST_KSEG0 0x40000000
1718 ebase = KVM_GUEST_KSEG0;
1719#else
1720 ebase = CKSEG0;
1721#endif
1717 if (cpu_has_mips_r2) 1722 if (cpu_has_mips_r2)
1718 ebase += (read_c0_ebase() & 0x3ffff000); 1723 ebase += (read_c0_ebase() & 0x3ffff000);
1719 } 1724 }
diff --git a/arch/mips/mti-malta/malta-time.c b/arch/mips/mti-malta/malta-time.c
index a144b89cf9ba..bc6ac00c0d57 100644
--- a/arch/mips/mti-malta/malta-time.c
+++ b/arch/mips/mti-malta/malta-time.c
@@ -76,6 +76,21 @@ static void __init estimate_frequencies(void)
76 unsigned int count, start; 76 unsigned int count, start;
77 unsigned int giccount = 0, gicstart = 0; 77 unsigned int giccount = 0, gicstart = 0;
78 78
79#if defined (CONFIG_KVM_GUEST) && defined (CONFIG_KVM_HOST_FREQ)
80 unsigned int prid = read_c0_prid() & 0xffff00;
81
82 /*
83 * XXXKYMA: hardwire the CPU frequency to Host Freq/4
84 */
85 count = (CONFIG_KVM_HOST_FREQ * 1000000) >> 3;
86 if ((prid != (PRID_COMP_MIPS | PRID_IMP_20KC)) &&
87 (prid != (PRID_COMP_MIPS | PRID_IMP_25KF)))
88 count *= 2;
89
90 mips_hpt_frequency = count;
91 return;
92#endif
93
79 local_irq_save(flags); 94 local_irq_save(flags);
80 95
81 /* Start counter exactly on falling edge of update flag. */ 96 /* Start counter exactly on falling edge of update flag. */