mirror of
https://github.com/Fishwaldo/Star64_linux.git
synced 2025-06-26 16:41:25 +00:00
Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/s390/linux
Pull s390 fixes from Martin Schwidefsky: "Three bug fixes: - The fix for the page table corruption (CVE-2016-2143) - The diagnose statistics introduced a regression for the dasd diag driver - Boot crash on systems without the set-program-parameters facility" * 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/s390/linux: s390/mm: four page table levels vs. fork s390/cpumf: Fix lpp detection s390/dasd: fix diag 0x250 inline assembly
This commit is contained in:
commit
2da33f9f96
4 changed files with 38 additions and 13 deletions
|
@ -15,17 +15,25 @@
|
||||||
static inline int init_new_context(struct task_struct *tsk,
|
static inline int init_new_context(struct task_struct *tsk,
|
||||||
struct mm_struct *mm)
|
struct mm_struct *mm)
|
||||||
{
|
{
|
||||||
|
spin_lock_init(&mm->context.list_lock);
|
||||||
|
INIT_LIST_HEAD(&mm->context.pgtable_list);
|
||||||
|
INIT_LIST_HEAD(&mm->context.gmap_list);
|
||||||
cpumask_clear(&mm->context.cpu_attach_mask);
|
cpumask_clear(&mm->context.cpu_attach_mask);
|
||||||
atomic_set(&mm->context.attach_count, 0);
|
atomic_set(&mm->context.attach_count, 0);
|
||||||
mm->context.flush_mm = 0;
|
mm->context.flush_mm = 0;
|
||||||
mm->context.asce_bits = _ASCE_TABLE_LENGTH | _ASCE_USER_BITS;
|
|
||||||
mm->context.asce_bits |= _ASCE_TYPE_REGION3;
|
|
||||||
#ifdef CONFIG_PGSTE
|
#ifdef CONFIG_PGSTE
|
||||||
mm->context.alloc_pgste = page_table_allocate_pgste;
|
mm->context.alloc_pgste = page_table_allocate_pgste;
|
||||||
mm->context.has_pgste = 0;
|
mm->context.has_pgste = 0;
|
||||||
mm->context.use_skey = 0;
|
mm->context.use_skey = 0;
|
||||||
#endif
|
#endif
|
||||||
mm->context.asce_limit = STACK_TOP_MAX;
|
if (mm->context.asce_limit == 0) {
|
||||||
|
/* context created by exec, set asce limit to 4TB */
|
||||||
|
mm->context.asce_bits = _ASCE_TABLE_LENGTH |
|
||||||
|
_ASCE_USER_BITS | _ASCE_TYPE_REGION3;
|
||||||
|
mm->context.asce_limit = STACK_TOP_MAX;
|
||||||
|
} else if (mm->context.asce_limit == (1UL << 31)) {
|
||||||
|
mm_inc_nr_pmds(mm);
|
||||||
|
}
|
||||||
crst_table_init((unsigned long *) mm->pgd, pgd_entry_type(mm));
|
crst_table_init((unsigned long *) mm->pgd, pgd_entry_type(mm));
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
@ -111,8 +119,6 @@ static inline void activate_mm(struct mm_struct *prev,
|
||||||
static inline void arch_dup_mmap(struct mm_struct *oldmm,
|
static inline void arch_dup_mmap(struct mm_struct *oldmm,
|
||||||
struct mm_struct *mm)
|
struct mm_struct *mm)
|
||||||
{
|
{
|
||||||
if (oldmm->context.asce_limit < mm->context.asce_limit)
|
|
||||||
crst_table_downgrade(mm, oldmm->context.asce_limit);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static inline void arch_exit_mmap(struct mm_struct *mm)
|
static inline void arch_exit_mmap(struct mm_struct *mm)
|
||||||
|
|
|
@ -100,12 +100,26 @@ static inline void pud_populate(struct mm_struct *mm, pud_t *pud, pmd_t *pmd)
|
||||||
|
|
||||||
static inline pgd_t *pgd_alloc(struct mm_struct *mm)
|
static inline pgd_t *pgd_alloc(struct mm_struct *mm)
|
||||||
{
|
{
|
||||||
spin_lock_init(&mm->context.list_lock);
|
unsigned long *table = crst_table_alloc(mm);
|
||||||
INIT_LIST_HEAD(&mm->context.pgtable_list);
|
|
||||||
INIT_LIST_HEAD(&mm->context.gmap_list);
|
if (!table)
|
||||||
return (pgd_t *) crst_table_alloc(mm);
|
return NULL;
|
||||||
|
if (mm->context.asce_limit == (1UL << 31)) {
|
||||||
|
/* Forking a compat process with 2 page table levels */
|
||||||
|
if (!pgtable_pmd_page_ctor(virt_to_page(table))) {
|
||||||
|
crst_table_free(mm, table);
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return (pgd_t *) table;
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline void pgd_free(struct mm_struct *mm, pgd_t *pgd)
|
||||||
|
{
|
||||||
|
if (mm->context.asce_limit == (1UL << 31))
|
||||||
|
pgtable_pmd_page_dtor(virt_to_page(pgd));
|
||||||
|
crst_table_free(mm, (unsigned long *) pgd);
|
||||||
}
|
}
|
||||||
#define pgd_free(mm, pgd) crst_table_free(mm, (unsigned long *) pgd)
|
|
||||||
|
|
||||||
static inline void pmd_populate(struct mm_struct *mm,
|
static inline void pmd_populate(struct mm_struct *mm,
|
||||||
pmd_t *pmd, pgtable_t pte)
|
pmd_t *pmd, pgtable_t pte)
|
||||||
|
|
|
@ -16,7 +16,7 @@
|
||||||
|
|
||||||
__HEAD
|
__HEAD
|
||||||
ENTRY(startup_continue)
|
ENTRY(startup_continue)
|
||||||
tm __LC_STFLE_FAC_LIST+6,0x80 # LPP available ?
|
tm __LC_STFLE_FAC_LIST+5,0x80 # LPP available ?
|
||||||
jz 0f
|
jz 0f
|
||||||
xc __LC_LPP+1(7,0),__LC_LPP+1 # clear lpp and current_pid
|
xc __LC_LPP+1(7,0),__LC_LPP+1 # clear lpp and current_pid
|
||||||
mvi __LC_LPP,0x80 # and set LPP_MAGIC
|
mvi __LC_LPP,0x80 # and set LPP_MAGIC
|
||||||
|
|
|
@ -67,7 +67,7 @@ static const u8 DASD_DIAG_CMS1[] = { 0xc3, 0xd4, 0xe2, 0xf1 };/* EBCDIC CMS1 */
|
||||||
* and function code cmd.
|
* and function code cmd.
|
||||||
* In case of an exception return 3. Otherwise return result of bitwise OR of
|
* In case of an exception return 3. Otherwise return result of bitwise OR of
|
||||||
* resulting condition code and DIAG return code. */
|
* resulting condition code and DIAG return code. */
|
||||||
static inline int dia250(void *iob, int cmd)
|
static inline int __dia250(void *iob, int cmd)
|
||||||
{
|
{
|
||||||
register unsigned long reg2 asm ("2") = (unsigned long) iob;
|
register unsigned long reg2 asm ("2") = (unsigned long) iob;
|
||||||
typedef union {
|
typedef union {
|
||||||
|
@ -77,7 +77,6 @@ static inline int dia250(void *iob, int cmd)
|
||||||
int rc;
|
int rc;
|
||||||
|
|
||||||
rc = 3;
|
rc = 3;
|
||||||
diag_stat_inc(DIAG_STAT_X250);
|
|
||||||
asm volatile(
|
asm volatile(
|
||||||
" diag 2,%2,0x250\n"
|
" diag 2,%2,0x250\n"
|
||||||
"0: ipm %0\n"
|
"0: ipm %0\n"
|
||||||
|
@ -91,6 +90,12 @@ static inline int dia250(void *iob, int cmd)
|
||||||
return rc;
|
return rc;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static inline int dia250(void *iob, int cmd)
|
||||||
|
{
|
||||||
|
diag_stat_inc(DIAG_STAT_X250);
|
||||||
|
return __dia250(iob, cmd);
|
||||||
|
}
|
||||||
|
|
||||||
/* Initialize block I/O to DIAG device using the specified blocksize and
|
/* Initialize block I/O to DIAG device using the specified blocksize and
|
||||||
* block offset. On success, return zero and set end_block to contain the
|
* block offset. On success, return zero and set end_block to contain the
|
||||||
* number of blocks on the device minus the specified offset. Return non-zero
|
* number of blocks on the device minus the specified offset. Return non-zero
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue