diff options
Diffstat (limited to 'arch/powerpc/kvm/44x.c')
-rw-r--r-- | arch/powerpc/kvm/44x.c | 62 |
1 files changed, 60 insertions, 2 deletions
diff --git a/arch/powerpc/kvm/44x.c b/arch/powerpc/kvm/44x.c index f5d7028eeb09..22054b164b5a 100644 --- a/arch/powerpc/kvm/44x.c +++ b/arch/powerpc/kvm/44x.c | |||
@@ -18,9 +18,13 @@ | |||
18 | */ | 18 | */ |
19 | 19 | ||
20 | #include <linux/kvm_host.h> | 20 | #include <linux/kvm_host.h> |
21 | #include <linux/err.h> | ||
22 | |||
21 | #include <asm/reg.h> | 23 | #include <asm/reg.h> |
22 | #include <asm/cputable.h> | 24 | #include <asm/cputable.h> |
23 | #include <asm/tlbflush.h> | 25 | #include <asm/tlbflush.h> |
26 | #include <asm/kvm_44x.h> | ||
27 | #include <asm/kvm_ppc.h> | ||
24 | 28 | ||
25 | #include "44x_tlb.h" | 29 | #include "44x_tlb.h" |
26 | 30 | ||
@@ -124,7 +128,8 @@ int kvmppc_core_check_processor_compat(void) | |||
124 | 128 | ||
125 | int kvmppc_core_vcpu_setup(struct kvm_vcpu *vcpu) | 129 | int kvmppc_core_vcpu_setup(struct kvm_vcpu *vcpu) |
126 | { | 130 | { |
127 | struct kvmppc_44x_tlbe *tlbe = &vcpu->arch.guest_tlb[0]; | 131 | struct kvmppc_vcpu_44x *vcpu_44x = to_44x(vcpu); |
132 | struct kvmppc_44x_tlbe *tlbe = &vcpu_44x->guest_tlb[0]; | ||
128 | 133 | ||
129 | tlbe->tid = 0; | 134 | tlbe->tid = 0; |
130 | tlbe->word0 = PPC44x_TLB_16M | PPC44x_TLB_VALID; | 135 | tlbe->word0 = PPC44x_TLB_16M | PPC44x_TLB_VALID; |
@@ -150,6 +155,7 @@ int kvmppc_core_vcpu_setup(struct kvm_vcpu *vcpu) | |||
150 | int kvmppc_core_vcpu_translate(struct kvm_vcpu *vcpu, | 155 | int kvmppc_core_vcpu_translate(struct kvm_vcpu *vcpu, |
151 | struct kvm_translation *tr) | 156 | struct kvm_translation *tr) |
152 | { | 157 | { |
158 | struct kvmppc_vcpu_44x *vcpu_44x = to_44x(vcpu); | ||
153 | struct kvmppc_44x_tlbe *gtlbe; | 159 | struct kvmppc_44x_tlbe *gtlbe; |
154 | int index; | 160 | int index; |
155 | gva_t eaddr; | 161 | gva_t eaddr; |
@@ -166,7 +172,7 @@ int kvmppc_core_vcpu_translate(struct kvm_vcpu *vcpu, | |||
166 | return 0; | 172 | return 0; |
167 | } | 173 | } |
168 | 174 | ||
169 | gtlbe = &vcpu->arch.guest_tlb[index]; | 175 | gtlbe = &vcpu_44x->guest_tlb[index]; |
170 | 176 | ||
171 | tr->physical_address = tlb_xlate(gtlbe, eaddr); | 177 | tr->physical_address = tlb_xlate(gtlbe, eaddr); |
172 | /* XXX what does "writeable" and "usermode" even mean? */ | 178 | /* XXX what does "writeable" and "usermode" even mean? */ |
@@ -174,3 +180,55 @@ int kvmppc_core_vcpu_translate(struct kvm_vcpu *vcpu, | |||
174 | 180 | ||
175 | return 0; | 181 | return 0; |
176 | } | 182 | } |
183 | |||
184 | struct kvm_vcpu *kvmppc_core_vcpu_create(struct kvm *kvm, unsigned int id) | ||
185 | { | ||
186 | struct kvmppc_vcpu_44x *vcpu_44x; | ||
187 | struct kvm_vcpu *vcpu; | ||
188 | int err; | ||
189 | |||
190 | vcpu_44x = kmem_cache_zalloc(kvm_vcpu_cache, GFP_KERNEL); | ||
191 | if (!vcpu_44x) { | ||
192 | err = -ENOMEM; | ||
193 | goto out; | ||
194 | } | ||
195 | |||
196 | vcpu = &vcpu_44x->vcpu; | ||
197 | err = kvm_vcpu_init(vcpu, kvm, id); | ||
198 | if (err) | ||
199 | goto free_vcpu; | ||
200 | |||
201 | return vcpu; | ||
202 | |||
203 | free_vcpu: | ||
204 | kmem_cache_free(kvm_vcpu_cache, vcpu_44x); | ||
205 | out: | ||
206 | return ERR_PTR(err); | ||
207 | } | ||
208 | |||
209 | void kvmppc_core_vcpu_free(struct kvm_vcpu *vcpu) | ||
210 | { | ||
211 | struct kvmppc_vcpu_44x *vcpu_44x = to_44x(vcpu); | ||
212 | |||
213 | kvm_vcpu_uninit(vcpu); | ||
214 | kmem_cache_free(kvm_vcpu_cache, vcpu_44x); | ||
215 | } | ||
216 | |||
217 | static int kvmppc_44x_init(void) | ||
218 | { | ||
219 | int r; | ||
220 | |||
221 | r = kvmppc_booke_init(); | ||
222 | if (r) | ||
223 | return r; | ||
224 | |||
225 | return kvm_init(NULL, sizeof(struct kvmppc_vcpu_44x), THIS_MODULE); | ||
226 | } | ||
227 | |||
228 | static void kvmppc_44x_exit(void) | ||
229 | { | ||
230 | kvmppc_booke_exit(); | ||
231 | } | ||
232 | |||
233 | module_init(kvmppc_44x_init); | ||
234 | module_exit(kvmppc_44x_exit); | ||