diff mbox series

mm: hugetlb: fix dissolve_free_huge_page use of tail/head page

Message ID 20210527231225.226987-1-mike.kravetz@oracle.com (mailing list archive)
State New, archived
Headers show
Series mm: hugetlb: fix dissolve_free_huge_page use of tail/head page | expand

Commit Message

Mike Kravetz May 27, 2021, 11:12 p.m. UTC
The routine dissolve_free_huge_page can be passed the tail page of a
hugetlb page.  The tail page is incorrectly passed on to the routines
alloc_huge_page_vmemmap and add_hugetlb_page which expect a hugetlb
head page.

Operating on a tail page instead of head page could result in addressing
exceptions or vmemmap corruption.

Signed-off-by: Mike Kravetz <mike.kravetz@oracle.com>
---
The code with this issue is only in mmotm (and next).  Specifically
mm: hugetlb: alloc the vmemmap pages associated with each HugeTLB page
Andrew, I assume you will fix in your tree.

 mm/hugetlb.c            | 4 ++--
 scripts/rust-version.sh | 0
 2 files changed, 2 insertions(+), 2 deletions(-)
 mode change 100644 => 100755 scripts/rust-version.sh

Comments

kernel test robot May 28, 2021, 1:18 a.m. UTC | #1
Hi Mike,

I love your patch! Yet something to improve:

[auto build test ERROR on hnaz-linux-mm/master]

url:    https://github.com/0day-ci/linux/commits/Mike-Kravetz/mm-hugetlb-fix-dissolve_free_huge_page-use-of-tail-head-page/20210528-071337
base:   https://github.com/hnaz/linux-mm master
config: m68k-randconfig-c023-20210528 (attached as .config)
compiler: m68k-linux-gcc (GCC) 9.3.0
reproduce (this is a W=1 build):
        wget https://raw.githubusercontent.com/intel/lkp-tests/master/sbin/make.cross -O ~/bin/make.cross
        chmod +x ~/bin/make.cross
        # https://github.com/0day-ci/linux/commit/b26b543d785ced93e7db05483ddc20e8fa45059e
        git remote add linux-review https://github.com/0day-ci/linux
        git fetch --no-tags linux-review Mike-Kravetz/mm-hugetlb-fix-dissolve_free_huge_page-use-of-tail-head-page/20210528-071337
        git checkout b26b543d785ced93e7db05483ddc20e8fa45059e
        # save the attached .config to linux build tree
        COMPILER_INSTALL_PATH=$HOME/0day COMPILER=gcc-9.3.0 make.cross ARCH=m68k 

If you fix the issue, kindly add following tag as appropriate
Reported-by: kernel test robot <lkp@intel.com>

