mirror of
git://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
synced 2025-08-05 16:54:27 +00:00
s390/mm,fault: use get_kernel_nofault() to dereference in dump_pagetable()
The page table dumper uses get_kernel_nofault() to test if dereferencing page table entries is possible. Use the result, which is the required page table entry, instead of throwing it away and dereferencing a second time without any safe guard. Reviewed-by: Claudio Imbrenda <imbrenda@linux.ibm.com> Signed-off-by: Heiko Carstens <hca@linux.ibm.com> Signed-off-by: Vasily Gorbik <gor@linux.ibm.com>
This commit is contained in:
parent
5be05c35e7
commit
f67c2da9f1
1 changed files with 19 additions and 26 deletions
|
@ -112,59 +112,52 @@ static __always_inline bool fault_is_write(struct pt_regs *regs)
|
|||
return false;
|
||||
}
|
||||
|
||||
static int bad_address(void *p)
|
||||
{
|
||||
unsigned long dummy;
|
||||
|
||||
return get_kernel_nofault(dummy, (unsigned long *)p);
|
||||
}
|
||||
|
||||
static void dump_pagetable(unsigned long asce, unsigned long address)
|
||||
{
|
||||
unsigned long *table = __va(asce & _ASCE_ORIGIN);
|
||||
unsigned long entry, *table = __va(asce & _ASCE_ORIGIN);
|
||||
|
||||
pr_alert("AS:%016lx ", asce);
|
||||
switch (asce & _ASCE_TYPE_MASK) {
|
||||
case _ASCE_TYPE_REGION1:
|
||||
table += (address & _REGION1_INDEX) >> _REGION1_SHIFT;
|
||||
if (bad_address(table))
|
||||
if (get_kernel_nofault(entry, table))
|
||||
goto bad;
|
||||
pr_cont("R1:%016lx ", *table);
|
||||
if (*table & _REGION_ENTRY_INVALID)
|
||||
pr_cont("R1:%016lx ", entry);
|
||||
if (entry & _REGION_ENTRY_INVALID)
|
||||
goto out;
|
||||
table = __va(*table & _REGION_ENTRY_ORIGIN);
|
||||
table = __va(entry & _REGION_ENTRY_ORIGIN);
|
||||
fallthrough;
|
||||
case _ASCE_TYPE_REGION2:
|
||||
table += (address & _REGION2_INDEX) >> _REGION2_SHIFT;
|
||||
if (bad_address(table))
|
||||
if (get_kernel_nofault(entry, table))
|
||||
goto bad;
|
||||
pr_cont("R2:%016lx ", *table);
|
||||
if (*table & _REGION_ENTRY_INVALID)
|
||||
pr_cont("R2:%016lx ", entry);
|
||||
if (entry & _REGION_ENTRY_INVALID)
|
||||
goto out;
|
||||
table = __va(*table & _REGION_ENTRY_ORIGIN);
|
||||
table = __va(entry & _REGION_ENTRY_ORIGIN);
|
||||
fallthrough;
|
||||
case _ASCE_TYPE_REGION3:
|
||||
table += (address & _REGION3_INDEX) >> _REGION3_SHIFT;
|
||||
if (bad_address(table))
|
||||
if (get_kernel_nofault(entry, table))
|
||||
goto bad;
|
||||
pr_cont("R3:%016lx ", *table);
|
||||
if (*table & (_REGION_ENTRY_INVALID | _REGION3_ENTRY_LARGE))
|
||||
pr_cont("R3:%016lx ", entry);
|
||||
if (entry & (_REGION_ENTRY_INVALID | _REGION3_ENTRY_LARGE))
|
||||
goto out;
|
||||
table = __va(*table & _REGION_ENTRY_ORIGIN);
|
||||
table = __va(entry & _REGION_ENTRY_ORIGIN);
|
||||
fallthrough;
|
||||
case _ASCE_TYPE_SEGMENT:
|
||||
table += (address & _SEGMENT_INDEX) >> _SEGMENT_SHIFT;
|
||||
if (bad_address(table))
|
||||
if (get_kernel_nofault(entry, table))
|
||||
goto bad;
|
||||
pr_cont("S:%016lx ", *table);
|
||||
if (*table & (_SEGMENT_ENTRY_INVALID | _SEGMENT_ENTRY_LARGE))
|
||||
pr_cont("S:%016lx ", entry);
|
||||
if (entry & (_SEGMENT_ENTRY_INVALID | _SEGMENT_ENTRY_LARGE))
|
||||
goto out;
|
||||
table = __va(*table & _SEGMENT_ENTRY_ORIGIN);
|
||||
table = __va(entry & _SEGMENT_ENTRY_ORIGIN);
|
||||
}
|
||||
table += (address & _PAGE_INDEX) >> _PAGE_SHIFT;
|
||||
if (bad_address(table))
|
||||
if (get_kernel_nofault(entry, table))
|
||||
goto bad;
|
||||
pr_cont("P:%016lx ", *table);
|
||||
pr_cont("P:%016lx ", entry);
|
||||
out:
|
||||
pr_cont("\n");
|
||||
return;
|
||||
|
|
Loading…
Add table
Reference in a new issue