• Arnd Bergmann's avatar
    arm64: kvm: avoid overflow in integer division · 14c3555f
    Arnd Bergmann authored
    The newly added kvm_mmu_split_nr_page_tables() function uses DIV_ROUND_DOWN_ULL()
    to divide 64-bit addresses, but this requires a 32-bit divisior, and PUD_SIZE
    may exceed that when 64KB pages are used:
    
    arch/arm64/kvm/mmu.c: In function 'kvm_mmu_split_nr_page_tables':
    include/linux/math.h:42:64: error: conversion from 'long unsigned int' to 'u32' {aka 'unsigned int'} changes value from '68719476736' to '0' [-Werror=overflow]
       42 |         DIV_ROUND_DOWN_ULL((unsigned long long)(ll) + (d) - 1, (d))
          |                                                                ^~~
    include/linux/math.h:39:47: note: in definition of macro 'DIV_ROUND_DOWN_ULL'
       39 | #define DIV_ROUND_DOWN_ULL(ll, d) div_u64(ll, d)
          |                                               ^
    arch/arm64/kvm/mmu.c:95:22: note: in expansion of macro 'DIV_ROUND_UP_ULL'
       95 |                 n += DIV_ROUND_UP_ULL(range, PUD_SIZE);
          |                      ^~~~~~~~~~~~~~~~
    
    Since this code is only used on 64-bit targets, DIV_ROUND_UP() can deal with this
    more easily, as it already takes 64-bit arguments.
    
    Fixes: e7bf7a49 ("KVM: arm64: Split huge pages when dirty logging is enabled")
    Signed-off-by: default avatarArnd Bergmann <arnd@arndb.de>
    Link: https://lore.kernel.org/r/20230517202352.793673-1-arnd@kernel.orgSigned-off-by: default avatarOliver Upton <oliver.upton@linux.dev>
    14c3555f
mmu.c 55.8 KB