• Li Xinhai's avatar
    mm/mempolicy.c: fix checking unmapped holes for mbind · f18da660
    Li Xinhai authored
    mbind() is required to report EFAULT if range, specified by addr and
    len, contains unmapped holes.  In current implementation, below rules
    are applied for this checking:
    
     1: Unmapped holes at any part of the specified range should be reported
        as EFAULT if mbind() for none MPOL_DEFAULT cases;
    
     2: Unmapped holes at any part of the specified range should be ignored
        (do not reprot EFAULT) if mbind() for MPOL_DEFAULT case;
    
     3: The whole range in an unmapped hole should be reported as EFAULT;
    
    Note that rule 2 does not fullfill the mbind() API definition, but since
    that behavior has existed for long days (the internal flag
    MPOL_MF_DISCONTIG_OK is for this purpose), this patch does not plan to
    change it.
    
    In current code, application observed inconsistent behavior on rule 1
    and rule 2 respectively.  That inconsistency is fixed as below details.
    
    Cases of rule 1:
    
     - Hole at head side of range. Current code reprot EFAULT, no change by
       this patch.
    
        [  vma  ][ hole ][  vma  ]
                    [  range  ]
    
     - Hole at middle of range. Current code report EFAULT, no change by
       this patch.
    
        [  vma  ][ hole ][ vma ]
           [     range      ]
    
     - Hole at tail side of range. Current code do not report EFAULT, this
       patch fixes it.
    
        [  vma  ][ hole ][ vma ]
           [  range  ]
    
    Cases of rule 2:
    
     - Hole at head side of range. Current code reports EFAULT, this patch
       fixes it.
    
        [  vma  ][ hole ][  vma  ]
                    [  range  ]
    
     - Hole at middle of range. Current code does not report EFAULT, no
       change by this patch.
    
        [  vma  ][ hole ][ vma]
           [     range      ]
    
     - Hole at tail side of range. Current code does not report EFAULT, no
       change by this patch.
    
        [  vma  ][ hole ][ vma]
           [  range  ]
    
    This patch has no changes to rule 3.
    
    The unmapped hole checking can also be handled by using .pte_hole(),
    instead of .test_walk().  But .pte_hole() is called for holes inside and
    outside vma, which causes more cost, so this patch keeps the original
    design with .test_walk().
    
    Link: http://lkml.kernel.org/r/1573218104-11021-3-git-send-email-lixinhai.lxh@gmail.com
    Fixes: 6f4576e3 ("mempolicy: apply page table walker on queue_pages_range()")
    Signed-off-by: default avatarLi Xinhai <lixinhai.lxh@gmail.com>
    Reviewed-by: default avatarNaoya Horiguchi <n-horiguchi@ah.jp.nec.com>
    Cc: Michal Hocko <mhocko@suse.com>
    Cc: Vlastimil Babka <vbabka@suse.cz>
    Cc: Hugh Dickins <hughd@google.com>
    Cc: linux-man <linux-man@vger.kernel.org>
    Signed-off-by: default avatarAndrew Morton <akpm@linux-foundation.org>
    Signed-off-by: default avatarLinus Torvalds <torvalds@linux-foundation.org>
    f18da660
mempolicy.c 74.7 KB