Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 5b1e94fa authored by David S. Miller's avatar David S. Miller
Browse files

sparc64: Fix executable bit testing in set_pmd_at() paths.



This code was mistakenly using the exec bit from the PMD in all
cases, even when the PMD isn't a huge PMD.

If it's not a huge PMD, test the exec bit in the individual ptes down
in tlb_batch_pmd_scan().

Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 16ce8a30
Loading
Loading
Loading
Loading
+9 −6
Original line number Diff line number Diff line
@@ -134,7 +134,7 @@ void tlb_batch_add(struct mm_struct *mm, unsigned long vaddr,

#ifdef CONFIG_TRANSPARENT_HUGEPAGE
static void tlb_batch_pmd_scan(struct mm_struct *mm, unsigned long vaddr,
			       pmd_t pmd, bool exec)
			       pmd_t pmd)
{
	unsigned long end;
	pte_t *pte;
@@ -142,8 +142,11 @@ static void tlb_batch_pmd_scan(struct mm_struct *mm, unsigned long vaddr,
	pte = pte_offset_map(&pmd, vaddr);
	end = vaddr + HPAGE_SIZE;
	while (vaddr < end) {
		if (pte_val(*pte) & _PAGE_VALID)
		if (pte_val(*pte) & _PAGE_VALID) {
			bool exec = pte_exec(*pte);

			tlb_batch_add_one(mm, vaddr, exec);
		}
		pte++;
		vaddr += PAGE_SIZE;
	}
@@ -177,15 +180,15 @@ void set_pmd_at(struct mm_struct *mm, unsigned long addr,
	}

	if (!pmd_none(orig)) {
		addr &= HPAGE_MASK;
		if (pmd_trans_huge(orig)) {
			pte_t orig_pte = __pte(pmd_val(orig));
			bool exec = pte_exec(orig_pte);

		addr &= HPAGE_MASK;
		if (pmd_trans_huge(orig)) {
			tlb_batch_add_one(mm, addr, exec);
			tlb_batch_add_one(mm, addr + REAL_HPAGE_SIZE, exec);
		} else {
			tlb_batch_pmd_scan(mm, addr, orig, exec);
			tlb_batch_pmd_scan(mm, addr, orig);
		}
	}
}