aboutsummaryrefslogtreecommitdiffstats
path: root/arch
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2013-06-03 05:04:07 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2013-06-03 05:04:07 -0400
commit286e050bc07a5ffcd7497e686c09b986d5ae6c6d (patch)
treeaa95ca5ccc7f083cf1d99c171f7e60676f1bb869 /arch
parent7d80fea4263d9a83ffedea448afa8510b05d04d0 (diff)
parente86cbd8765bd2e1f9eeb209822449c9b1e5958cf (diff)
Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/s390/linux
Pull s390 fixes from Martin Schwidefsky: "Recent bug fixes, one of them touches a common code file. It adds two #ifndef/#endif pairs to asm-generic/io.h to be able to override xlate_dev_kmem_ptr and xlate_dev_mem_ptr." * 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/s390/linux: s390/pgtable: Fix gmap notifier address s390/dasd: fix handling of gone paths s390/pgtable: Fix check for pgste/storage key handling arch: s390: appldata: using strncpy() and strnlen() instead of sprintf() s390/smp: lost IPIs on cpu hotplug kernel: Fix s390 absolute memory access for /dev/mem s390/dma: do not call debug_dma after free
Diffstat (limited to 'arch')
-rw-r--r--arch/s390/appldata/appldata_base.c7
-rw-r--r--arch/s390/include/asm/dma-mapping.h2
-rw-r--r--arch/s390/include/asm/io.h1
-rw-r--r--arch/s390/include/asm/pgtable.h15
-rw-r--r--arch/s390/kernel/smp.c27
-rw-r--r--arch/s390/mm/pgtable.c2
6 files changed, 30 insertions, 24 deletions
diff --git a/arch/s390/appldata/appldata_base.c b/arch/s390/appldata/appldata_base.c
index bae0f402bf2a..87a22092b68f 100644
--- a/arch/s390/appldata/appldata_base.c
+++ b/arch/s390/appldata/appldata_base.c
@@ -212,7 +212,9 @@ appldata_timer_handler(ctl_table *ctl, int write,
212 return 0; 212 return 0;
213 } 213 }
214 if (!write) { 214 if (!write) {
215 len = sprintf(buf, appldata_timer_active ? "1\n" : "0\n"); 215 strncpy(buf, appldata_timer_active ? "1\n" : "0\n",
216 ARRAY_SIZE(buf));
217 len = strnlen(buf, ARRAY_SIZE(buf));
216 if (len > *lenp) 218 if (len > *lenp)
217 len = *lenp; 219 len = *lenp;
218 if (copy_to_user(buffer, buf, len)) 220 if (copy_to_user(buffer, buf, len))
@@ -317,7 +319,8 @@ appldata_generic_handler(ctl_table *ctl, int write,
317 return 0; 319 return 0;
318 } 320 }
319 if (!write) { 321 if (!write) {
320 len = sprintf(buf, ops->active ? "1\n" : "0\n"); 322 strncpy(buf, ops->active ? "1\n" : "0\n", ARRAY_SIZE(buf));
323 len = strnlen(buf, ARRAY_SIZE(buf));
321 if (len > *lenp) 324 if (len > *lenp)
322 len = *lenp; 325 len = *lenp;
323 if (copy_to_user(buffer, buf, len)) { 326 if (copy_to_user(buffer, buf, len)) {
diff --git a/arch/s390/include/asm/dma-mapping.h b/arch/s390/include/asm/dma-mapping.h
index 9411db653bac..886ac7d4937a 100644
--- a/arch/s390/include/asm/dma-mapping.h
+++ b/arch/s390/include/asm/dma-mapping.h
@@ -71,8 +71,8 @@ static inline void dma_free_coherent(struct device *dev, size_t size,
71{ 71{
72 struct dma_map_ops *dma_ops = get_dma_ops(dev); 72 struct dma_map_ops *dma_ops = get_dma_ops(dev);
73 73
74 dma_ops->free(dev, size, cpu_addr, dma_handle, NULL);
75 debug_dma_free_coherent(dev, size, cpu_addr, dma_handle); 74 debug_dma_free_coherent(dev, size, cpu_addr, dma_handle);
75 dma_ops->free(dev, size, cpu_addr, dma_handle, NULL);
76} 76}
77 77
78#endif /* _ASM_S390_DMA_MAPPING_H */ 78#endif /* _ASM_S390_DMA_MAPPING_H */
diff --git a/arch/s390/include/asm/io.h b/arch/s390/include/asm/io.h
index 379d96e2105e..fd9be010f9b2 100644
--- a/arch/s390/include/asm/io.h
+++ b/arch/s390/include/asm/io.h
@@ -36,6 +36,7 @@ static inline void * phys_to_virt(unsigned long address)
36} 36}
37 37
38void *xlate_dev_mem_ptr(unsigned long phys); 38void *xlate_dev_mem_ptr(unsigned long phys);
39#define xlate_dev_mem_ptr xlate_dev_mem_ptr
39void unxlate_dev_mem_ptr(unsigned long phys, void *addr); 40void unxlate_dev_mem_ptr(unsigned long phys, void *addr);
40 41
41/* 42/*
diff --git a/arch/s390/include/asm/pgtable.h b/arch/s390/include/asm/pgtable.h
index 0f0de30e3e3f..ac01463038f1 100644
--- a/arch/s390/include/asm/pgtable.h
+++ b/arch/s390/include/asm/pgtable.h
@@ -646,7 +646,7 @@ static inline pgste_t pgste_update_all(pte_t *ptep, pgste_t pgste)
646 unsigned long address, bits; 646 unsigned long address, bits;
647 unsigned char skey; 647 unsigned char skey;
648 648
649 if (!pte_present(*ptep)) 649 if (pte_val(*ptep) & _PAGE_INVALID)
650 return pgste; 650 return pgste;
651 address = pte_val(*ptep) & PAGE_MASK; 651 address = pte_val(*ptep) & PAGE_MASK;
652 skey = page_get_storage_key(address); 652 skey = page_get_storage_key(address);
@@ -680,7 +680,7 @@ static inline pgste_t pgste_update_young(pte_t *ptep, pgste_t pgste)
680#ifdef CONFIG_PGSTE 680#ifdef CONFIG_PGSTE
681 int young; 681 int young;
682 682
683 if (!pte_present(*ptep)) 683 if (pte_val(*ptep) & _PAGE_INVALID)
684 return pgste; 684 return pgste;
685 /* Get referenced bit from storage key */ 685 /* Get referenced bit from storage key */
686 young = page_reset_referenced(pte_val(*ptep) & PAGE_MASK); 686 young = page_reset_referenced(pte_val(*ptep) & PAGE_MASK);
@@ -706,7 +706,7 @@ static inline void pgste_set_key(pte_t *ptep, pgste_t pgste, pte_t entry)
706 unsigned long address; 706 unsigned long address;
707 unsigned long okey, nkey; 707 unsigned long okey, nkey;
708 708
709 if (!pte_present(entry)) 709 if (pte_val(entry) & _PAGE_INVALID)
710 return; 710 return;
711 address = pte_val(entry) & PAGE_MASK; 711 address = pte_val(entry) & PAGE_MASK;
712 okey = nkey = page_get_storage_key(address); 712 okey = nkey = page_get_storage_key(address);
@@ -1098,6 +1098,9 @@ static inline pte_t ptep_modify_prot_start(struct mm_struct *mm,
1098 pte = *ptep; 1098 pte = *ptep;
1099 if (!mm_exclusive(mm)) 1099 if (!mm_exclusive(mm))
1100 __ptep_ipte(address, ptep); 1100 __ptep_ipte(address, ptep);
1101
1102 if (mm_has_pgste(mm))
1103 pgste = pgste_update_all(&pte, pgste);
1101 return pte; 1104 return pte;
1102} 1105}
1103 1106
@@ -1105,9 +1108,13 @@ static inline void ptep_modify_prot_commit(struct mm_struct *mm,
1105 unsigned long address, 1108 unsigned long address,
1106 pte_t *ptep, pte_t pte) 1109 pte_t *ptep, pte_t pte)
1107{ 1110{
1111 pgste_t pgste;
1112
1108 if (mm_has_pgste(mm)) { 1113 if (mm_has_pgste(mm)) {
1114 pgste = *(pgste_t *)(ptep + PTRS_PER_PTE);
1115 pgste_set_key(ptep, pgste, pte);
1109 pgste_set_pte(ptep, pte); 1116 pgste_set_pte(ptep, pte);
1110 pgste_set_unlock(ptep, *(pgste_t *)(ptep + PTRS_PER_PTE)); 1117 pgste_set_unlock(ptep, pgste);
1111 } else 1118 } else
1112 *ptep = pte; 1119 *ptep = pte;
1113} 1120}
diff --git a/arch/s390/kernel/smp.c b/arch/s390/kernel/smp.c
index 05674b669001..4f977d0d25c2 100644
--- a/arch/s390/kernel/smp.c
+++ b/arch/s390/kernel/smp.c
@@ -428,34 +428,27 @@ void smp_stop_cpu(void)
428 * This is the main routine where commands issued by other 428 * This is the main routine where commands issued by other
429 * cpus are handled. 429 * cpus are handled.
430 */ 430 */
431static void do_ext_call_interrupt(struct ext_code ext_code, 431static void smp_handle_ext_call(void)
432 unsigned int param32, unsigned long param64)
433{ 432{
434 unsigned long bits; 433 unsigned long bits;
435 int cpu;
436
437 cpu = smp_processor_id();
438 if (ext_code.code == 0x1202)
439 inc_irq_stat(IRQEXT_EXC);
440 else
441 inc_irq_stat(IRQEXT_EMS);
442 /*
443 * handle bit signal external calls
444 */
445 bits = xchg(&pcpu_devices[cpu].ec_mask, 0);
446 434
435 /* handle bit signal external calls */
436 bits = xchg(&pcpu_devices[smp_processor_id()].ec_mask, 0);
447 if (test_bit(ec_stop_cpu, &bits)) 437 if (test_bit(ec_stop_cpu, &bits))
448 smp_stop_cpu(); 438 smp_stop_cpu();
449
450 if (test_bit(ec_schedule, &bits)) 439 if (test_bit(ec_schedule, &bits))
451 scheduler_ipi(); 440 scheduler_ipi();
452
453 if (test_bit(ec_call_function, &bits)) 441 if (test_bit(ec_call_function, &bits))
454 generic_smp_call_function_interrupt(); 442 generic_smp_call_function_interrupt();
455
456 if (test_bit(ec_call_function_single, &bits)) 443 if (test_bit(ec_call_function_single, &bits))
457 generic_smp_call_function_single_interrupt(); 444 generic_smp_call_function_single_interrupt();
445}
458 446
447static void do_ext_call_interrupt(struct ext_code ext_code,
448 unsigned int param32, unsigned long param64)
449{
450 inc_irq_stat(ext_code.code == 0x1202 ? IRQEXT_EXC : IRQEXT_EMS);
451 smp_handle_ext_call();
459} 452}
460 453
461void arch_send_call_function_ipi_mask(const struct cpumask *mask) 454void arch_send_call_function_ipi_mask(const struct cpumask *mask)
@@ -760,6 +753,8 @@ int __cpu_disable(void)
760{ 753{
761 unsigned long cregs[16]; 754 unsigned long cregs[16];
762 755
756 /* Handle possible pending IPIs */
757 smp_handle_ext_call();
763 set_cpu_online(smp_processor_id(), false); 758 set_cpu_online(smp_processor_id(), false);
764 /* Disable pseudo page faults on this cpu. */ 759 /* Disable pseudo page faults on this cpu. */
765 pfault_fini(); 760 pfault_fini();
diff --git a/arch/s390/mm/pgtable.c b/arch/s390/mm/pgtable.c
index 18dc417aaf79..a938b548f07e 100644
--- a/arch/s390/mm/pgtable.c
+++ b/arch/s390/mm/pgtable.c
@@ -492,7 +492,7 @@ static int gmap_connect_pgtable(unsigned long address, unsigned long segment,
492 mp = (struct gmap_pgtable *) page->index; 492 mp = (struct gmap_pgtable *) page->index;
493 rmap->gmap = gmap; 493 rmap->gmap = gmap;
494 rmap->entry = segment_ptr; 494 rmap->entry = segment_ptr;
495 rmap->vmaddr = address; 495 rmap->vmaddr = address & PMD_MASK;
496 spin_lock(&mm->page_table_lock); 496 spin_lock(&mm->page_table_lock);
497 if (*segment_ptr == segment) { 497 if (*segment_ptr == segment) {
498 list_add(&rmap->list, &mp->mapper); 498 list_add(&rmap->list, &mp->mapper);