84
84
85
85
#define PMDS_PER_MID_PAGE (P2M_MID_PER_PAGE / PTRS_PER_PTE)
86
86
87
- static void __init m2p_override_init (void );
88
-
89
87
unsigned long * xen_p2m_addr __read_mostly ;
90
88
EXPORT_SYMBOL_GPL (xen_p2m_addr );
91
89
unsigned long xen_p2m_size __read_mostly ;
@@ -402,8 +400,6 @@ void __init xen_vmalloc_p2m_tree(void)
402
400
xen_p2m_size = xen_max_p2m_pfn ;
403
401
404
402
xen_inv_extra_mem ();
405
-
406
- m2p_override_init ();
407
403
}
408
404
409
405
unsigned long get_phys_to_machine (unsigned long pfn )
@@ -652,100 +648,21 @@ bool set_phys_to_machine(unsigned long pfn, unsigned long mfn)
652
648
return true;
653
649
}
654
650
655
- #define M2P_OVERRIDE_HASH_SHIFT 10
656
- #define M2P_OVERRIDE_HASH (1 << M2P_OVERRIDE_HASH_SHIFT)
657
-
658
- static struct list_head * m2p_overrides ;
659
- static DEFINE_SPINLOCK (m2p_override_lock );
660
-
661
- static void __init m2p_override_init (void )
662
- {
663
- unsigned i ;
664
-
665
- m2p_overrides = alloc_bootmem_align (
666
- sizeof (* m2p_overrides ) * M2P_OVERRIDE_HASH ,
667
- sizeof (unsigned long ));
668
-
669
- for (i = 0 ; i < M2P_OVERRIDE_HASH ; i ++ )
670
- INIT_LIST_HEAD (& m2p_overrides [i ]);
671
- }
672
-
673
- static unsigned long mfn_hash (unsigned long mfn )
674
- {
675
- return hash_long (mfn , M2P_OVERRIDE_HASH_SHIFT );
676
- }
677
-
678
- /* Add an MFN override for a particular page */
679
- static int m2p_add_override (unsigned long mfn , struct page * page ,
680
- struct gnttab_map_grant_ref * kmap_op )
681
- {
682
- unsigned long flags ;
683
- unsigned long pfn ;
684
- unsigned long uninitialized_var (address );
685
- unsigned level ;
686
- pte_t * ptep = NULL ;
687
-
688
- pfn = page_to_pfn (page );
689
- if (!PageHighMem (page )) {
690
- address = (unsigned long )__va (pfn << PAGE_SHIFT );
691
- ptep = lookup_address (address , & level );
692
- if (WARN (ptep == NULL || level != PG_LEVEL_4K ,
693
- "m2p_add_override: pfn %lx not mapped" , pfn ))
694
- return - EINVAL ;
695
- }
696
-
697
- if (kmap_op != NULL ) {
698
- if (!PageHighMem (page )) {
699
- struct multicall_space mcs =
700
- xen_mc_entry (sizeof (* kmap_op ));
701
-
702
- MULTI_grant_table_op (mcs .mc ,
703
- GNTTABOP_map_grant_ref , kmap_op , 1 );
704
-
705
- xen_mc_issue (PARAVIRT_LAZY_MMU );
706
- }
707
- }
708
- spin_lock_irqsave (& m2p_override_lock , flags );
709
- list_add (& page -> lru , & m2p_overrides [mfn_hash (mfn )]);
710
- spin_unlock_irqrestore (& m2p_override_lock , flags );
711
-
712
- /* p2m(m2p(mfn)) == mfn: the mfn is already present somewhere in
713
- * this domain. Set the FOREIGN_FRAME_BIT in the p2m for the other
714
- * pfn so that the following mfn_to_pfn(mfn) calls will return the
715
- * pfn from the m2p_override (the backend pfn) instead.
716
- * We need to do this because the pages shared by the frontend
717
- * (xen-blkfront) can be already locked (lock_page, called by
718
- * do_read_cache_page); when the userspace backend tries to use them
719
- * with direct_IO, mfn_to_pfn returns the pfn of the frontend, so
720
- * do_blockdev_direct_IO is going to try to lock the same pages
721
- * again resulting in a deadlock.
722
- * As a side effect get_user_pages_fast might not be safe on the
723
- * frontend pages while they are being shared with the backend,
724
- * because mfn_to_pfn (that ends up being called by GUPF) will
725
- * return the backend pfn rather than the frontend pfn. */
726
- pfn = mfn_to_pfn_no_overrides (mfn );
727
- if (__pfn_to_mfn (pfn ) == mfn )
728
- set_phys_to_machine (pfn , FOREIGN_FRAME (mfn ));
729
-
730
- return 0 ;
731
- }
732
-
733
651
int set_foreign_p2m_mapping (struct gnttab_map_grant_ref * map_ops ,
734
652
struct gnttab_map_grant_ref * kmap_ops ,
735
653
struct page * * pages , unsigned int count )
736
654
{
737
655
int i , ret = 0 ;
738
- bool lazy = false;
739
656
pte_t * pte ;
740
657
741
658
if (xen_feature (XENFEAT_auto_translated_physmap ))
742
659
return 0 ;
743
660
744
- if (kmap_ops &&
745
- ! in_interrupt () &&
746
- paravirt_get_lazy_mode () == PARAVIRT_LAZY_NONE ) {
747
- arch_enter_lazy_mmu_mode ();
748
- lazy = true ;
661
+ if (kmap_ops ) {
662
+ ret = HYPERVISOR_grant_table_op ( GNTTABOP_map_grant_ref ,
663
+ kmap_ops , count );
664
+ if ( ret )
665
+ goto out ;
749
666
}
750
667
751
668
for (i = 0 ; i < count ; i ++ ) {
@@ -773,160 +690,22 @@ int set_foreign_p2m_mapping(struct gnttab_map_grant_ref *map_ops,
773
690
ret = - ENOMEM ;
774
691
goto out ;
775
692
}
776
-
777
- if (kmap_ops ) {
778
- ret = m2p_add_override (mfn , pages [i ], & kmap_ops [i ]);
779
- if (ret )
780
- goto out ;
781
- }
782
693
}
783
694
784
695
out :
785
- if (lazy )
786
- arch_leave_lazy_mmu_mode ();
787
-
788
696
return ret ;
789
697
}
790
698
EXPORT_SYMBOL_GPL (set_foreign_p2m_mapping );
791
699
792
- static struct page * m2p_find_override (unsigned long mfn )
793
- {
794
- unsigned long flags ;
795
- struct list_head * bucket ;
796
- struct page * p , * ret ;
797
-
798
- if (unlikely (!m2p_overrides ))
799
- return NULL ;
800
-
801
- ret = NULL ;
802
- bucket = & m2p_overrides [mfn_hash (mfn )];
803
-
804
- spin_lock_irqsave (& m2p_override_lock , flags );
805
-
806
- list_for_each_entry (p , bucket , lru ) {
807
- if (page_private (p ) == mfn ) {
808
- ret = p ;
809
- break ;
810
- }
811
- }
812
-
813
- spin_unlock_irqrestore (& m2p_override_lock , flags );
814
-
815
- return ret ;
816
- }
817
-
818
- static int m2p_remove_override (struct page * page ,
819
- struct gnttab_unmap_grant_ref * kunmap_op ,
820
- unsigned long mfn )
821
- {
822
- unsigned long flags ;
823
- unsigned long pfn ;
824
- unsigned long uninitialized_var (address );
825
- unsigned level ;
826
- pte_t * ptep = NULL ;
827
-
828
- pfn = page_to_pfn (page );
829
-
830
- if (!PageHighMem (page )) {
831
- address = (unsigned long )__va (pfn << PAGE_SHIFT );
832
- ptep = lookup_address (address , & level );
833
-
834
- if (WARN (ptep == NULL || level != PG_LEVEL_4K ,
835
- "m2p_remove_override: pfn %lx not mapped" , pfn ))
836
- return - EINVAL ;
837
- }
838
-
839
- spin_lock_irqsave (& m2p_override_lock , flags );
840
- list_del (& page -> lru );
841
- spin_unlock_irqrestore (& m2p_override_lock , flags );
842
-
843
- if (kunmap_op != NULL ) {
844
- if (!PageHighMem (page )) {
845
- struct multicall_space mcs ;
846
- struct gnttab_unmap_and_replace * unmap_op ;
847
- struct page * scratch_page = get_balloon_scratch_page ();
848
- unsigned long scratch_page_address = (unsigned long )
849
- __va (page_to_pfn (scratch_page ) << PAGE_SHIFT );
850
-
851
- /*
852
- * It might be that we queued all the m2p grant table
853
- * hypercalls in a multicall, then m2p_remove_override
854
- * get called before the multicall has actually been
855
- * issued. In this case handle is going to -1 because
856
- * it hasn't been modified yet.
857
- */
858
- if (kunmap_op -> handle == -1 )
859
- xen_mc_flush ();
860
- /*
861
- * Now if kmap_op->handle is negative it means that the
862
- * hypercall actually returned an error.
863
- */
864
- if (kunmap_op -> handle == GNTST_general_error ) {
865
- pr_warn ("m2p_remove_override: pfn %lx mfn %lx, failed to modify kernel mappings" ,
866
- pfn , mfn );
867
- put_balloon_scratch_page ();
868
- return -1 ;
869
- }
870
-
871
- xen_mc_batch ();
872
-
873
- mcs = __xen_mc_entry (
874
- sizeof (struct gnttab_unmap_and_replace ));
875
- unmap_op = mcs .args ;
876
- unmap_op -> host_addr = kunmap_op -> host_addr ;
877
- unmap_op -> new_addr = scratch_page_address ;
878
- unmap_op -> handle = kunmap_op -> handle ;
879
-
880
- MULTI_grant_table_op (mcs .mc ,
881
- GNTTABOP_unmap_and_replace , unmap_op , 1 );
882
-
883
- mcs = __xen_mc_entry (0 );
884
- MULTI_update_va_mapping (mcs .mc , scratch_page_address ,
885
- pfn_pte (page_to_pfn (scratch_page ),
886
- PAGE_KERNEL_RO ), 0 );
887
-
888
- xen_mc_issue (PARAVIRT_LAZY_MMU );
889
-
890
- put_balloon_scratch_page ();
891
- }
892
- }
893
-
894
- /* p2m(m2p(mfn)) == FOREIGN_FRAME(mfn): the mfn is already present
895
- * somewhere in this domain, even before being added to the
896
- * m2p_override (see comment above in m2p_add_override).
897
- * If there are no other entries in the m2p_override corresponding
898
- * to this mfn, then remove the FOREIGN_FRAME_BIT from the p2m for
899
- * the original pfn (the one shared by the frontend): the backend
900
- * cannot do any IO on this page anymore because it has been
901
- * unshared. Removing the FOREIGN_FRAME_BIT from the p2m entry of
902
- * the original pfn causes mfn_to_pfn(mfn) to return the frontend
903
- * pfn again. */
904
- mfn &= ~FOREIGN_FRAME_BIT ;
905
- pfn = mfn_to_pfn_no_overrides (mfn );
906
- if (__pfn_to_mfn (pfn ) == FOREIGN_FRAME (mfn ) &&
907
- m2p_find_override (mfn ) == NULL )
908
- set_phys_to_machine (pfn , mfn );
909
-
910
- return 0 ;
911
- }
912
-
913
700
int clear_foreign_p2m_mapping (struct gnttab_unmap_grant_ref * unmap_ops ,
914
701
struct gnttab_unmap_grant_ref * kunmap_ops ,
915
702
struct page * * pages , unsigned int count )
916
703
{
917
704
int i , ret = 0 ;
918
- bool lazy = false;
919
705
920
706
if (xen_feature (XENFEAT_auto_translated_physmap ))
921
707
return 0 ;
922
708
923
- if (kunmap_ops &&
924
- !in_interrupt () &&
925
- paravirt_get_lazy_mode () == PARAVIRT_LAZY_NONE ) {
926
- arch_enter_lazy_mmu_mode ();
927
- lazy = true;
928
- }
929
-
930
709
for (i = 0 ; i < count ; i ++ ) {
931
710
unsigned long mfn = __pfn_to_mfn (page_to_pfn (pages [i ]));
932
711
unsigned long pfn = page_to_pfn (pages [i ]);
@@ -940,32 +719,15 @@ int clear_foreign_p2m_mapping(struct gnttab_unmap_grant_ref *unmap_ops,
940
719
WARN_ON (!PagePrivate (pages [i ]));
941
720
ClearPagePrivate (pages [i ]);
942
721
set_phys_to_machine (pfn , pages [i ]-> index );
943
-
944
- if (kunmap_ops )
945
- ret = m2p_remove_override (pages [i ], & kunmap_ops [i ], mfn );
946
- if (ret )
947
- goto out ;
948
722
}
949
-
723
+ if (kunmap_ops )
724
+ ret = HYPERVISOR_grant_table_op (GNTTABOP_unmap_grant_ref ,
725
+ kunmap_ops , count );
950
726
out :
951
- if (lazy )
952
- arch_leave_lazy_mmu_mode ();
953
727
return ret ;
954
728
}
955
729
EXPORT_SYMBOL_GPL (clear_foreign_p2m_mapping );
956
730
957
- unsigned long m2p_find_override_pfn (unsigned long mfn , unsigned long pfn )
958
- {
959
- struct page * p = m2p_find_override (mfn );
960
- unsigned long ret = pfn ;
961
-
962
- if (p )
963
- ret = page_to_pfn (p );
964
-
965
- return ret ;
966
- }
967
- EXPORT_SYMBOL_GPL (m2p_find_override_pfn );
968
-
969
731
#ifdef CONFIG_XEN_DEBUG_FS
970
732
#include <linux/debugfs.h>
971
733
#include "debugfs.h"
0 commit comments