Commit | Line | Data |
---|---|---|
feef87eb VK |
1 | #include <linux/types.h> |
2 | #include <linux/crash_dump.h> | |
3 | ||
4 | #include <xen/interface/xen.h> | |
5 | #include <xen/hvm.h> | |
6 | ||
7 | #include "mmu.h" | |
8 | ||
9 | #ifdef CONFIG_PROC_VMCORE | |
10 | /* | |
11 | * This function is used in two contexts: | |
12 | * - the kdump kernel has to check whether a pfn of the crashed kernel | |
13 | * was a ballooned page. vmcore is using this function to decide | |
14 | * whether to access a pfn of the crashed kernel. | |
15 | * - the kexec kernel has to check whether a pfn was ballooned by the | |
16 | * previous kernel. If the pfn is ballooned, handle it properly. | |
17 | * Returns 0 if the pfn is not backed by a RAM page, the caller may | |
18 | * handle the pfn special in this case. | |
19 | */ | |
20 | static int xen_oldmem_pfn_is_ram(unsigned long pfn) | |
21 | { | |
22 | struct xen_hvm_get_mem_type a = { | |
23 | .domid = DOMID_SELF, | |
24 | .pfn = pfn, | |
25 | }; | |
26 | int ram; | |
27 | ||
28 | if (HYPERVISOR_hvm_op(HVMOP_get_mem_type, &a)) | |
29 | return -ENXIO; | |
30 | ||
31 | switch (a.mem_type) { | |
32 | case HVMMEM_mmio_dm: | |
33 | ram = 0; | |
34 | break; | |
35 | case HVMMEM_ram_rw: | |
36 | case HVMMEM_ram_ro: | |
37 | default: | |
38 | ram = 1; | |
39 | break; | |
40 | } | |
41 | ||
42 | return ram; | |
43 | } | |
44 | #endif | |
45 | ||
46 | static void xen_hvm_exit_mmap(struct mm_struct *mm) | |
47 | { | |
48 | struct xen_hvm_pagetable_dying a; | |
49 | int rc; | |
50 | ||
51 | a.domid = DOMID_SELF; | |
52 | a.gpa = __pa(mm->pgd); | |
53 | rc = HYPERVISOR_hvm_op(HVMOP_pagetable_dying, &a); | |
54 | WARN_ON_ONCE(rc < 0); | |
55 | } | |
56 | ||
57 | static int is_pagetable_dying_supported(void) | |
58 | { | |
59 | struct xen_hvm_pagetable_dying a; | |
60 | int rc = 0; | |
61 | ||
62 | a.domid = DOMID_SELF; | |
63 | a.gpa = 0x00; | |
64 | rc = HYPERVISOR_hvm_op(HVMOP_pagetable_dying, &a); | |
65 | if (rc < 0) { | |
66 | printk(KERN_DEBUG "HVMOP_pagetable_dying not supported\n"); | |
67 | return 0; | |
68 | } | |
69 | return 1; | |
70 | } | |
71 | ||
72 | void __init xen_hvm_init_mmu_ops(void) | |
73 | { | |
74 | if (is_pagetable_dying_supported()) | |
75 | pv_mmu_ops.exit_mmap = xen_hvm_exit_mmap; | |
76 | #ifdef CONFIG_PROC_VMCORE | |
77 | register_oldmem_pfn_is_ram(&xen_oldmem_pfn_is_ram); | |
78 | #endif | |
79 | } |