All errors (new ones prefixed by >>):

   arch/m68k/math-emu/fp_arith.c:310:1: warning: no previous prototype for 'fp_fsglmul' [-Wmissing-prototypes]
     310 | fp_fsglmul(struct fp_ext *dest, struct fp_ext *src)
         | ^~~~~~~~~~
   arch/m68k/math-emu/fp_arith.c:367:1: warning: no previous prototype for 'fp_fsgldiv' [-Wmissing-prototypes]
     367 | fp_fsgldiv(struct fp_ext *dest, struct fp_ext *src)
         | ^~~~~~~~~~
   {standard input}: Assembler messages:
   {standard input}:333: Error: invalid instruction for this architecture; needs 68000 or higher (68000 [68ec000, 68hc000, 68hc001, 68008, 68302, 68306, 68307, 68322, 68356], 68010, 68020 [68k, 68ec020], 68030 [68ec030], 68040 [68ec040], 68060 [68ec060], cpu32 [68330, 68331, 68332, 68333, 68334, 68336, 68340, 68341, 68349, 68360], fidoa [fido]) -- statement `sub.b %d2,%d3' ignored
   {standard input}:465: Error: invalid instruction for this architecture; needs 68000 or higher (68000 [68ec000, 68hc000, 68hc001, 68008, 68302, 68306, 68307, 68322, 68356], 68010, 68020 [68k, 68ec020], 68030 [68ec030], 68040 [68ec040], 68060 [68ec060], cpu32 [68330, 68331, 68332, 68333, 68334, 68336, 68340, 68341, 68349, 68360], fidoa [fido]) -- statement `add.b %d3,%d2' ignored
   {standard input}:511: Error: invalid instruction for this architecture; needs 68000 or higher (68000 [68ec000, 68hc000, 68hc001, 68008, 68302, 68306, 68307, 68322, 68356], 68010, 68020 [68k, 68ec020], 68030 [68ec030], 68040 [68ec040], 68060 [68ec060], cpu32 [68330, 68331, 68332, 68333, 68334, 68336, 68340, 68341, 68349, 68360], fidoa [fido]) -- statement `sub.b %d3,%d2' ignored
   {standard input}:670: Error: invalid instruction for this architecture; needs 68020 or higher (68020 [68k, 68ec020], 68030 [68ec030], 68040 [68ec040], 68060 [68ec060]) -- statement `bfextu 4(%a4){%d3,#8},%d3' ignored
   {standard input}:712: Error: invalid instruction for this architecture; needs 68020 or higher (68020 [68k, 68ec020], 68030 [68ec030], 68040 [68ec040], 68060 [68ec060]) -- statement `bfextu 4(%a3){%d2,#8},%d2' ignored
>> {standard input}:862: Error: operands mismatch -- statement `mulu.l 4(%a3),%d4:%d0' ignored
>> {standard input}:862: Error: operands mismatch -- statement `mulu.l 8(%a3),%d1:%d3' ignored
   {standard input}:862: Error: operands mismatch -- statement `mulu.l 4(%a3),%d6:%d5' ignored
   {standard input}:868: Error: operands mismatch -- statement `mulu.l 8(%a3),%d7:%d5' ignored
   {standard input}:876: Error: invalid instruction for this architecture; needs 68000 or higher (68000 [68ec000, 68hc000, 68hc001, 68008, 68302, 68306, 68307, 68322, 68356], 68010, 68020 [68k, 68ec020], 68030 [68ec030], 68040 [68ec040], 68060 [68ec060], cpu32 [68330, 68331, 68332, 68333, 68334, 68336, 68340, 68341, 68349, 68360], fidoa [fido]) -- statement `roxl.l #1,%d0' ignored
   {standard input}:879: Error: invalid instruction for this architecture; needs 68000 or higher (68000 [68ec000, 68hc000, 68hc001, 68008, 68302, 68306, 68307, 68322, 68356], 68010, 68020 [68k, 68ec020], 68030 [68ec030], 68040 [68ec040], 68060 [68ec060], cpu32 [68330, 68331, 68332, 68333, 68334, 68336, 68340, 68341, 68349, 68360], fidoa [fido]) -- statement `roxl.l #1,%d4' ignored
   {standard input}:979: Error: invalid instruction for this architecture; needs 68020 or higher (68020 [68k, 68ec020], 68030 [68ec030], 68040 [68ec040], 68060 [68ec060]) -- statement `bfffo %d0{#0,#32},%d1' ignored
   {standard input}:996: Error: invalid instruction for this architecture; needs 68020 or higher (68020 [68k, 68ec020], 68030 [68ec030], 68040 [68ec040], 68060 [68ec060]) -- statement `bfffo %d1{#0,#32},%d0' ignored
   {standard input}:1083: Error: invalid instruction for this architecture; needs 68020 or higher (68020 [68k, 68ec020], 68030 [68ec030], 68040 [68ec040], 68060 [68ec060]) -- statement `bfffo %d3{#0,#32},%d0' ignored
   {standard input}:1093: Error: invalid instruction for this architecture; needs 68020 or higher (68020 [68k, 68ec020], 68030 [68ec030], 68040 [68ec040], 68060 [68ec060]) -- statement `bfffo %d3{#0,#32},%d1' ignored
   {standard input}:1167: Error: invalid instruction for this architecture; needs 68020 or higher (68020 [68k, 68ec020], 68030 [68ec030], 68040 [68ec040], 68060 [68ec060]) -- statement `bfextu 4(%a3){%d0,#8},%d0' ignored
>> {standard input}:1317: Error: operands mismatch -- statement `divu.l %d0,%d4:%d3' ignored
   {standard input}:1326: Error: operands mismatch -- statement `divu.l %d2,%d4:%d1' ignored
   {standard input}:1330: Error: operands mismatch -- statement `mulu.l %d1,%d3:%d0' ignored
>> {standard input}:1333: Error: operands mismatch -- statement `mulu.l %d3,%d7:%d2' ignored
   {standard input}:1338: Error: operands mismatch -- statement `mulu.l 4(%a4),%d0:%d1' ignored
   {standard input}:1373: Error: operands mismatch -- statement `divu.l %d2,%d4:%d1' ignored
   {standard input}:1373: Error: operands mismatch -- statement `mulu.l %d1,%d3:%d0' ignored
   {standard input}:1379: Error: operands mismatch -- statement `mulu.l %d3,%d7:%d2' ignored
   {standard input}:1379: Error: operands mismatch -- statement `mulu.l 4(%a4),%d0:%d1' ignored
   {standard input}:1496: Error: operands mismatch -- statement `divu.l %d0,%d4:%d3' ignored
   {standard input}:1504: Error: invalid instruction for this architecture; needs 68020 or higher (68020 [68k, 68ec020], 68030 [68ec030], 68040 [68ec040], 68060 [68ec060]) -- statement `bfffo %d1{#0,#32},%d2' ignored
   {standard input}:1522: Error: invalid instruction for this architecture; needs 68020 or higher (68020 [68k, 68ec020], 68030 [68ec030], 68040 [68ec040], 68060 [68ec060]) -- statement `bfffo %d0{#0,#32},%d1' ignored
   {standard input}:1577: Error: invalid instruction for this architecture; needs 68000 or higher (68000 [68ec000, 68hc000, 68hc001, 68008, 68302, 68306, 68307, 68322, 68356], 68010, 68020 [68k, 68ec020], 68030 [68ec030], 68040 [68ec040], 68060 [68ec060], cpu32 [68330, 68331, 68332, 68333, 68334, 68336, 68340, 68341, 68349, 68360], fidoa [fido]) -- statement `roxr.l #1,%d1' ignored
   {standard input}:1581: Error: invalid instruction for this architecture; needs 68000 or higher (68000 [68ec000, 68hc000, 68hc001, 68008, 68302, 68306, 68307, 68322, 68356], 68010, 68020 [68k, 68ec020], 68030 [68ec030], 68040 [68ec040], 68060 [68ec060], cpu32 [68330, 68331, 68332, 68333, 68334, 68336, 68340, 68341, 68349, 68360], fidoa [fido]) -- statement `roxr.l #1,%d2' ignored
   {standard input}:1586: Error: invalid instruction for this architecture; needs 68000 or higher (68000 [68ec000, 68hc000, 68hc001, 68008, 68302, 68306, 68307, 68322, 68356], 68010, 68020 [68k, 68ec020], 68030 [68ec030], 68040 [68ec040], 68060 [68ec060], cpu32 [68330, 68331, 68332, 68333, 68334, 68336, 68340, 68341, 68349, 68360], fidoa [fido]) -- statement `roxr.l #1,%d0' ignored
   {standard input}:1599: Error: invalid instruction for this architecture; needs 68020 or higher (68020 [68k, 68ec020], 68030 [68ec030], 68040 [68ec040], 68060 [68ec060]) -- statement `bfffo %d2{#0,#32},%d1' ignored
   {standard input}:1609: Error: invalid instruction for this architecture; needs 68020 or higher (68020 [68k, 68ec020], 68030 [68ec030], 68040 [68ec040], 68060 [68ec060]) -- statement `bfffo %d0{#0,#32},%d2' ignored
   {standard input}:1684: Error: invalid instruction for this architecture; needs 68020 or higher (68020 [68k, 68ec020], 68030 [68ec030], 68040 [68ec040], 68060 [68ec060]) -- statement `bfextu 4(%a3){%d0,#8},%d0' ignored
   {standard input}:1859: Error: operands mismatch -- statement `mulu.l %d3,%d3:%d0' ignored
   {standard input}:2070: Error: invalid instruction for this architecture; needs 68020 or higher (68020 [68k, 68ec020], 68030 [68ec030], 68040 [68ec040], 68060 [68ec060]) -- statement `bfextu 4(%a3){%d0,#8},%d0' ignored
   {standard input}:2200: Error: operands mismatch -- statement `divu.l 4(%a4),%d0:%d2' ignored
   {standard input}:2283: Error: operands mismatch -- statement `divu.l %d2,%d0:%d3' ignored
   {standard input}:2378: Error: invalid instruction for this architecture; needs 68020 or higher (68020 [68k, 68ec020], 68030 [68ec030], 68040 [68ec040], 68060 [68ec060]) -- statement `bfextu 4(%a3){%d0,#8},%d0' ignored
   {standard input}:2705: Error: invalid instruction for this architecture; needs 68020 or higher (68020 [68k, 68ec020], 68030 [68ec030], 68040 [68ec040], 68060 [68ec060]) -- statement `bfextu 4(%a3){%d1,#8},%d1' ignored

---
0-DAY CI Kernel Test Service, Intel Corporation
https://lists.01.org/hyperkitty/list/kbuild-all@lists.01.org
Muchun Song May 28, 2021, 2:42 a.m. UTC | #2
On Fri, May 28, 2021 at 7:12 AM Mike Kravetz <mike.kravetz@oracle.com> wrote:
>
> The routine dissolve_free_huge_page can be passed the tail page of a
> hugetlb page.  The tail page is incorrectly passed on to the routines
> alloc_huge_page_vmemmap and add_hugetlb_page which expect a hugetlb
> head page.
>
> Operating on a tail page instead of head page could result in addressing
> exceptions or vmemmap corruption.
>
> Signed-off-by: Mike Kravetz <mike.kravetz@oracle.com>
> ---
> The code with this issue is only in mmotm (and next).  Specifically
> mm: hugetlb: alloc the vmemmap pages associated with each HugeTLB page
> Andrew, I assume you will fix in your tree.

Sorry. It's my bad commit. Thanks Mike for fixing this. I suspect this
should be squashed to "mm: hugetlb: alloc the vmemmap pages
associated with each HugeTLB page".

Reviewed-by: Muchun Song <songmuchun@bytedance.com>

Thanks.

>
>  mm/hugetlb.c            | 4 ++--
>  scripts/rust-version.sh | 0
>  2 files changed, 2 insertions(+), 2 deletions(-)
>  mode change 100644 => 100755 scripts/rust-version.sh
>
> diff --git a/mm/hugetlb.c b/mm/hugetlb.c
> index 69a4b551c157..d2461c1f32dd 100644
> --- a/mm/hugetlb.c
> +++ b/mm/hugetlb.c
> @@ -1954,7 +1954,7 @@ int dissolve_free_huge_page(struct page *page)
>                  * Attempt to allocate vmemmmap here so that we can take
>                  * appropriate action on failure.
>                  */
> -               rc = alloc_huge_page_vmemmap(h, page);
> +               rc = alloc_huge_page_vmemmap(h, head);
>                 if (!rc) {
>                         /*
>                          * Move PageHWPoison flag from head page to the raw
> @@ -1968,7 +1968,7 @@ int dissolve_free_huge_page(struct page *page)
>                         update_and_free_page(h, head, false);
>                 } else {
>                         spin_lock_irq(&hugetlb_lock);
> -                       add_hugetlb_page(h, page, false);
> +                       add_hugetlb_page(h, head, false);
>                         h->max_huge_pages++;
>                         spin_unlock_irq(&hugetlb_lock);
>                 }
> diff --git a/scripts/rust-version.sh b/scripts/rust-version.sh
> old mode 100644
> new mode 100755
> --
> 2.31.1
>
Oscar Salvador May 28, 2021, 7:30 a.m. UTC | #3
On Thu, May 27, 2021 at 04:12:25PM -0700, Mike Kravetz wrote:
> The routine dissolve_free_huge_page can be passed the tail page of a
> hugetlb page.  The tail page is incorrectly passed on to the routines
> alloc_huge_page_vmemmap and add_hugetlb_page which expect a hugetlb
> head page.
> 
> Operating on a tail page instead of head page could result in addressing
> exceptions or vmemmap corruption.
> 
> Signed-off-by: Mike Kravetz <mike.kravetz@oracle.com>

I guess Andrew will squash the changes, but fwiw:

Reviewed-by: Oscar Salvador <osalvador@suse.de>
Michal Hocko May 31, 2021, 6:48 a.m. UTC | #4
On Thu 27-05-21 16:12:25, Mike Kravetz wrote:
> The routine dissolve_free_huge_page can be passed the tail page of a
> hugetlb page.  The tail page is incorrectly passed on to the routines
> alloc_huge_page_vmemmap and add_hugetlb_page which expect a hugetlb
> head page.
> 
> Operating on a tail page instead of head page could result in addressing
> exceptions or vmemmap corruption.
> 
> Signed-off-by: Mike Kravetz <mike.kravetz@oracle.com>

Acked-by: Michal Hocko <mhocko@suse.com>

> ---
> The code with this issue is only in mmotm (and next).  Specifically
> mm: hugetlb: alloc the vmemmap pages associated with each HugeTLB page
> Andrew, I assume you will fix in your tree.

Yes, folding this in sounds like the best way forward.

> 
>  mm/hugetlb.c            | 4 ++--
>  scripts/rust-version.sh | 0
>  2 files changed, 2 insertions(+), 2 deletions(-)
>  mode change 100644 => 100755 scripts/rust-version.sh
> 
> diff --git a/mm/hugetlb.c b/mm/hugetlb.c
> index 69a4b551c157..d2461c1f32dd 100644
> --- a/mm/hugetlb.c
> +++ b/mm/hugetlb.c
> @@ -1954,7 +1954,7 @@ int dissolve_free_huge_page(struct page *page)
>  		 * Attempt to allocate vmemmmap here so that we can take
>  		 * appropriate action on failure.
>  		 */
> -		rc = alloc_huge_page_vmemmap(h, page);
> +		rc = alloc_huge_page_vmemmap(h, head);
>  		if (!rc) {
>  			/*
>  			 * Move PageHWPoison flag from head page to the raw
> @@ -1968,7 +1968,7 @@ int dissolve_free_huge_page(struct page *page)
>  			update_and_free_page(h, head, false);
>  		} else {
>  			spin_lock_irq(&hugetlb_lock);
> -			add_hugetlb_page(h, page, false);
> +			add_hugetlb_page(h, head, false);
>  			h->max_huge_pages++;
>  			spin_unlock_irq(&hugetlb_lock);
>  		}
> diff --git a/scripts/rust-version.sh b/scripts/rust-version.sh
> old mode 100644
> new mode 100755
> -- 
> 2.31.1
>
diff mbox series

Patch

diff --git a/mm/hugetlb.c b/mm/hugetlb.c
index 69a4b551c157..d2461c1f32dd 100644
--- a/mm/hugetlb.c
+++ b/mm/hugetlb.c
@@ -1954,7 +1954,7 @@  int dissolve_free_huge_page(struct page *page)
 		 * Attempt to allocate vmemmmap here so that we can take
 		 * appropriate action on failure.
 		 */
-		rc = alloc_huge_page_vmemmap(h, page);
+		rc = alloc_huge_page_vmemmap(h, head);
 		if (!rc) {
 			/*
 			 * Move PageHWPoison flag from head page to the raw
@@ -1968,7 +1968,7 @@  int dissolve_free_huge_page(struct page *page)
 			update_and_free_page(h, head, false);
 		} else {
 			spin_lock_irq(&hugetlb_lock);
-			add_hugetlb_page(h, page, false);
+			add_hugetlb_page(h, head, false);
 			h->max_huge_pages++;
 			spin_unlock_irq(&hugetlb_lock);
 		}
diff --git a/scripts/rust-version.sh b/scripts/rust-version.sh
old mode 100644
new mode 100755