aboutsummaryrefslogtreecommitdiffstats
path: root/arch/parisc
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2013-07-10 13:10:02 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2013-07-10 13:10:02 -0400
commitb247759642cc96a75122907cc898b4c43b4f86ce (patch)
tree568e6ab08f2b986ff0b1ef80318c6c56c5d2ef42 /arch/parisc
parent61e312914cc82c085c945f88e5a53d507dd7d0d4 (diff)
parent5b879d78bc0818aa710f5d4d9abbfc2aca075cc3 (diff)
Merge branch 'parisc-for-3.11' of git://git.kernel.org/pub/scm/linux/kernel/git/deller/parisc-linux
Pull parisc updates from Helge Deller: "The PA-RISC updates for v3.11 include a gcc miscompilation fix, gzip-compressed vmlinuz support, a fix in the PCI code for ATI FireGL support on c8000 machines, a fix to prevent that %sr1 is being clobbered and a few smaller optimizations and documentation updates" * 'parisc-for-3.11' of git://git.kernel.org/pub/scm/linux/kernel/git/deller/parisc-linux: parisc: Fix gcc miscompilation in pa_memcpy() parisc: Ensure volatile space register %sr1 is not clobbered parisc: optimize mtsp(0,sr) inline assembly parisc: switch to gzip-compressed vmlinuz kernel parisc: document the shadow registers parisc: more capabilities info in /proc/cpuinfo parisc: fix LMMIO mismatch between PAT length and MASK register
Diffstat (limited to 'arch/parisc')
-rw-r--r--arch/parisc/Makefile15
-rw-r--r--arch/parisc/defpalo.conf8
-rw-r--r--arch/parisc/include/asm/special_insns.h9
-rw-r--r--arch/parisc/include/asm/tlbflush.h5
-rw-r--r--arch/parisc/install.sh6
-rw-r--r--arch/parisc/kernel/cache.c2
-rw-r--r--arch/parisc/kernel/processor.c19
-rw-r--r--arch/parisc/lib/memcpy.c79
8 files changed, 94 insertions, 49 deletions
diff --git a/arch/parisc/Makefile b/arch/parisc/Makefile
index 96ec3982be8d..e02f665f804a 100644
--- a/arch/parisc/Makefile
+++ b/arch/parisc/Makefile
@@ -17,6 +17,8 @@
17# Mike Shaver, Helge Deller and Martin K. Petersen 17# Mike Shaver, Helge Deller and Martin K. Petersen
18# 18#
19 19
20KBUILD_IMAGE := vmlinuz
21
20KBUILD_DEFCONFIG := default_defconfig 22KBUILD_DEFCONFIG := default_defconfig
21 23
22NM = sh $(srctree)/arch/parisc/nm 24NM = sh $(srctree)/arch/parisc/nm
@@ -92,7 +94,7 @@ PALOCONF := $(shell if [ -f $(src)/palo.conf ]; then echo $(src)/palo.conf; \
92 else echo $(obj)/palo.conf; \ 94 else echo $(obj)/palo.conf; \
93 fi) 95 fi)
94 96
95palo: vmlinux 97palo: vmlinuz
96 @if test ! -x "$(PALO)"; then \ 98 @if test ! -x "$(PALO)"; then \
97 echo 'ERROR: Please install palo first (apt-get install palo)';\ 99 echo 'ERROR: Please install palo first (apt-get install palo)';\
98 echo 'or build it from source and install it somewhere in your $$PATH';\ 100 echo 'or build it from source and install it somewhere in your $$PATH';\
@@ -107,10 +109,14 @@ palo: vmlinux
107 fi 109 fi
108 $(PALO) -f $(PALOCONF) 110 $(PALO) -f $(PALOCONF)
109 111
110# Shorthands for known targets not supported by parisc, use vmlinux as default 112# Shorthands for known targets not supported by parisc, use vmlinux/vmlinuz as default
111Image zImage bzImage: vmlinux 113Image: vmlinux
114zImage bzImage: vmlinuz
115
116vmlinuz: vmlinux
117 @gzip -cf -9 $< > $@
112 118
113install: vmlinux 119install: vmlinuz
114 sh $(src)/arch/parisc/install.sh \ 120 sh $(src)/arch/parisc/install.sh \
115 $(KERNELRELEASE) $< System.map "$(INSTALL_PATH)" 121 $(KERNELRELEASE) $< System.map "$(INSTALL_PATH)"
116 122
@@ -119,6 +125,7 @@ MRPROPER_FILES += palo.conf
119 125
120define archhelp 126define archhelp
121 @echo '* vmlinux - Uncompressed kernel image (./vmlinux)' 127 @echo '* vmlinux - Uncompressed kernel image (./vmlinux)'
128 @echo ' vmlinuz - Compressed kernel image (./vmlinuz)'
122 @echo ' palo - Bootable image (./lifimage)' 129 @echo ' palo - Bootable image (./lifimage)'
123 @echo ' install - Install kernel using' 130 @echo ' install - Install kernel using'
124 @echo ' (your) ~/bin/$(INSTALLKERNEL) or' 131 @echo ' (your) ~/bin/$(INSTALLKERNEL) or'
diff --git a/arch/parisc/defpalo.conf b/arch/parisc/defpalo.conf
index 4e1ae25b08d1..208ff3b41487 100644
--- a/arch/parisc/defpalo.conf
+++ b/arch/parisc/defpalo.conf
@@ -4,7 +4,7 @@
4# Most people using 'make palo' want a bootable file, usable for 4# Most people using 'make palo' want a bootable file, usable for
5# network or tape booting for example. 5# network or tape booting for example.
6--init-tape=lifimage 6--init-tape=lifimage
7--recoverykernel=vmlinux 7--recoverykernel=vmlinuz
8 8
9########## Pick your ROOT here! ########## 9########## Pick your ROOT here! ##########
10# You need at least one 'root='! 10# You need at least one 'root='!
@@ -12,10 +12,10 @@
12# If you want a root ramdisk, use the next 2 lines 12# If you want a root ramdisk, use the next 2 lines
13# (Edit the ramdisk image name!!!!) 13# (Edit the ramdisk image name!!!!)
14--ramdisk=ram-disk-image-file 14--ramdisk=ram-disk-image-file
15--commandline=0/vmlinux HOME=/ root=/dev/ram initrd=0/ramdisk 15--commandline=0/vmlinuz HOME=/ root=/dev/ram initrd=0/ramdisk panic_timeout=60 panic=-1
16 16
17# If you want NFS root, use the following command line (Edit the HOSTNAME!!!) 17# If you want NFS root, use the following command line (Edit the HOSTNAME!!!)
18#--commandline=0/vmlinux HOME=/ root=/dev/nfs nfsroot=HOSTNAME ip=bootp 18#--commandline=0/vmlinuz HOME=/ root=/dev/nfs nfsroot=HOSTNAME ip=bootp
19 19
20# If you have root on a disk partition, use this (Edit the partition name!!!) 20# If you have root on a disk partition, use this (Edit the partition name!!!)
21#--commandline=0/vmlinux HOME=/ root=/dev/sda1 21#--commandline=0/vmlinuz HOME=/ root=/dev/sda1
diff --git a/arch/parisc/include/asm/special_insns.h b/arch/parisc/include/asm/special_insns.h
index d306b75bc77f..e1509308899f 100644
--- a/arch/parisc/include/asm/special_insns.h
+++ b/arch/parisc/include/asm/special_insns.h
@@ -32,9 +32,12 @@ static inline void set_eiem(unsigned long val)
32 cr; \ 32 cr; \
33}) 33})
34 34
35#define mtsp(gr, cr) \ 35#define mtsp(val, cr) \
36 __asm__ __volatile__("mtsp %0,%1" \ 36 { if (__builtin_constant_p(val) && ((val) == 0)) \
37 __asm__ __volatile__("mtsp %%r0,%0" : : "i" (cr) : "memory"); \
38 else \
39 __asm__ __volatile__("mtsp %0,%1" \
37 : /* no outputs */ \ 40 : /* no outputs */ \
38 : "r" (gr), "i" (cr) : "memory") 41 : "r" (val), "i" (cr) : "memory"); }
39 42
40#endif /* __PARISC_SPECIAL_INSNS_H */ 43#endif /* __PARISC_SPECIAL_INSNS_H */
diff --git a/arch/parisc/include/asm/tlbflush.h b/arch/parisc/include/asm/tlbflush.h
index 5273da991e06..9d086a599fa0 100644
--- a/arch/parisc/include/asm/tlbflush.h
+++ b/arch/parisc/include/asm/tlbflush.h
@@ -63,13 +63,14 @@ static inline void flush_tlb_mm(struct mm_struct *mm)
63static inline void flush_tlb_page(struct vm_area_struct *vma, 63static inline void flush_tlb_page(struct vm_area_struct *vma,
64 unsigned long addr) 64 unsigned long addr)
65{ 65{
66 unsigned long flags; 66 unsigned long flags, sid;
67 67
68 /* For one page, it's not worth testing the split_tlb variable */ 68 /* For one page, it's not worth testing the split_tlb variable */
69 69
70 mb(); 70 mb();
71 mtsp(vma->vm_mm->context,1); 71 sid = vma->vm_mm->context;
72 purge_tlb_start(flags); 72 purge_tlb_start(flags);
73 mtsp(sid, 1);
73 pdtlb(addr); 74 pdtlb(addr);
74 pitlb(addr); 75 pitlb(addr);
75 purge_tlb_end(flags); 76 purge_tlb_end(flags);
diff --git a/arch/parisc/install.sh b/arch/parisc/install.sh
index e593fc8d58bc..4da682b466d0 100644
--- a/arch/parisc/install.sh
+++ b/arch/parisc/install.sh
@@ -26,13 +26,13 @@ if [ -x /sbin/${INSTALLKERNEL} ]; then exec /sbin/${INSTALLKERNEL} "$@"; fi
26 26
27# Default install 27# Default install
28 28
29if [ -f $4/vmlinux ]; then 29if [ -f $4/vmlinuz ]; then
30 mv $4/vmlinux $4/vmlinux.old 30 mv $4/vmlinuz $4/vmlinuz.old
31fi 31fi
32 32
33if [ -f $4/System.map ]; then 33if [ -f $4/System.map ]; then
34 mv $4/System.map $4/System.old 34 mv $4/System.map $4/System.old
35fi 35fi
36 36
37cat $2 > $4/vmlinux 37cat $2 > $4/vmlinuz
38cp $3 $4/System.map 38cp $3 $4/System.map
diff --git a/arch/parisc/kernel/cache.c b/arch/parisc/kernel/cache.c
index 65fb4cbc3a0f..2e65aa54bd10 100644
--- a/arch/parisc/kernel/cache.c
+++ b/arch/parisc/kernel/cache.c
@@ -440,8 +440,8 @@ void __flush_tlb_range(unsigned long sid, unsigned long start,
440 else { 440 else {
441 unsigned long flags; 441 unsigned long flags;
442 442
443 mtsp(sid, 1);
444 purge_tlb_start(flags); 443 purge_tlb_start(flags);
444 mtsp(sid, 1);
445 if (split_tlb) { 445 if (split_tlb) {
446 while (npages--) { 446 while (npages--) {
447 pdtlb(start); 447 pdtlb(start);
diff --git a/arch/parisc/kernel/processor.c b/arch/parisc/kernel/processor.c
index c8fb61ed32f4..8a96c8ab9fe6 100644
--- a/arch/parisc/kernel/processor.c
+++ b/arch/parisc/kernel/processor.c
@@ -371,10 +371,23 @@ show_cpuinfo (struct seq_file *m, void *v)
371 371
372 seq_printf(m, "capabilities\t:"); 372 seq_printf(m, "capabilities\t:");
373 if (boot_cpu_data.pdc.capabilities & PDC_MODEL_OS32) 373 if (boot_cpu_data.pdc.capabilities & PDC_MODEL_OS32)
374 seq_printf(m, " os32"); 374 seq_puts(m, " os32");
375 if (boot_cpu_data.pdc.capabilities & PDC_MODEL_OS64) 375 if (boot_cpu_data.pdc.capabilities & PDC_MODEL_OS64)
376 seq_printf(m, " os64"); 376 seq_puts(m, " os64");
377 seq_printf(m, "\n"); 377 if (boot_cpu_data.pdc.capabilities & PDC_MODEL_IOPDIR_FDC)
378 seq_puts(m, " iopdir_fdc");
379 switch (boot_cpu_data.pdc.capabilities & PDC_MODEL_NVA_MASK) {
380 case PDC_MODEL_NVA_SUPPORTED:
381 seq_puts(m, " nva_supported");
382 break;
383 case PDC_MODEL_NVA_SLOW:
384 seq_puts(m, " nva_slow");
385 break;
386 case PDC_MODEL_NVA_UNSUPPORTED:
387 seq_puts(m, " needs_equivalent_aliasing");
388 break;
389 }
390 seq_printf(m, " (0x%02lx)\n", boot_cpu_data.pdc.capabilities);
378 391
379 seq_printf(m, "model\t\t: %s\n" 392 seq_printf(m, "model\t\t: %s\n"
380 "model name\t: %s\n", 393 "model name\t: %s\n",
diff --git a/arch/parisc/lib/memcpy.c b/arch/parisc/lib/memcpy.c
index a49cc812df8a..ac4370b1ca40 100644
--- a/arch/parisc/lib/memcpy.c
+++ b/arch/parisc/lib/memcpy.c
@@ -2,6 +2,7 @@
2 * Optimized memory copy routines. 2 * Optimized memory copy routines.
3 * 3 *
4 * Copyright (C) 2004 Randolph Chung <tausq@debian.org> 4 * Copyright (C) 2004 Randolph Chung <tausq@debian.org>
5 * Copyright (C) 2013 Helge Deller <deller@gmx.de>
5 * 6 *
6 * This program is free software; you can redistribute it and/or modify 7 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by 8 * it under the terms of the GNU General Public License as published by
@@ -153,17 +154,21 @@ static inline void prefetch_dst(const void *addr)
153#define prefetch_dst(addr) do { } while(0) 154#define prefetch_dst(addr) do { } while(0)
154#endif 155#endif
155 156
157#define PA_MEMCPY_OK 0
158#define PA_MEMCPY_LOAD_ERROR 1
159#define PA_MEMCPY_STORE_ERROR 2
160
156/* Copy from a not-aligned src to an aligned dst, using shifts. Handles 4 words 161/* Copy from a not-aligned src to an aligned dst, using shifts. Handles 4 words
157 * per loop. This code is derived from glibc. 162 * per loop. This code is derived from glibc.
158 */ 163 */
159static inline unsigned long copy_dstaligned(unsigned long dst, unsigned long src, unsigned long len, unsigned long o_dst, unsigned long o_src, unsigned long o_len) 164static inline unsigned long copy_dstaligned(unsigned long dst,
165 unsigned long src, unsigned long len)
160{ 166{
161 /* gcc complains that a2 and a3 may be uninitialized, but actually 167 /* gcc complains that a2 and a3 may be uninitialized, but actually
162 * they cannot be. Initialize a2/a3 to shut gcc up. 168 * they cannot be. Initialize a2/a3 to shut gcc up.
163 */ 169 */
164 register unsigned int a0, a1, a2 = 0, a3 = 0; 170 register unsigned int a0, a1, a2 = 0, a3 = 0;
165 int sh_1, sh_2; 171 int sh_1, sh_2;
166 struct exception_data *d;
167 172
168 /* prefetch_src((const void *)src); */ 173 /* prefetch_src((const void *)src); */
169 174
@@ -197,7 +202,7 @@ static inline unsigned long copy_dstaligned(unsigned long dst, unsigned long src
197 goto do2; 202 goto do2;
198 case 0: 203 case 0:
199 if (len == 0) 204 if (len == 0)
200 return 0; 205 return PA_MEMCPY_OK;
201 /* a3 = ((unsigned int *) src)[0]; 206 /* a3 = ((unsigned int *) src)[0];
202 a0 = ((unsigned int *) src)[1]; */ 207 a0 = ((unsigned int *) src)[1]; */
203 ldw(s_space, 0, src, a3, cda_ldw_exc); 208 ldw(s_space, 0, src, a3, cda_ldw_exc);
@@ -256,42 +261,35 @@ do0:
256 preserve_branch(handle_load_error); 261 preserve_branch(handle_load_error);
257 preserve_branch(handle_store_error); 262 preserve_branch(handle_store_error);
258 263
259 return 0; 264 return PA_MEMCPY_OK;
260 265
261handle_load_error: 266handle_load_error:
262 __asm__ __volatile__ ("cda_ldw_exc:\n"); 267 __asm__ __volatile__ ("cda_ldw_exc:\n");
263 d = &__get_cpu_var(exception_data); 268 return PA_MEMCPY_LOAD_ERROR;
264 DPRINTF("cda_ldw_exc: o_len=%lu fault_addr=%lu o_src=%lu ret=%lu\n",
265 o_len, d->fault_addr, o_src, o_len - d->fault_addr + o_src);
266 return o_len * 4 - d->fault_addr + o_src;
267 269
268handle_store_error: 270handle_store_error:
269 __asm__ __volatile__ ("cda_stw_exc:\n"); 271 __asm__ __volatile__ ("cda_stw_exc:\n");
270 d = &__get_cpu_var(exception_data); 272 return PA_MEMCPY_STORE_ERROR;
271 DPRINTF("cda_stw_exc: o_len=%lu fault_addr=%lu o_dst=%lu ret=%lu\n",
272 o_len, d->fault_addr, o_dst, o_len - d->fault_addr + o_dst);
273 return o_len * 4 - d->fault_addr + o_dst;
274} 273}
275 274
276 275
277/* Returns 0 for success, otherwise, returns number of bytes not transferred. */ 276/* Returns PA_MEMCPY_OK, PA_MEMCPY_LOAD_ERROR or PA_MEMCPY_STORE_ERROR.
278static unsigned long pa_memcpy(void *dstp, const void *srcp, unsigned long len) 277 * In case of an access fault the faulty address can be read from the per_cpu
278 * exception data struct. */
279static unsigned long pa_memcpy_internal(void *dstp, const void *srcp,
280 unsigned long len)
279{ 281{
280 register unsigned long src, dst, t1, t2, t3; 282 register unsigned long src, dst, t1, t2, t3;
281 register unsigned char *pcs, *pcd; 283 register unsigned char *pcs, *pcd;
282 register unsigned int *pws, *pwd; 284 register unsigned int *pws, *pwd;
283 register double *pds, *pdd; 285 register double *pds, *pdd;
284 unsigned long ret = 0; 286 unsigned long ret;
285 unsigned long o_dst, o_src, o_len;
286 struct exception_data *d;
287 287
288 src = (unsigned long)srcp; 288 src = (unsigned long)srcp;
289 dst = (unsigned long)dstp; 289 dst = (unsigned long)dstp;
290 pcs = (unsigned char *)srcp; 290 pcs = (unsigned char *)srcp;
291 pcd = (unsigned char *)dstp; 291 pcd = (unsigned char *)dstp;
292 292
293 o_dst = dst; o_src = src; o_len = len;
294
295 /* prefetch_src((const void *)srcp); */ 293 /* prefetch_src((const void *)srcp); */
296 294
297 if (len < THRESHOLD) 295 if (len < THRESHOLD)
@@ -401,7 +399,7 @@ byte_copy:
401 len--; 399 len--;
402 } 400 }
403 401
404 return 0; 402 return PA_MEMCPY_OK;
405 403
406unaligned_copy: 404unaligned_copy:
407 /* possibly we are aligned on a word, but not on a double... */ 405 /* possibly we are aligned on a word, but not on a double... */
@@ -438,8 +436,7 @@ unaligned_copy:
438 src = (unsigned long)pcs; 436 src = (unsigned long)pcs;
439 } 437 }
440 438
441 ret = copy_dstaligned(dst, src, len / sizeof(unsigned int), 439 ret = copy_dstaligned(dst, src, len / sizeof(unsigned int));
442 o_dst, o_src, o_len);
443 if (ret) 440 if (ret)
444 return ret; 441 return ret;
445 442
@@ -454,17 +451,41 @@ unaligned_copy:
454 451
455handle_load_error: 452handle_load_error:
456 __asm__ __volatile__ ("pmc_load_exc:\n"); 453 __asm__ __volatile__ ("pmc_load_exc:\n");
457 d = &__get_cpu_var(exception_data); 454 return PA_MEMCPY_LOAD_ERROR;
458 DPRINTF("pmc_load_exc: o_len=%lu fault_addr=%lu o_src=%lu ret=%lu\n",
459 o_len, d->fault_addr, o_src, o_len - d->fault_addr + o_src);
460 return o_len - d->fault_addr + o_src;
461 455
462handle_store_error: 456handle_store_error:
463 __asm__ __volatile__ ("pmc_store_exc:\n"); 457 __asm__ __volatile__ ("pmc_store_exc:\n");
458 return PA_MEMCPY_STORE_ERROR;
459}
460
461
462/* Returns 0 for success, otherwise, returns number of bytes not transferred. */
463static unsigned long pa_memcpy(void *dstp, const void *srcp, unsigned long len)
464{
465 unsigned long ret, fault_addr, reference;
466 struct exception_data *d;
467
468 ret = pa_memcpy_internal(dstp, srcp, len);
469 if (likely(ret == PA_MEMCPY_OK))
470 return 0;
471
472 /* if a load or store fault occured we can get the faulty addr */
464 d = &__get_cpu_var(exception_data); 473 d = &__get_cpu_var(exception_data);
465 DPRINTF("pmc_store_exc: o_len=%lu fault_addr=%lu o_dst=%lu ret=%lu\n", 474 fault_addr = d->fault_addr;
466 o_len, d->fault_addr, o_dst, o_len - d->fault_addr + o_dst); 475
467 return o_len - d->fault_addr + o_dst; 476 /* error in load or store? */
477 if (ret == PA_MEMCPY_LOAD_ERROR)
478 reference = (unsigned long) srcp;
479 else
480 reference = (unsigned long) dstp;
481
482 DPRINTF("pa_memcpy: fault type = %lu, len=%lu fault_addr=%lu ref=%lu\n",
483 ret, len, fault_addr, reference);
484
485 if (fault_addr >= reference)
486 return len - (fault_addr - reference);
487 else
488 return len;
468} 489}
469 490
470#ifdef __KERNEL__ 491#ifdef __KERNEL__