diff options
Diffstat (limited to 'arch/alpha')
114 files changed, 828 insertions, 767 deletions
diff --git a/arch/alpha/Kconfig b/arch/alpha/Kconfig index 7d0d26b5b3f5..3afd042150f8 100644 --- a/arch/alpha/Kconfig +++ b/arch/alpha/Kconfig @@ -3,6 +3,7 @@ config ALPHA bool default y select ARCH_32BIT_USTAT_F_TINODE + select ARCH_HAS_CURRENT_STACK_POINTER select ARCH_MIGHT_HAVE_PC_PARPORT select ARCH_MIGHT_HAVE_PC_SERIO select ARCH_NO_PREEMPT @@ -13,11 +14,11 @@ config ALPHA select PCI_DOMAINS if PCI select PCI_SYSCALL if PCI select HAVE_ASM_MODVERSIONS + select HAVE_PAGE_SIZE_8KB select HAVE_PCSPKR_PLATFORM select HAVE_PERF_EVENTS select NEED_DMA_MAP_STATE select NEED_SG_DMA_LENGTH - select VIRT_TO_BUS select GENERIC_IRQ_PROBE select GENERIC_PCI_IOMAP select AUTO_IRQ_AFFINITY if SMP @@ -27,8 +28,10 @@ config ALPHA select AUDIT_ARCH select GENERIC_CPU_VULNERABILITIES select GENERIC_SMP_IDLE_THREAD + select HAS_IOPORT select HAVE_ARCH_AUDITSYSCALL select HAVE_MOD_ARCH_SPECIFIC + select LOCK_MM_AND_FIND_VMA select MODULES_USE_ELF_RELA select ODD_RT_SIGACTION select OLD_SIGSUSPEND @@ -336,6 +339,7 @@ config ALPHA_EV4 bool depends on ALPHA_JENSEN || (ALPHA_SABLE && !ALPHA_GAMMA) || ALPHA_LYNX || ALPHA_NORITAKE && !ALPHA_PRIMO || ALPHA_MIKASA && !ALPHA_PRIMO || ALPHA_CABRIOLET || ALPHA_AVANTI_CH || ALPHA_EB64P_CH || ALPHA_XL || ALPHA_NONAME || ALPHA_EB66 || ALPHA_EB66P || ALPHA_P2K default y if !ALPHA_LYNX + default y if !ALPHA_EV5 config ALPHA_LCA bool @@ -363,10 +367,6 @@ config ALPHA_EV5 bool "EV5 CPU(s) (model 5/xxx)?" if ALPHA_LYNX default y if ALPHA_RX164 || ALPHA_RAWHIDE || ALPHA_MIATA || ALPHA_LX164 || ALPHA_SX164 || ALPHA_RUFFIAN || ALPHA_SABLE && ALPHA_GAMMA || ALPHA_NORITAKE && ALPHA_PRIMO || ALPHA_MIKASA && ALPHA_PRIMO || ALPHA_PC164 || ALPHA_TAKARA || ALPHA_EB164 || ALPHA_ALCOR -config ALPHA_EV4 - bool - default y if ALPHA_LYNX && !ALPHA_EV5 - config ALPHA_CIA bool depends on ALPHA_MIATA || ALPHA_LX164 || ALPHA_SX164 || ALPHA_RUFFIAN || ALPHA_NORITAKE && ALPHA_PRIMO || ALPHA_MIKASA && ALPHA_PRIMO || ALPHA_PC164 || ALPHA_TAKARA || ALPHA_EB164 || ALPHA_ALCOR @@ -391,16 +391,12 @@ config ALPHA_PRIMO Say Y if you have an AS 1000 5/xxx or an AS 1000A 5/xxx. config ALPHA_GAMMA - bool "EV5 CPU(s) (model 5/xxx)?" - depends on ALPHA_SABLE + bool "EV5 CPU(s) (model 5/xxx)?" if ALPHA_SABLE + depends on ALPHA_SABLE || ALPHA_LYNX + default ALPHA_LYNX help Say Y if you have an AS 2000 5/xxx or an AS 2100 5/xxx. -config ALPHA_GAMMA - bool - depends on ALPHA_LYNX - default y - config ALPHA_T2 bool depends on ALPHA_SABLE || ALPHA_LYNX diff --git a/arch/alpha/Makefile b/arch/alpha/Makefile index 881cb913e23a..45158024085e 100644 --- a/arch/alpha/Makefile +++ b/arch/alpha/Makefile @@ -36,8 +36,6 @@ cflags-y += $(cpuflags-y) # BWX is most important, but we don't really want any emulation ever. KBUILD_CFLAGS += $(cflags-y) -Wa,-mev6 -head-y := arch/alpha/kernel/head.o - libs-y += arch/alpha/lib/ # export what is needed by arch/alpha/boot/Makefile diff --git a/arch/alpha/boot/bootp.c b/arch/alpha/boot/bootp.c index b4faba2432d5..842e85776cc0 100644 --- a/arch/alpha/boot/bootp.c +++ b/arch/alpha/boot/bootp.c @@ -18,7 +18,7 @@ #include <asm/hwrpb.h> #include <asm/io.h> -#include <stdarg.h> +#include <linux/stdarg.h> #include "ksize.h" diff --git a/arch/alpha/boot/bootpz.c b/arch/alpha/boot/bootpz.c index 90a2b341e9c0..c6079308eab3 100644 --- a/arch/alpha/boot/bootpz.c +++ b/arch/alpha/boot/bootpz.c @@ -20,7 +20,7 @@ #include <asm/hwrpb.h> #include <asm/io.h> -#include <stdarg.h> +#include <linux/stdarg.h> #include "kzsize.h" diff --git a/arch/alpha/boot/main.c b/arch/alpha/boot/main.c index e5347a080008..22a1cb0264af 100644 --- a/arch/alpha/boot/main.c +++ b/arch/alpha/boot/main.c @@ -15,7 +15,7 @@ #include <asm/console.h> #include <asm/hwrpb.h> -#include <stdarg.h> +#include <linux/stdarg.h> #include "ksize.h" diff --git a/arch/alpha/boot/misc.c b/arch/alpha/boot/misc.c index 325d4dd4f904..1ab91852d9f7 100644 --- a/arch/alpha/boot/misc.c +++ b/arch/alpha/boot/misc.c @@ -89,8 +89,6 @@ static ulg output_ptr; static ulg bytes_out; static void error(char *m); -static void gzip_mark(void **); -static void gzip_release(void **); extern int end; static ulg free_mem_ptr; diff --git a/arch/alpha/boot/stdio.c b/arch/alpha/boot/stdio.c index 60f73ccd2e89..faa5234b90b8 100644 --- a/arch/alpha/boot/stdio.c +++ b/arch/alpha/boot/stdio.c @@ -2,8 +2,8 @@ /* * Copyright (C) Paul Mackerras 1997. */ -#include <stdarg.h> -#include <stddef.h> +#include <linux/string.h> +#include <linux/stdarg.h> size_t strnlen(const char * s, size_t count) { @@ -42,8 +42,8 @@ static int skip_atoi(const char **s) static char * number(char * str, unsigned long long num, int base, int size, int precision, int type) { - char c,sign,tmp[66]; - const char *digits="0123456789abcdefghijklmnopqrstuvwxyz"; + char c, sign, tmp[66]; + const char *digits = "0123456789abcdefghijklmnopqrstuvwxyz"; int i; if (type & LARGE) @@ -83,14 +83,14 @@ static char * number(char * str, unsigned long long num, int base, int size, int precision = i; size -= precision; if (!(type&(ZEROPAD+LEFT))) - while(size-->0) + while (size-- > 0) *str++ = ' '; if (sign) *str++ = sign; if (type & SPECIAL) { if (base==8) *str++ = '0'; - else if (base==16) { + else if (base == 16) { *str++ = '0'; *str++ = digits[33]; } @@ -125,7 +125,7 @@ int vsprintf(char *buf, const char *fmt, va_list args) /* 'z' changed to 'Z' --davidm 1/25/99 */ - for (str=buf ; *fmt ; ++fmt) { + for (str = buf ; *fmt ; ++fmt) { if (*fmt != '%') { *str++ = *fmt; continue; @@ -296,7 +296,7 @@ int sprintf(char * buf, const char *fmt, ...) int i; va_start(args, fmt); - i=vsprintf(buf,fmt,args); + i = vsprintf(buf, fmt, args); va_end(args); return i; } diff --git a/arch/alpha/boot/tools/objstrip.c b/arch/alpha/boot/tools/objstrip.c index 08b430d25a31..7cf92d172dce 100644 --- a/arch/alpha/boot/tools/objstrip.c +++ b/arch/alpha/boot/tools/objstrip.c @@ -148,7 +148,7 @@ main (int argc, char *argv[]) #ifdef __ELF__ elf = (struct elfhdr *) buf; - if (elf->e_ident[0] == 0x7f && str_has_prefix((char *)elf->e_ident + 1, "ELF")) { + if (memcmp(&elf->e_ident[EI_MAG0], ELFMAG, SELFMAG) == 0) { if (elf->e_type != ET_EXEC) { fprintf(stderr, "%s: %s is not an ELF executable\n", prog_name, inname); diff --git a/arch/alpha/configs/defconfig b/arch/alpha/configs/defconfig index 7e9336930880..1816c1dc22b1 100644 --- a/arch/alpha/configs/defconfig +++ b/arch/alpha/configs/defconfig @@ -39,14 +39,12 @@ CONFIG_PATA_CYPRESS=y CONFIG_ATA_GENERIC=y CONFIG_NETDEVICES=y CONFIG_DUMMY=m -CONFIG_NET_ETHERNET=y CONFIG_NET_VENDOR_3COM=y CONFIG_VORTEX=y CONFIG_NET_TULIP=y CONFIG_DE2104X=m CONFIG_TULIP=y CONFIG_TULIP_MMIO=y -CONFIG_NET_PCI=y CONFIG_YELLOWFIN=y CONFIG_SERIAL_8250=y CONFIG_SERIAL_8250_CONSOLE=y @@ -65,7 +63,7 @@ CONFIG_NFSD=m CONFIG_NLS_CODEPAGE_437=y CONFIG_MAGIC_SYSRQ=y CONFIG_DEBUG_KERNEL=y -CONFIG_DEBUG_INFO=y +CONFIG_DEBUG_INFO_DWARF_TOOLCHAIN_DEFAULT=y CONFIG_ALPHA_LEGACY_START_ADDRESS=y CONFIG_MATHEMU=y CONFIG_CRYPTO_HMAC=y diff --git a/arch/alpha/include/asm/Kbuild b/arch/alpha/include/asm/Kbuild index 42911c8340c7..396caece6d6d 100644 --- a/arch/alpha/include/asm/Kbuild +++ b/arch/alpha/include/asm/Kbuild @@ -1,6 +1,7 @@ # SPDX-License-Identifier: GPL-2.0 generated-y += syscall_table.h -generic-y += export.h +generic-y += agp.h +generic-y += asm-offsets.h generic-y += kvm_para.h generic-y += mcs_spinlock.h diff --git a/arch/alpha/include/asm/a.out.h b/arch/alpha/include/asm/a.out.h deleted file mode 100644 index d2346b7caff1..000000000000 --- a/arch/alpha/include/asm/a.out.h +++ /dev/null @@ -1,16 +0,0 @@ -/* SPDX-License-Identifier: GPL-2.0 */ -#ifndef __ALPHA_A_OUT_H__ -#define __ALPHA_A_OUT_H__ - -#include <uapi/asm/a.out.h> - - -/* Assume that start addresses below 4G belong to a TASO application. - Unfortunately, there is no proper bit in the exec header to check. - Worse, we have to notice the start address before swapping to use - /sbin/loader, which of course is _not_ a TASO application. */ -#define SET_AOUT_PERSONALITY(BFPM, EX) \ - set_personality (((BFPM->taso || EX.ah.entry < 0x100000000L \ - ? ADDR_LIMIT_32BIT : 0) | PER_OSF4)) - -#endif /* __A_OUT_GNU_H__ */ diff --git a/arch/alpha/include/asm/agp.h b/arch/alpha/include/asm/agp.h deleted file mode 100644 index 7874f063d000..000000000000 --- a/arch/alpha/include/asm/agp.h +++ /dev/null @@ -1,19 +0,0 @@ -/* SPDX-License-Identifier: GPL-2.0 */ -#ifndef AGP_H -#define AGP_H 1 - -#include <asm/io.h> - -/* dummy for now */ - -#define map_page_into_agp(page) do { } while (0) -#define unmap_page_from_agp(page) do { } while (0) -#define flush_agp_cache() mb() - -/* GATT allocation. Returns/accepts GATT kernel virtual address. */ -#define alloc_gatt_pages(order) \ - ((char *)__get_free_pages(GFP_KERNEL, (order))) -#define free_gatt_pages(table, order) \ - free_pages((unsigned long)(table), (order)) - -#endif diff --git a/arch/alpha/include/asm/asm-offsets.h b/arch/alpha/include/asm/asm-offsets.h deleted file mode 100644 index d370ee36a182..000000000000 --- a/arch/alpha/include/asm/asm-offsets.h +++ /dev/null @@ -1 +0,0 @@ -#include <generated/asm-offsets.h> diff --git a/arch/alpha/include/asm/atomic.h b/arch/alpha/include/asm/atomic.h index f2861a43a61e..cbd9244571af 100644 --- a/arch/alpha/include/asm/atomic.h +++ b/arch/alpha/include/asm/atomic.h @@ -200,25 +200,6 @@ ATOMIC_OPS(xor, xor) #undef ATOMIC_OP_RETURN #undef ATOMIC_OP -#define arch_atomic64_cmpxchg(v, old, new) \ - (arch_cmpxchg(&((v)->counter), old, new)) -#define arch_atomic64_xchg(v, new) \ - (arch_xchg(&((v)->counter), new)) - -#define arch_atomic_cmpxchg(v, old, new) \ - (arch_cmpxchg(&((v)->counter), old, new)) -#define arch_atomic_xchg(v, new) \ - (arch_xchg(&((v)->counter), new)) - -/** - * arch_atomic_fetch_add_unless - add unless the number is a given value - * @v: pointer of type atomic_t - * @a: the amount to add to v... - * @u: ...unless v is equal to u. - * - * Atomically adds @a to @v, so long as it was not @u. - * Returns the old value of @v. - */ static __inline__ int arch_atomic_fetch_add_unless(atomic_t *v, int a, int u) { int c, new, old; @@ -242,15 +223,6 @@ static __inline__ int arch_atomic_fetch_add_unless(atomic_t *v, int a, int u) } #define arch_atomic_fetch_add_unless arch_atomic_fetch_add_unless -/** - * arch_atomic64_fetch_add_unless - add unless the number is a given value - * @v: pointer of type atomic64_t - * @a: the amount to add to v... - * @u: ...unless v is equal to u. - * - * Atomically adds @a to @v, so long as it was not @u. - * Returns the old value of @v. - */ static __inline__ s64 arch_atomic64_fetch_add_unless(atomic64_t *v, s64 a, s64 u) { s64 c, new, old; @@ -274,13 +246,6 @@ static __inline__ s64 arch_atomic64_fetch_add_unless(atomic64_t *v, s64 a, s64 u } #define arch_atomic64_fetch_add_unless arch_atomic64_fetch_add_unless -/* - * arch_atomic64_dec_if_positive - decrement by 1 if old value positive - * @v: pointer of type atomic_t - * - * The function returns the old value of *v minus 1, even if - * the atomic variable, v, was not decremented. - */ static inline s64 arch_atomic64_dec_if_positive(atomic64_t *v) { s64 old, tmp; diff --git a/arch/alpha/include/asm/bitops.h b/arch/alpha/include/asm/bitops.h index e1d8483a45f2..3e33621922c3 100644 --- a/arch/alpha/include/asm/bitops.h +++ b/arch/alpha/include/asm/bitops.h @@ -46,8 +46,8 @@ set_bit(unsigned long nr, volatile void * addr) /* * WARNING: non atomic version. */ -static inline void -__set_bit(unsigned long nr, volatile void * addr) +static __always_inline void +arch___set_bit(unsigned long nr, volatile unsigned long *addr) { int *m = ((int *) addr) + (nr >> 5); @@ -82,8 +82,8 @@ clear_bit_unlock(unsigned long nr, volatile void * addr) /* * WARNING: non atomic version. */ -static __inline__ void -__clear_bit(unsigned long nr, volatile void * addr) +static __always_inline void +arch___clear_bit(unsigned long nr, volatile unsigned long *addr) { int *m = ((int *) addr) + (nr >> 5); @@ -94,7 +94,7 @@ static inline void __clear_bit_unlock(unsigned long nr, volatile void * addr) { smp_mb(); - __clear_bit(nr, addr); + arch___clear_bit(nr, addr); } static inline void @@ -118,8 +118,8 @@ change_bit(unsigned long nr, volatile void * addr) /* * WARNING: non atomic version. */ -static __inline__ void -__change_bit(unsigned long nr, volatile void * addr) +static __always_inline void +arch___change_bit(unsigned long nr, volatile unsigned long *addr) { int *m = ((int *) addr) + (nr >> 5); @@ -186,8 +186,8 @@ test_and_set_bit_lock(unsigned long nr, volatile void *addr) /* * WARNING: non atomic version. */ -static inline int -__test_and_set_bit(unsigned long nr, volatile void * addr) +static __always_inline bool +arch___test_and_set_bit(unsigned long nr, volatile unsigned long *addr) { unsigned long mask = 1 << (nr & 0x1f); int *m = ((int *) addr) + (nr >> 5); @@ -230,8 +230,8 @@ test_and_clear_bit(unsigned long nr, volatile void * addr) /* * WARNING: non atomic version. */ -static inline int -__test_and_clear_bit(unsigned long nr, volatile void * addr) +static __always_inline bool +arch___test_and_clear_bit(unsigned long nr, volatile unsigned long *addr) { unsigned long mask = 1 << (nr & 0x1f); int *m = ((int *) addr) + (nr >> 5); @@ -272,8 +272,8 @@ test_and_change_bit(unsigned long nr, volatile void * addr) /* * WARNING: non atomic version. */ -static __inline__ int -__test_and_change_bit(unsigned long nr, volatile void * addr) +static __always_inline bool +arch___test_and_change_bit(unsigned long nr, volatile unsigned long *addr) { unsigned long mask = 1 << (nr & 0x1f); int *m = ((int *) addr) + (nr >> 5); @@ -283,10 +283,27 @@ __test_and_change_bit(unsigned long nr, volatile void * addr) return (old & mask) != 0; } -static inline int -test_bit(int nr, const volatile void * addr) +#define arch_test_bit generic_test_bit +#define arch_test_bit_acquire generic_test_bit_acquire + +static inline bool xor_unlock_is_negative_byte(unsigned long mask, + volatile unsigned long *p) { - return (1UL & (((const int *) addr)[nr >> 5] >> (nr & 31))) != 0UL; + unsigned long temp, old; + + __asm__ __volatile__( + "1: ldl_l %0,%4\n" + " mov %0,%2\n" + " xor %0,%3,%0\n" + " stl_c %0,%1\n" + " beq %0,2f\n" + ".subsection 2\n" + "2: br 1b\n" + ".previous" + :"=&r" (temp), "=m" (*p), "=&r" (old) + :"Ir" (mask), "m" (*p)); + + return (old & BIT(7)) != 0; } /* @@ -450,6 +467,8 @@ sched_find_first_bit(const unsigned long b[2]) return __ffs(tmp) + ofs; } +#include <asm-generic/bitops/non-instrumented-non-atomic.h> + #include <asm-generic/bitops/le.h> #include <asm-generic/bitops/ext2-atomic-setbit.h> diff --git a/arch/alpha/include/asm/bugs.h b/arch/alpha/include/asm/bugs.h deleted file mode 100644 index 78030d1c7e7e..000000000000 --- a/arch/alpha/include/asm/bugs.h +++ /dev/null @@ -1,20 +0,0 @@ -/* - * include/asm-alpha/bugs.h - * - * Copyright (C) 1994 Linus Torvalds - */ - -/* - * This is included by init/main.c to check for architecture-dependent bugs. - * - * Needs: - * void check_bugs(void); - */ - -/* - * I don't know of any alpha bugs yet.. Nice chip - */ - -static void check_bugs(void) -{ -} diff --git a/arch/alpha/include/asm/cacheflush.h b/arch/alpha/include/asm/cacheflush.h index 9945ff483eaf..36a7e924c3b9 100644 --- a/arch/alpha/include/asm/cacheflush.h +++ b/arch/alpha/include/asm/cacheflush.h @@ -53,9 +53,16 @@ extern void flush_icache_user_page(struct vm_area_struct *vma, #define flush_icache_user_page flush_icache_user_page #endif /* CONFIG_SMP */ -/* This is used only in __do_fault and do_swap_page. */ -#define flush_icache_page(vma, page) \ - flush_icache_user_page((vma), (page), 0, 0) +/* + * Both implementations of flush_icache_user_page flush the entire + * address space, so one call, no matter how many pages. + */ +static inline void flush_icache_pages(struct vm_area_struct *vma, + struct page *page, unsigned int nr) +{ + flush_icache_user_page(vma, page, 0, 0); +} +#define flush_icache_pages flush_icache_pages #include <asm-generic/cacheflush.h> diff --git a/arch/alpha/include/asm/cmpxchg.h b/arch/alpha/include/asm/cmpxchg.h index 6e0a850aa9d3..91d4a4d9258c 100644 --- a/arch/alpha/include/asm/cmpxchg.h +++ b/arch/alpha/include/asm/cmpxchg.h @@ -6,15 +6,15 @@ * Atomic exchange routines. */ -#define ____xchg(type, args...) __xchg ## type ## _local(args) +#define ____xchg(type, args...) __arch_xchg ## type ## _local(args) #define ____cmpxchg(type, args...) __cmpxchg ## type ## _local(args) #include <asm/xchg.h> #define xchg_local(ptr, x) \ ({ \ __typeof__(*(ptr)) _x_ = (x); \ - (__typeof__(*(ptr))) __xchg_local((ptr), (unsigned long)_x_, \ - sizeof(*(ptr))); \ + (__typeof__(*(ptr))) __arch_xchg_local((ptr), (unsigned long)_x_,\ + sizeof(*(ptr))); \ }) #define arch_cmpxchg_local(ptr, o, n) \ @@ -34,7 +34,7 @@ #undef ____xchg #undef ____cmpxchg -#define ____xchg(type, args...) __xchg ##type(args) +#define ____xchg(type, args...) __arch_xchg ##type(args) #define ____cmpxchg(type, args...) __cmpxchg ##type(args) #include <asm/xchg.h> @@ -48,7 +48,7 @@ __typeof__(*(ptr)) _x_ = (x); \ smp_mb(); \ __ret = (__typeof__(*(ptr))) \ - __xchg((ptr), (unsigned long)_x_, sizeof(*(ptr))); \ + __arch_xchg((ptr), (unsigned long)_x_, sizeof(*(ptr))); \ smp_mb(); \ __ret; \ }) diff --git a/arch/alpha/include/asm/core_apecs.h b/arch/alpha/include/asm/core_apecs.h index 2d9726fc02ef..69a2fc62c9c3 100644 --- a/arch/alpha/include/asm/core_apecs.h +++ b/arch/alpha/include/asm/core_apecs.h @@ -384,7 +384,7 @@ struct el_apecs_procdata } \ } while (0) -__EXTERN_INLINE unsigned int apecs_ioread8(const void __iomem *xaddr) +__EXTERN_INLINE u8 apecs_ioread8(const void __iomem *xaddr) { unsigned long addr = (unsigned long) xaddr; unsigned long result, base_and_type; @@ -420,7 +420,7 @@ __EXTERN_INLINE void apecs_iowrite8(u8 b, void __iomem *xaddr) *(vuip) ((addr << 5) + base_and_type) = w; } -__EXTERN_INLINE unsigned int apecs_ioread16(const void __iomem *xaddr) +__EXTERN_INLINE u16 apecs_ioread16(const void __iomem *xaddr) { unsigned long addr = (unsigned long) xaddr; unsigned long result, base_and_type; @@ -456,7 +456,7 @@ __EXTERN_INLINE void apecs_iowrite16(u16 b, void __iomem *xaddr) *(vuip) ((addr << 5) + base_and_type) = w; } -__EXTERN_INLINE unsigned int apecs_ioread32(const void __iomem *xaddr) +__EXTERN_INLINE u32 apecs_ioread32(const void __iomem *xaddr) { unsigned long addr = (unsigned long) xaddr; if (addr < APECS_DENSE_MEM) @@ -472,6 +472,22 @@ __EXTERN_INLINE void apecs_iowrite32(u32 b, void __iomem *xaddr) *(vuip)addr = b; } +__EXTERN_INLINE u64 apecs_ioread64(const void __iomem *xaddr) +{ + unsigned long addr = (unsigned long) xaddr; + if (addr < APECS_DENSE_MEM) + addr = ((addr - APECS_IO) << 5) + APECS_IO + 0x18; + return *(vulp)addr; +} + +__EXTERN_INLINE void apecs_iowrite64(u64 b, void __iomem *xaddr) +{ + unsigned long addr = (unsigned long) xaddr; + if (addr < APECS_DENSE_MEM) + addr = ((addr - APECS_IO) << 5) + APECS_IO + 0x18; + *(vulp)addr = b; +} + __EXTERN_INLINE void __iomem *apecs_ioportmap(unsigned long addr) { return (void __iomem *)(addr + APECS_IO); diff --git a/arch/alpha/include/asm/core_cia.h b/arch/alpha/include/asm/core_cia.h index cb22991f6761..d26bdfb7ca3b 100644 --- a/arch/alpha/include/asm/core_cia.h +++ b/arch/alpha/include/asm/core_cia.h @@ -342,7 +342,7 @@ struct el_CIA_sysdata_mcheck { #define vuip volatile unsigned int __force * #define vulp volatile unsigned long __force * -__EXTERN_INLINE unsigned int cia_ioread8(const void __iomem *xaddr) +__EXTERN_INLINE u8 cia_ioread8(const void __iomem *xaddr) { unsigned long addr = (unsigned long) xaddr; unsigned long result, base_and_type; @@ -374,7 +374,7 @@ __EXTERN_INLINE void cia_iowrite8(u8 b, void __iomem *xaddr) *(vuip) ((addr << 5) + base_and_type) = w; } -__EXTERN_INLINE unsigned int cia_ioread16(const void __iomem *xaddr) +__EXTERN_INLINE u16 cia_ioread16(const void __iomem *xaddr) { unsigned long addr = (unsigned long) xaddr; unsigned long result, base_and_type; @@ -404,7 +404,7 @@ __EXTERN_INLINE void cia_iowrite16(u16 b, void __iomem *xaddr) *(vuip) ((addr << 5) + base_and_type) = w; } -__EXTERN_INLINE unsigned int cia_ioread32(const void __iomem *xaddr) +__EXTERN_INLINE u32 cia_ioread32(const void __iomem *xaddr) { unsigned long addr = (unsigned long) xaddr; if (addr < CIA_DENSE_MEM) @@ -420,6 +420,22 @@ __EXTERN_INLINE void cia_iowrite32(u32 b, void __iomem *xaddr) *(vuip)addr = b; } +__EXTERN_INLINE u64 cia_ioread64(const void __iomem *xaddr) +{ + unsigned long addr = (unsigned long) xaddr; + if (addr < CIA_DENSE_MEM) + addr = ((addr - CIA_IO) << 5) + CIA_IO + 0x18; + return *(vulp)addr; +} + +__EXTERN_INLINE void cia_iowrite64(u64 b, void __iomem *xaddr) +{ + unsigned long addr = (unsigned long) xaddr; + if (addr < CIA_DENSE_MEM) + addr = ((addr - CIA_IO) << 5) + CIA_IO + 0x18; + *(vulp)addr = b; +} + __EXTERN_INLINE void __iomem *cia_ioportmap(unsigned long addr) { return (void __iomem *)(addr + CIA_IO); diff --git a/arch/alpha/include/asm/core_lca.h b/arch/alpha/include/asm/core_lca.h index ec86314418cb..d8c3e72ef8f6 100644 --- a/arch/alpha/include/asm/core_lca.h +++ b/arch/alpha/include/asm/core_lca.h @@ -230,7 +230,7 @@ union el_lca { } while (0) -__EXTERN_INLINE unsigned int lca_ioread8(const void __iomem *xaddr) +__EXTERN_INLINE u8 lca_ioread8(const void __iomem *xaddr) { unsigned long addr = (unsigned long) xaddr; unsigned long result, base_and_type; @@ -266,7 +266,7 @@ __EXTERN_INLINE void lca_iowrite8(u8 b, void __iomem *xaddr) *(vuip) ((addr << 5) + base_and_type) = w; } -__EXTERN_INLINE unsigned int lca_ioread16(const void __iomem *xaddr) +__EXTERN_INLINE u16 lca_ioread16(const void __iomem *xaddr) { unsigned long addr = (unsigned long) xaddr; unsigned long result, base_and_type; @@ -302,7 +302,7 @@ __EXTERN_INLINE void lca_iowrite16(u16 b, void __iomem *xaddr) *(vuip) ((addr << 5) + base_and_type) = w; } -__EXTERN_INLINE unsigned int lca_ioread32(const void __iomem *xaddr) +__EXTERN_INLINE u32 lca_ioread32(const void __iomem *xaddr) { unsigned long addr = (unsigned long) xaddr; if (addr < LCA_DENSE_MEM) @@ -318,6 +318,22 @@ __EXTERN_INLINE void lca_iowrite32(u32 b, void __iomem *xaddr) *(vuip)addr = b; } +__EXTERN_INLINE u64 lca_ioread64(const void __iomem *xaddr) +{ + unsigned long addr = (unsigned long) xaddr; + if (addr < LCA_DENSE_MEM) + addr = ((addr - LCA_IO) << 5) + LCA_IO + 0x18; + return *(vulp)addr; +} + +__EXTERN_INLINE void lca_iowrite64(u64 b, void __iomem *xaddr) +{ + unsigned long addr = (unsigned long) xaddr; + if (addr < LCA_DENSE_MEM) + addr = ((addr - LCA_IO) << 5) + LCA_IO + 0x18; + *(vulp)addr = b; +} + __EXTERN_INLINE void __iomem *lca_ioportmap(unsigned long addr) { return (void __iomem *)(addr + LCA_IO); diff --git a/arch/alpha/include/asm/core_marvel.h b/arch/alpha/include/asm/core_marvel.h index b266e02e284b..d99f3a82e0e5 100644 --- a/arch/alpha/include/asm/core_marvel.h +++ b/arch/alpha/include/asm/core_marvel.h @@ -332,10 +332,10 @@ struct io7 { #define vucp volatile unsigned char __force * #define vusp volatile unsigned short __force * -extern unsigned int marvel_ioread8(const void __iomem *); +extern u8 marvel_ioread8(const void __iomem *); extern void marvel_iowrite8(u8 b, void __iomem *); -__EXTERN_INLINE unsigned int marvel_ioread16(const void __iomem *addr) +__EXTERN_INLINE u16 marvel_ioread16(const void __iomem *addr) { return __kernel_ldwu(*(vusp)addr); } diff --git a/arch/alpha/include/asm/core_mcpcia.h b/arch/alpha/include/asm/core_mcpcia.h index cb24d1bd6141..ed2bf8ad40ed 100644 --- a/arch/alpha/include/asm/core_mcpcia.h +++ b/arch/alpha/include/asm/core_mcpcia.h @@ -248,6 +248,7 @@ struct el_MCPCIA_uncorrected_frame_mcheck { #define vip volatile int __force * #define vuip volatile unsigned int __force * +#define vulp volatile unsigned long __force * #ifndef MCPCIA_ONE_HAE_WINDOW #define MCPCIA_FROB_MMIO \ @@ -267,7 +268,7 @@ extern inline int __mcpcia_is_mmio(unsigned long addr) return (addr & 0x80000000UL) == 0; } -__EXTERN_INLINE unsigned int mcpcia_ioread8(const void __iomem *xaddr) +__EXTERN_INLINE u8 mcpcia_ioread8(const void __iomem *xaddr) { unsigned long addr = (unsigned long)xaddr & MCPCIA_MEM_MASK; unsigned long hose = (unsigned long)xaddr & ~MCPCIA_MEM_MASK; @@ -291,7 +292,7 @@ __EXTERN_INLINE void mcpcia_iowrite8(u8 b, void __iomem *xaddr) *(vuip) ((addr << 5) + hose + 0x00) = w; } -__EXTERN_INLINE unsigned int mcpcia_ioread16(const void __iomem *xaddr) +__EXTERN_INLINE u16 mcpcia_ioread16(const void __iomem *xaddr) { unsigned long addr = (unsigned long)xaddr & MCPCIA_MEM_MASK; unsigned long hose = (unsigned long)xaddr & ~MCPCIA_MEM_MASK; @@ -315,7 +316,7 @@ __EXTERN_INLINE void mcpcia_iowrite16(u16 b, void __iomem *xaddr) *(vuip) ((addr << 5) + hose + 0x08) = w; } -__EXTERN_INLINE unsigned int mcpcia_ioread32(const void __iomem *xaddr) +__EXTERN_INLINE u32 mcpcia_ioread32(const void __iomem *xaddr) { unsigned long addr = (unsigned long)xaddr; @@ -335,6 +336,26 @@ __EXTERN_INLINE void mcpcia_iowrite32(u32 b, void __iomem *xaddr) *(vuip)addr = b; } +__EXTERN_INLINE u64 mcpcia_ioread64(const void __iomem *xaddr) +{ + unsigned long addr = (unsigned long)xaddr; + + if (!__mcpcia_is_mmio(addr)) + addr = ((addr & 0xffff) << 5) + (addr & ~0xfffful) + 0x18; + + return *(vulp)addr; +} + +__EXTERN_INLINE void mcpcia_iowrite64(u64 b, void __iomem *xaddr) +{ + unsigned long addr = (unsigned long)xaddr; + + if (!__mcpcia_is_mmio(addr)) + addr = ((addr & 0xffff) << 5) + (addr & ~0xfffful) + 0x18; + + *(vulp)addr = b; +} + __EXTERN_INLINE void __iomem *mcpcia_ioportmap(unsigned long addr) { @@ -362,6 +383,7 @@ __EXTERN_INLINE int mcpcia_is_mmio(const volatile void __iomem *xaddr) #undef vip #undef vuip +#undef vulp #undef __IO_PREFIX #define __IO_PREFIX mcpcia diff --git a/arch/alpha/include/asm/core_t2.h b/arch/alpha/include/asm/core_t2.h index 12bb7addc789..ab956b1625b5 100644 --- a/arch/alpha/include/asm/core_t2.h +++ b/arch/alpha/include/asm/core_t2.h @@ -360,6 +360,7 @@ struct el_t2_frame_corrected { #define vip volatile int * #define vuip volatile unsigned int * +#define vulp volatile unsigned long * extern inline u8 t2_inb(unsigned long addr) { @@ -402,6 +403,17 @@ extern inline void t2_outl(u32 b, unsigned long addr) mb(); } +extern inline u64 t2_inq(unsigned long addr) +{ + return *(vulp) ((addr << 5) + T2_IO + 0x18); +} + +extern inline void t2_outq(u64 b, unsigned long addr) +{ + *(vulp) ((addr << 5) + T2_IO + 0x18) = b; + mb(); +} + /* * Memory functions. @@ -572,7 +584,7 @@ __EXTERN_INLINE int t2_is_mmio(const volatile void __iomem *addr) it doesn't make sense to merge the pio and mmio routines. */ #define IOPORT(OS, NS) \ -__EXTERN_INLINE unsigned int t2_ioread##NS(const void __iomem *xaddr) \ +__EXTERN_INLINE u##NS t2_ioread##NS(const void __iomem *xaddr) \ { \ if (t2_is_mmio(xaddr)) \ return t2_read##OS(xaddr); \ @@ -590,11 +602,13 @@ __EXTERN_INLINE void t2_iowrite##NS(u##NS b, void __iomem *xaddr) \ IOPORT(b, 8) IOPORT(w, 16) IOPORT(l, 32) +IOPORT(q, 64) #undef IOPORT #undef vip #undef vuip +#undef vulp #undef __IO_PREFIX #define __IO_PREFIX t2 diff --git a/arch/alpha/include/asm/div64.h b/arch/alpha/include/asm/div64.h deleted file mode 100644 index 6cd978cefb28..000000000000 --- a/arch/alpha/include/asm/div64.h +++ /dev/null @@ -1 +0,0 @@ -#include <asm-generic/div64.h> diff --git a/arch/alpha/include/asm/dma-mapping.h b/arch/alpha/include/asm/dma-mapping.h index 0ee6a5c99b16..6ce7e2041685 100644 --- a/arch/alpha/include/asm/dma-mapping.h +++ b/arch/alpha/include/asm/dma-mapping.h @@ -4,7 +4,7 @@ extern const struct dma_map_ops alpha_pci_ops; -static inline const struct dma_map_ops *get_arch_dma_ops(struct bus_type *bus) +static inline const struct dma_map_ops *get_arch_dma_ops(void) { #ifdef CONFIG_ALPHA_JENSEN return NULL; diff --git a/arch/alpha/include/asm/dma.h b/arch/alpha/include/asm/dma.h index 28610ea7786d..a04d76b96089 100644 --- a/arch/alpha/include/asm/dma.h +++ b/arch/alpha/include/asm/dma.h @@ -365,13 +365,4 @@ extern void free_dma(unsigned int dmanr); /* release it again */ #define KERNEL_HAVE_CHECK_DMA extern int check_dma(unsigned int dmanr); -/* From PCI */ - -#ifdef CONFIG_PCI -extern int isa_dma_bridge_buggy; -#else -#define isa_dma_bridge_buggy (0) -#endif - - #endif /* _ASM_DMA_H */ diff --git a/arch/alpha/include/asm/elf.h b/arch/alpha/include/asm/elf.h index 8049997fa372..e6da23f1da83 100644 --- a/arch/alpha/include/asm/elf.h +++ b/arch/alpha/include/asm/elf.h @@ -120,12 +120,6 @@ extern int dump_elf_task(elf_greg_t *dest, struct task_struct *task); #define ELF_CORE_COPY_TASK_REGS(TASK, DEST) \ dump_elf_task(*(DEST), TASK) -/* Similar, but for the FP registers. */ - -extern int dump_elf_task_fp(elf_fpreg_t *dest, struct task_struct *task); -#define ELF_CORE_COPY_FPREGS(TASK, DEST) \ - dump_elf_task_fp(*(DEST), TASK) - /* This yields a mask that user programs can use to figure out what instruction set this CPU supports. This is trivial on Alpha, but not so on other machines. */ diff --git a/arch/alpha/include/asm/floppy.h b/arch/alpha/include/asm/floppy.h index 588758685439..64b42d9591fc 100644 --- a/arch/alpha/include/asm/floppy.h +++ b/arch/alpha/include/asm/floppy.h @@ -20,7 +20,7 @@ #define fd_free_dma() free_dma(FLOPPY_DMA) #define fd_clear_dma_ff() clear_dma_ff(FLOPPY_DMA) #define fd_set_dma_mode(mode) set_dma_mode(FLOPPY_DMA,mode) -#define fd_set_dma_addr(addr) set_dma_addr(FLOPPY_DMA,virt_to_bus(addr)) +#define fd_set_dma_addr(addr) set_dma_addr(FLOPPY_DMA,isa_virt_to_bus(addr)) #define fd_set_dma_count(count) set_dma_count(FLOPPY_DMA,count) #define fd_enable_irq() enable_irq(FLOPPY_IRQ) #define fd_disable_irq() disable_irq(FLOPPY_IRQ) diff --git a/arch/alpha/include/asm/fpu.h b/arch/alpha/include/asm/fpu.h index b9691405e56b..30b24135dd7a 100644 --- a/arch/alpha/include/asm/fpu.h +++ b/arch/alpha/include/asm/fpu.h @@ -15,21 +15,27 @@ rdfpcr(void) { unsigned long tmp, ret; + preempt_disable(); + if (current_thread_info()->status & TS_SAVED_FP) { + ret = current_thread_info()->fp[31]; + } else { #if defined(CONFIG_ALPHA_EV6) || defined(CONFIG_ALPHA_EV67) - __asm__ __volatile__ ( - "ftoit $f0,%0\n\t" - "mf_fpcr $f0\n\t" - "ftoit $f0,%1\n\t" - "itoft %0,$f0" - : "=r"(tmp), "=r"(ret)); + __asm__ __volatile__ ( + "ftoit $f0,%0\n\t" + "mf_fpcr $f0\n\t" + "ftoit $f0,%1\n\t" + "itoft %0,$f0" + : "=r"(tmp), "=r"(ret)); #else - __asm__ __volatile__ ( - "stt $f0,%0\n\t" - "mf_fpcr $f0\n\t" - "stt $f0,%1\n\t" - "ldt $f0,%0" - : "=m"(tmp), "=m"(ret)); + __asm__ __volatile__ ( + "stt $f0,%0\n\t" + "mf_fpcr $f0\n\t" + "stt $f0,%1\n\t" + "ldt $f0,%0" + : "=m"(tmp), "=m"(ret)); #endif + } + preempt_enable(); return ret; } @@ -39,21 +45,28 @@ wrfpcr(unsigned long val) { unsigned long tmp; + preempt_disable(); + if (current_thread_info()->status & TS_SAVED_FP) { + current_thread_info()->status |= TS_RESTORE_FP; + current_thread_info()->fp[31] = val; + } else { #if defined(CONFIG_ALPHA_EV6) || defined(CONFIG_ALPHA_EV67) - __asm__ __volatile__ ( - "ftoit $f0,%0\n\t" - "itoft %1,$f0\n\t" - "mt_fpcr $f0\n\t" - "itoft %0,$f0" - : "=&r"(tmp) : "r"(val)); + __asm__ __volatile__ ( + "ftoit $f0,%0\n\t" + "itoft %1,$f0\n\t" + "mt_fpcr $f0\n\t" + "itoft %0,$f0" + : "=&r"(tmp) : "r"(val)); #else - __asm__ __volatile__ ( - "stt $f0,%0\n\t" - "ldt $f0,%1\n\t" - "mt_fpcr $f0\n\t" - "ldt $f0,%0" - : "=m"(tmp) : "m"(val)); + __asm__ __volatile__ ( + "stt $f0,%0\n\t" + "ldt $f0,%1\n\t" + "mt_fpcr $f0\n\t" + "ldt $f0,%0" + : "=m"(tmp) : "m"(val)); #endif + } + preempt_enable(); } static inline unsigned long diff --git a/arch/alpha/include/asm/io.h b/arch/alpha/include/asm/io.h index c9cb554fbe54..4f47a5003fe8 100644 --- a/arch/alpha/include/asm/io.h +++ b/arch/alpha/include/asm/io.h @@ -14,10 +14,6 @@ the implementation we have here matches that interface. */ #include <asm-generic/iomap.h> -/* We don't use IO slowdowns on the Alpha, but.. */ -#define __SLOW_DOWN_IO do { } while (0) -#define SLOW_DOWN_IO do { } while (0) - /* * Virtual -> physical identity mapping starts at this offset */ @@ -90,6 +86,8 @@ static inline void * phys_to_virt(unsigned long address) } #endif +#define virt_to_phys virt_to_phys +#define phys_to_virt phys_to_virt #define page_to_phys(page) page_to_pa(page) /* Maximum PIO space address supported? */ @@ -106,15 +104,15 @@ static inline void * phys_to_virt(unsigned long address) extern unsigned long __direct_map_base; extern unsigned long __direct_map_size; -static inline unsigned long __deprecated virt_to_bus(volatile void *address) +static inline unsigned long __deprecated isa_virt_to_bus(volatile void *address) { unsigned long phys = virt_to_phys(address); unsigned long bus = phys + __direct_map_base; return phys <= __direct_map_size ? bus : 0; } -#define isa_virt_to_bus virt_to_bus +#define isa_virt_to_bus isa_virt_to_bus -static inline void * __deprecated bus_to_virt(unsigned long address) +static inline void * __deprecated isa_bus_to_virt(unsigned long address) { void *virt; @@ -125,7 +123,7 @@ static inline void * __deprecated bus_to_virt(unsigned long address) virt = phys_to_virt(address); return (long)address <= 0 ? NULL : virt; } -#define isa_bus_to_virt bus_to_virt +#define isa_bus_to_virt isa_bus_to_virt /* * There are different chipsets to interface the Alpha CPUs to the world. @@ -153,6 +151,7 @@ static inline void generic_##NAME(TYPE b, QUAL void __iomem *addr) \ REMAP1(unsigned int, ioread8, const) REMAP1(unsigned int, ioread16, const) REMAP1(unsigned int, ioread32, const) +REMAP1(u64, ioread64, const) REMAP1(u8, readb, const volatile) REMAP1(u16, readw, const volatile) REMAP1(u32, readl, const volatile) @@ -161,6 +160,7 @@ REMAP1(u64, readq, const volatile) REMAP2(u8, iowrite8, /**/) REMAP2(u16, iowrite16, /**/) REMAP2(u32, iowrite32, /**/) +REMAP2(u64, iowrite64, /**/) REMAP2(u8, writeb, volatile) REMAP2(u16, writew, volatile) REMAP2(u32, writel, volatile) @@ -242,6 +242,12 @@ extern u32 inl(unsigned long port); extern void outb(u8 b, unsigned long port); extern void outw(u16 b, unsigned long port); extern void outl(u32 b, unsigned long port); +#define inb inb +#define inw inw +#define inl inl +#define outb outb +#define outw outw +#define outl outl extern u8 readb(const volatile void __iomem *addr); extern u16 readw(const volatile void __iomem *addr); @@ -251,6 +257,14 @@ extern void writeb(u8 b, volatile void __iomem *addr); extern void writew(u16 b, volatile void __iomem *addr); extern void writel(u32 b, volatile void __iomem *addr); extern void writeq(u64 b, volatile void __iomem *addr); +#define readb readb +#define readw readw +#define readl readl +#define readq readq +#define writeb writeb +#define writew writew +#define writel writel +#define writeq writeq extern u8 __raw_readb(const volatile void __iomem *addr); extern u16 __raw_readw(const volatile void __iomem *addr); @@ -260,6 +274,14 @@ extern void __raw_writeb(u8 b, volatile void __iomem *addr); extern void __raw_writew(u16 b, volatile void __iomem *addr); extern void __raw_writel(u32 b, volatile void __iomem *addr); extern void __raw_writeq(u64 b, volatile void __iomem *addr); +#define __raw_readb __raw_readb +#define __raw_readw __raw_readw +#define __raw_readl __raw_readl +#define __raw_readq __raw_readq +#define __raw_writeb __raw_writeb +#define __raw_writew __raw_writew +#define __raw_writel __raw_writel +#define __raw_writeq __raw_writeq /* * Mapping from port numbers to __iomem space is pretty easy. @@ -277,13 +299,15 @@ extern inline void ioport_unmap(void __iomem *addr) { } +#define ioport_map ioport_map +#define ioport_unmap ioport_unmap + static inline void __iomem *ioremap(unsigned long port, unsigned long size) { return IO_CONCAT(__IO_PREFIX,ioremap) (port, size); } #define ioremap_wc ioremap -#define ioremap_uc ioremap static inline void iounmap(volatile void __iomem *addr) { @@ -358,6 +382,11 @@ extern inline void outw(u16 b, unsigned long port) } #endif +#define ioread8 ioread8 +#define ioread16 ioread16 +#define iowrite8 iowrite8 +#define iowrite16 iowrite16 + #if IO_CONCAT(__IO_PREFIX,trivial_io_lq) extern inline unsigned int ioread32(const void __iomem *addr) { @@ -368,12 +397,27 @@ extern inline unsigned int ioread32(const void __iomem *addr) return ret; } +extern inline u64 ioread64(const void __iomem *addr) +{ + unsigned int ret; + mb(); + ret = IO_CONCAT(__IO_PREFIX,ioread64)(addr); + mb(); + return ret; +} + extern inline void iowrite32(u32 b, void __iomem *addr) { mb(); IO_CONCAT(__IO_PREFIX, iowrite32)(b, addr); } +extern inline void iowrite64(u64 b, void __iomem *addr) +{ + mb(); + IO_CONCAT(__IO_PREFIX, iowrite64)(b, addr); +} + extern inline u32 inl(unsigned long port) { return ioread32(ioport_map(port, 4)); @@ -385,6 +429,11 @@ extern inline void outl(u32 b, unsigned long port) } #endif +#define ioread32 ioread32 +#define ioread64 ioread64 +#define iowrite32 iowrite32 +#define iowrite64 iowrite64 + #if IO_CONCAT(__IO_PREFIX,trivial_rw_bw) == 1 extern inline u8 __raw_readb(const volatile void __iomem *addr) { @@ -505,6 +554,10 @@ extern u8 readb_relaxed(const volatile void __iomem *addr); extern u16 readw_relaxed(const volatile void __iomem *addr); extern u32 readl_relaxed(const volatile void __iomem *addr); extern u64 readq_relaxed(const volatile void __iomem *addr); +#define readb_relaxed readb_relaxed +#define readw_relaxed readw_relaxed +#define readl_relaxed readl_relaxed +#define readq_relaxed readq_relaxed #if IO_CONCAT(__IO_PREFIX,trivial_io_bw) extern inline u8 readb_relaxed(const volatile void __iomem *addr) @@ -557,6 +610,10 @@ static inline void memsetw_io(volatile void __iomem *addr, u16 c, long len) _memset_c_io(addr, 0x0001000100010001UL * c, len); } +#define memset_io memset_io +#define memcpy_fromio memcpy_fromio +#define memcpy_toio memcpy_toio + /* * String versions of in/out ops: */ @@ -567,6 +624,13 @@ extern void outsb (unsigned long port, const void *src, unsigned long count); extern void outsw (unsigned long port, const void *src, unsigned long count); extern void outsl (unsigned long port, const void *src, unsigned long count); +#define insb insb +#define insw insw +#define insl insl +#define outsb outsb +#define outsw outsw +#define outsl outsl + /* * The Alpha Jensen hardware for some rather strange reason puts * the RTC clock at 0x170 instead of 0x70. Probably due to some @@ -587,20 +651,22 @@ extern void outsl (unsigned long port, const void *src, unsigned long count); #define RTC_ALWAYS_BCD 0 /* - * Some mucking forons use if[n]def writeq to check if platform has it. - * It's a bloody bad idea and we probably want ARCH_HAS_WRITEQ for them - * to play with; for now just use cpp anti-recursion logics and make sure - * that damn thing is defined and expands to itself. - */ - -#define writeq writeq -#define readq readq - -/* - * Convert a physical pointer to a virtual kernel pointer for /dev/mem - * access + * These get provided from <asm-generic/iomap.h> since alpha does not + * select GENERIC_IOMAP. */ -#define xlate_dev_mem_ptr(p) __va(p) +#define ioread64 ioread64 +#define iowrite64 iowrite64 +#define ioread64be ioread64be +#define iowrite64be iowrite64be +#define ioread8_rep ioread8_rep +#define ioread16_rep ioread16_rep +#define ioread32_rep ioread32_rep +#define iowrite8_rep iowrite8_rep +#define iowrite16_rep iowrite16_rep +#define iowrite32_rep iowrite32_rep +#define pci_iounmap pci_iounmap + +#include <asm-generic/io.h> #endif /* __KERNEL__ */ diff --git a/arch/alpha/include/asm/io_trivial.h b/arch/alpha/include/asm/io_trivial.h index a1a29cbe02fa..00032093bcfc 100644 --- a/arch/alpha/include/asm/io_trivial.h +++ b/arch/alpha/include/asm/io_trivial.h @@ -6,13 +6,13 @@ /* This file may be included multiple times. */ #if IO_CONCAT(__IO_PREFIX,trivial_io_bw) -__EXTERN_INLINE unsigned int +__EXTERN_INLINE u8 IO_CONCAT(__IO_PREFIX,ioread8)(const void __iomem *a) { return __kernel_ldbu(*(const volatile u8 __force *)a); } -__EXTERN_INLINE unsigned int +__EXTERN_INLINE u16 IO_CONCAT(__IO_PREFIX,ioread16)(const void __iomem *a) { return __kernel_ldwu(*(const volatile u16 __force *)a); @@ -32,7 +32,7 @@ IO_CONCAT(__IO_PREFIX,iowrite16)(u16 b, void __iomem *a) #endif #if IO_CONCAT(__IO_PREFIX,trivial_io_lq) -__EXTERN_INLINE unsigned int +__EXTERN_INLINE u32 IO_CONCAT(__IO_PREFIX,ioread32)(const void __iomem *a) { return *(const volatile u32 __force *)a; @@ -43,6 +43,18 @@ IO_CONCAT(__IO_PREFIX,iowrite32)(u32 b, void __iomem *a) { *(volatile u32 __force *)a = b; } + +__EXTERN_INLINE u64 +IO_CONCAT(__IO_PREFIX,ioread64)(const void __iomem *a) +{ + return *(const volatile u64 __force *)a; +} + +__EXTERN_INLINE void +IO_CONCAT(__IO_PREFIX,iowrite64)(u64 b, void __iomem *a) +{ + *(volatile u64 __force *)a = b; +} #endif #if IO_CONCAT(__IO_PREFIX,trivial_rw_bw) == 1 diff --git a/arch/alpha/include/asm/irq_regs.h b/arch/alpha/include/asm/irq_regs.h deleted file mode 100644 index 3dd9c0b70270..000000000000 --- a/arch/alpha/include/asm/irq_regs.h +++ /dev/null @@ -1 +0,0 @@ -#include <asm-generic/irq_regs.h> diff --git a/arch/alpha/include/asm/jensen.h b/arch/alpha/include/asm/jensen.h index 1c4131453db2..66eb049eb421 100644 --- a/arch/alpha/include/asm/jensen.h +++ b/arch/alpha/include/asm/jensen.h @@ -98,6 +98,7 @@ __EXTERN_INLINE void jensen_set_hae(unsigned long addr) } #define vuip volatile unsigned int * +#define vulp volatile unsigned long * /* * IO functions @@ -183,6 +184,12 @@ __EXTERN_INLINE u32 jensen_inl(unsigned long addr) return *(vuip) ((addr << 7) + EISA_IO + 0x60); } +__EXTERN_INLINE u64 jensen_inq(unsigned long addr) +{ + jensen_set_hae(0); + return *(vulp) ((addr << 7) + EISA_IO + 0x60); +} + __EXTERN_INLINE void jensen_outw(u16 b, unsigned long addr) { jensen_set_hae(0); @@ -197,6 +204,13 @@ __EXTERN_INLINE void jensen_outl(u32 b, unsigned long addr) mb(); } +__EXTERN_INLINE void jensen_outq(u64 b, unsigned long addr) +{ + jensen_set_hae(0); + *(vulp) ((addr << 7) + EISA_IO + 0x60) = b; + mb(); +} + /* * Memory functions. */ @@ -305,7 +319,7 @@ __EXTERN_INLINE int jensen_is_mmio(const volatile void __iomem *addr) that it doesn't make sense to merge them. */ #define IOPORT(OS, NS) \ -__EXTERN_INLINE unsigned int jensen_ioread##NS(const void __iomem *xaddr) \ +__EXTERN_INLINE u##NS jensen_ioread##NS(const void __iomem *xaddr) \ { \ if (jensen_is_mmio(xaddr)) \ return jensen_read##OS(xaddr - 0x100000000ul); \ @@ -323,10 +337,12 @@ __EXTERN_INLINE void jensen_iowrite##NS(u##NS b, void __iomem *xaddr) \ IOPORT(b, 8) IOPORT(w, 16) IOPORT(l, 32) +IOPORT(q, 64) #undef IOPORT #undef vuip +#undef vulp #undef __IO_PREFIX #define __IO_PREFIX jensen diff --git a/arch/alpha/include/asm/kdebug.h b/arch/alpha/include/asm/kdebug.h deleted file mode 100644 index 6ece1b037665..000000000000 --- a/arch/alpha/include/asm/kdebug.h +++ /dev/null @@ -1 +0,0 @@ -#include <asm-generic/kdebug.h> diff --git a/arch/alpha/include/asm/local.h b/arch/alpha/include/asm/local.h index fab26a1c93d5..88eb398947a5 100644 --- a/arch/alpha/include/asm/local.h +++ b/arch/alpha/include/asm/local.h @@ -52,33 +52,40 @@ static __inline__ long local_sub_return(long i, local_t * l) return result; } -#define local_cmpxchg(l, o, n) \ - (cmpxchg_local(&((l)->a.counter), (o), (n))) +static __inline__ long local_cmpxchg(local_t *l, long old, long new) +{ + return cmpxchg_local(&l->a.counter, old, new); +} + +static __inline__ bool local_try_cmpxchg(local_t *l, long *old, long new) +{ + return try_cmpxchg_local(&l->a.counter, (s64 *)old, new); +} + #define local_xchg(l, n) (xchg_local(&((l)->a.counter), (n))) /** - * local_add_unless - add unless the number is a given value + * local_add_unless - add unless the number is already a given value * @l: pointer of type local_t * @a: the amount to add to l... * @u: ...unless l is equal to u. * - * Atomically adds @a to @l, so long as it was not @u. - * Returns non-zero if @l was not @u, and zero otherwise. + * Atomically adds @a to @l, if @v was not already @u. + * Returns true if the addition was done. */ -#define local_add_unless(l, a, u) \ -({ \ - long c, old; \ - c = local_read(l); \ - for (;;) { \ - if (unlikely(c == (u))) \ - break; \ - old = local_cmpxchg((l), c, c + (a)); \ - if (likely(old == c)) \ - break; \ - c = old; \ - } \ - c != (u); \ -}) +static __inline__ bool +local_add_unless(local_t *l, long a, long u) +{ + long c = local_read(l); + + do { + if (unlikely(c == u)) + return false; + } while (!local_try_cmpxchg(l, &c, c + a)); + + return true; +} + #define local_inc_not_zero(l) local_add_unless((l), 1, 0) #define local_add_negative(a, l) (local_add_return((a), (l)) < 0) diff --git a/arch/alpha/include/asm/machvec.h b/arch/alpha/include/asm/machvec.h index e49fabce7b33..8623f995d34c 100644 --- a/arch/alpha/include/asm/machvec.h +++ b/arch/alpha/include/asm/machvec.h @@ -46,13 +46,15 @@ struct alpha_machine_vector void (*mv_pci_tbi)(struct pci_controller *hose, dma_addr_t start, dma_addr_t end); - unsigned int (*mv_ioread8)(const void __iomem *); - unsigned int (*mv_ioread16)(const void __iomem *); - unsigned int (*mv_ioread32)(const void __iomem *); + u8 (*mv_ioread8)(const void __iomem *); + u16 (*mv_ioread16)(const void __iomem *); + u32 (*mv_ioread32)(const void __iomem *); + u64 (*mv_ioread64)(const void __iomem *); void (*mv_iowrite8)(u8, void __iomem *); void (*mv_iowrite16)(u16, void __iomem *); void (*mv_iowrite32)(u32, void __iomem *); + void (*mv_iowrite64)(u64, void __iomem *); u8 (*mv_readb)(const volatile void __iomem *); u16 (*mv_readw)(const volatile void __iomem *); diff --git a/arch/alpha/include/asm/mmu_context.h b/arch/alpha/include/asm/mmu_context.h index 4eea7c616992..29a3e3a1f02b 100644 --- a/arch/alpha/include/asm/mmu_context.h +++ b/arch/alpha/include/asm/mmu_context.h @@ -183,6 +183,8 @@ ev4_switch_mm(struct mm_struct *prev_mm, struct mm_struct *next_mm, } extern void __load_new_mm_context(struct mm_struct *); +asmlinkage void do_page_fault(unsigned long address, unsigned long mmcsr, + long cause, struct pt_regs *regs); #ifdef CONFIG_SMP #define check_mmu_context() \ diff --git a/arch/alpha/include/asm/page.h b/arch/alpha/include/asm/page.h index 8f3f5eecba28..70419e6be1a3 100644 --- a/arch/alpha/include/asm/page.h +++ b/arch/alpha/include/asm/page.h @@ -6,7 +6,7 @@ #include <asm/pal.h> /* PAGE_SHIFT determines the page size */ -#define PAGE_SHIFT 13 +#define PAGE_SHIFT CONFIG_PAGE_SHIFT #define PAGE_SIZE (_AC(1,UL) << PAGE_SHIFT) #define PAGE_MASK (~(PAGE_SIZE-1)) @@ -17,9 +17,8 @@ extern void clear_page(void *page); #define clear_user_page(page, vaddr, pg) clear_page(page) -#define alloc_zeroed_user_highpage_movable(vma, vaddr) \ - alloc_page_vma(GFP_HIGHUSER_MOVABLE | __GFP_ZERO, vma, vaddr) -#define __HAVE_ARCH_ALLOC_ZEROED_USER_HIGHPAGE_MOVABLE +#define vma_alloc_zeroed_movable_folio(vma, vaddr) \ + vma_alloc_folio(GFP_HIGHUSER_MOVABLE | __GFP_ZERO, 0, vma, vaddr, false) extern void copy_page(void * _to, void * _from); #define copy_user_page(to, from, vaddr, pg) copy_page(to, from) @@ -87,10 +86,6 @@ typedef struct page *pgtable_t; #define virt_to_page(kaddr) pfn_to_page(__pa(kaddr) >> PAGE_SHIFT) #define virt_addr_valid(kaddr) pfn_valid((__pa(kaddr) >> PAGE_SHIFT)) -#ifdef CONFIG_FLATMEM -#define pfn_valid(pfn) ((pfn) < max_mapnr) -#endif /* CONFIG_FLATMEM */ - #include <asm-generic/memory_model.h> #include <asm-generic/getorder.h> diff --git a/arch/alpha/include/asm/pci.h b/arch/alpha/include/asm/pci.h index cf6bc1e64d66..6c04fcbdc8ed 100644 --- a/arch/alpha/include/asm/pci.h +++ b/arch/alpha/include/asm/pci.h @@ -56,12 +56,6 @@ struct pci_controller { /* IOMMU controls. */ -/* TODO: integrate with include/asm-generic/pci.h ? */ -static inline int pci_get_legacy_ide_irq(struct pci_dev *dev, int channel) -{ - return channel ? 15 : 14; -} - #define pci_domain_nr(bus) ((struct pci_controller *)(bus)->sysdata)->index static inline int pci_proc_domain(struct pci_bus *bus) @@ -94,7 +88,4 @@ extern void pci_adjust_legacy_attr(struct pci_bus *bus, enum pci_mmap_state mmap_type); #define HAVE_PCI_LEGACY 1 -extern int pci_create_resource_files(struct pci_dev *dev); -extern void pci_remove_resource_files(struct pci_dev *dev); - #endif /* __ALPHA_PCI_H */ diff --git a/arch/alpha/include/asm/pgtable.h b/arch/alpha/include/asm/pgtable.h index 170451fde043..635f0a5f5bbd 100644 --- a/arch/alpha/include/asm/pgtable.h +++ b/arch/alpha/include/asm/pgtable.h @@ -26,7 +26,6 @@ struct vm_area_struct; * hook is made available. */ #define set_pte(pteptr, pteval) ((*(pteptr)) = (pteval)) -#define set_pte_at(mm,addr,ptep,pteval) set_pte(ptep,pteval) /* PMD_SHIFT determines the size of the area a second-level page table can map */ #define PMD_SHIFT (PAGE_SHIFT + (PAGE_SHIFT-3)) @@ -74,6 +73,9 @@ struct vm_area_struct; #define _PAGE_DIRTY 0x20000 #define _PAGE_ACCESSED 0x40000 +/* We borrow bit 39 to store the exclusive marker in swap PTEs. */ +#define _PAGE_SWP_EXCLUSIVE 0x8000000000UL + /* * NOTE! The "accessed" bit isn't necessarily exact: it can be kept exactly * by software (use the KRE/URE/KWE/UWE bits appropriately), but I'll fake it. @@ -116,23 +118,6 @@ struct vm_area_struct; * arch/alpha/mm/fault.c) */ /* xwr */ -#define __P000 _PAGE_P(_PAGE_FOE | _PAGE_FOW | _PAGE_FOR) -#define __P001 _PAGE_P(_PAGE_FOE | _PAGE_FOW) -#define __P010 _PAGE_P(_PAGE_FOE) -#define __P011 _PAGE_P(_PAGE_FOE) -#define __P100 _PAGE_P(_PAGE_FOW | _PAGE_FOR) -#define __P101 _PAGE_P(_PAGE_FOW) -#define __P110 _PAGE_P(0) -#define __P111 _PAGE_P(0) - -#define __S000 _PAGE_S(_PAGE_FOE | _PAGE_FOW | _PAGE_FOR) -#define __S001 _PAGE_S(_PAGE_FOE | _PAGE_FOW) -#define __S010 _PAGE_S(_PAGE_FOE) -#define __S011 _PAGE_S(_PAGE_FOE) -#define __S100 _PAGE_S(_PAGE_FOW | _PAGE_FOR) -#define __S101 _PAGE_S(_PAGE_FOW) -#define __S110 _PAGE_S(0) -#define __S111 _PAGE_S(0) /* * pgprot_noncached() is only for infiniband pci support, and a real @@ -203,7 +188,8 @@ extern unsigned long __zero_page(void); * and a page entry and page directory to the page they refer to. */ #define page_to_pa(page) (page_to_pfn(page) << PAGE_SHIFT) -#define pte_pfn(pte) (pte_val(pte) >> 32) +#define PFN_PTE_SHIFT 32 +#define pte_pfn(pte) (pte_val(pte) >> PFN_PTE_SHIFT) #define pte_page(pte) pfn_to_page(pte_pfn(pte)) #define mk_pte(page, pgprot) \ @@ -270,7 +256,7 @@ extern inline int pte_young(pte_t pte) { return pte_val(pte) & _PAGE_ACCESSED; extern inline pte_t pte_wrprotect(pte_t pte) { pte_val(pte) |= _PAGE_FOW; return pte; } extern inline pte_t pte_mkclean(pte_t pte) { pte_val(pte) &= ~(__DIRTY_BITS); return pte; } extern inline pte_t pte_mkold(pte_t pte) { pte_val(pte) &= ~(__ACCESS_BITS); return pte; } -extern inline pte_t pte_mkwrite(pte_t pte) { pte_val(pte) &= ~_PAGE_FOW; return pte; } +extern inline pte_t pte_mkwrite_novma(pte_t pte){ pte_val(pte) &= ~_PAGE_FOW; return pte; } extern inline pte_t pte_mkdirty(pte_t pte) { pte_val(pte) |= __DIRTY_BITS; return pte; } extern inline pte_t pte_mkyoung(pte_t pte) { pte_val(pte) |= __ACCESS_BITS; return pte; } @@ -317,20 +303,53 @@ extern inline void update_mmu_cache(struct vm_area_struct * vma, { } +static inline void update_mmu_cache_range(struct vm_fault *vmf, + struct vm_area_struct *vma, unsigned long address, + pte_t *ptep, unsigned int nr) +{ +} + /* - * Non-present pages: high 24 bits are offset, next 8 bits type, - * low 32 bits zero. + * Encode/decode swap entries and swap PTEs. Swap PTEs are all PTEs that + * are !pte_none() && !pte_present(). + * + * Format of swap PTEs: + * + * 6 6 6 6 5 5 5 5 5 5 5 5 5 5 4 4 4 4 4 4 4 4 4 4 3 3 3 3 3 3 3 3 + * 3 2 1 0 9 8 7 6 5 4 3 2 1 0 9 8 7 6 5 4 3 2 1 0 9 8 7 6 5 4 3 2 + * <------------------- offset ------------------> E <--- type --> + * + * 3 3 2 2 2 2 2 2 2 2 2 2 1 1 1 1 1 1 1 1 1 1 + * 1 0 9 8 7 6 5 4 3 2 1 0 9 8 7 6 5 4 3 2 1 0 9 8 7 6 5 4 3 2 1 0 + * <--------------------------- zeroes --------------------------> + * + * E is the exclusive marker that is not stored in swap entries. */ extern inline pte_t mk_swap_pte(unsigned long type, unsigned long offset) -{ pte_t pte; pte_val(pte) = (type << 32) | (offset << 40); return pte; } +{ pte_t pte; pte_val(pte) = ((type & 0x7f) << 32) | (offset << 40); return pte; } -#define __swp_type(x) (((x).val >> 32) & 0xff) +#define __swp_type(x) (((x).val >> 32) & 0x7f) #define __swp_offset(x) ((x).val >> 40) #define __swp_entry(type, off) ((swp_entry_t) { pte_val(mk_swap_pte((type), (off))) }) #define __pte_to_swp_entry(pte) ((swp_entry_t) { pte_val(pte) }) #define __swp_entry_to_pte(x) ((pte_t) { (x).val }) -#define kern_addr_valid(addr) (1) +static inline int pte_swp_exclusive(pte_t pte) +{ + return pte_val(pte) & _PAGE_SWP_EXCLUSIVE; +} + +static inline pte_t pte_swp_mkexclusive(pte_t pte) +{ + pte_val(pte) |= _PAGE_SWP_EXCLUSIVE; + return pte; +} + +static inline pte_t pte_swp_clear_exclusive(pte_t pte) +{ + pte_val(pte) &= ~_PAGE_SWP_EXCLUSIVE; + return pte; +} #define pte_ERROR(e) \ printk("%s:%d: bad pte %016lx.\n", __FILE__, __LINE__, pte_val(e)) diff --git a/arch/alpha/include/asm/processor.h b/arch/alpha/include/asm/processor.h index 43e234c518b1..55bb1c09fd39 100644 --- a/arch/alpha/include/asm/processor.h +++ b/arch/alpha/include/asm/processor.h @@ -36,8 +36,6 @@ extern void start_thread(struct pt_regs *, unsigned long, unsigned long); /* Free all resources held by a thread. */ struct task_struct; -extern void release_thread(struct task_struct *); - unsigned long __get_wchan(struct task_struct *p); #define KSTK_EIP(tsk) (task_pt_regs(tsk)->pc) @@ -49,12 +47,6 @@ unsigned long __get_wchan(struct task_struct *p); #define ARCH_HAS_PREFETCH #define ARCH_HAS_PREFETCHW -#define ARCH_HAS_SPINLOCK_PREFETCH - -#ifndef CONFIG_SMP -/* Nothing to prefetch. */ -#define spin_lock_prefetch(lock) do { } while (0) -#endif extern inline void prefetch(const void *ptr) { @@ -66,11 +58,4 @@ extern inline void prefetchw(const void *ptr) __builtin_prefetch(ptr, 1, 3); } -#ifdef CONFIG_SMP -extern inline void spin_lock_prefetch(const void *ptr) -{ - __builtin_prefetch(ptr, 1, 3); -} -#endif - #endif /* __ASM_ALPHA_PROCESSOR_H */ diff --git a/arch/alpha/include/asm/ptrace.h b/arch/alpha/include/asm/ptrace.h index df5f317ab3fc..3557ce64ed21 100644 --- a/arch/alpha/include/asm/ptrace.h +++ b/arch/alpha/include/asm/ptrace.h @@ -16,7 +16,6 @@ #define current_pt_regs() \ ((struct pt_regs *) ((char *)current_thread_info() + 2*PAGE_SIZE) - 1) -#define signal_pt_regs current_pt_regs #define force_successful_syscall_return() (current_pt_regs()->r0 = 0) diff --git a/arch/alpha/include/asm/termios.h b/arch/alpha/include/asm/termios.h deleted file mode 100644 index b7c77bb1bfd2..000000000000 --- a/arch/alpha/include/asm/termios.h +++ /dev/null @@ -1,87 +0,0 @@ -/* SPDX-License-Identifier: GPL-2.0 */ -#ifndef _ALPHA_TERMIOS_H -#define _ALPHA_TERMIOS_H - -#include <uapi/asm/termios.h> - -/* eof=^D eol=\0 eol2=\0 erase=del - werase=^W kill=^U reprint=^R sxtc=\0 - intr=^C quit=^\ susp=^Z <OSF/1 VDSUSP> - start=^Q stop=^S lnext=^V discard=^U - vmin=\1 vtime=\0 -*/ -#define INIT_C_CC "\004\000\000\177\027\025\022\000\003\034\032\000\021\023\026\025\001\000" - -/* - * Translate a "termio" structure into a "termios". Ugh. - */ - -#define user_termio_to_kernel_termios(a_termios, u_termio) \ -({ \ - struct ktermios *k_termios = (a_termios); \ - struct termio k_termio; \ - int canon, ret; \ - \ - ret = copy_from_user(&k_termio, u_termio, sizeof(k_termio)); \ - if (!ret) { \ - /* Overwrite only the low bits. */ \ - *(unsigned short *)&k_termios->c_iflag = k_termio.c_iflag; \ - *(unsigned short *)&k_termios->c_oflag = k_termio.c_oflag; \ - *(unsigned short *)&k_termios->c_cflag = k_termio.c_cflag; \ - *(unsigned short *)&k_termios->c_lflag = k_termio.c_lflag; \ - canon = k_termio.c_lflag & ICANON; \ - \ - k_termios->c_cc[VINTR] = k_termio.c_cc[_VINTR]; \ - k_termios->c_cc[VQUIT] = k_termio.c_cc[_VQUIT]; \ - k_termios->c_cc[VERASE] = k_termio.c_cc[_VERASE]; \ - k_termios->c_cc[VKILL] = k_termio.c_cc[_VKILL]; \ - k_termios->c_cc[VEOL2] = k_termio.c_cc[_VEOL2]; \ - k_termios->c_cc[VSWTC] = k_termio.c_cc[_VSWTC]; \ - k_termios->c_cc[canon ? VEOF : VMIN] = k_termio.c_cc[_VEOF]; \ - k_termios->c_cc[canon ? VEOL : VTIME] = k_termio.c_cc[_VEOL]; \ - } \ - ret; \ -}) - -/* - * Translate a "termios" structure into a "termio". Ugh. - * - * Note the "fun" _VMIN overloading. - */ -#define kernel_termios_to_user_termio(u_termio, a_termios) \ -({ \ - struct ktermios *k_termios = (a_termios); \ - struct termio k_termio; \ - int canon; \ - \ - k_termio.c_iflag = k_termios->c_iflag; \ - k_termio.c_oflag = k_termios->c_oflag; \ - k_termio.c_cflag = k_termios->c_cflag; \ - canon = (k_termio.c_lflag = k_termios->c_lflag) & ICANON; \ - \ - k_termio.c_line = k_termios->c_line; \ - k_termio.c_cc[_VINTR] = k_termios->c_cc[VINTR]; \ - k_termio.c_cc[_VQUIT] = k_termios->c_cc[VQUIT]; \ - k_termio.c_cc[_VERASE] = k_termios->c_cc[VERASE]; \ - k_termio.c_cc[_VKILL] = k_termios->c_cc[VKILL]; \ - k_termio.c_cc[_VEOF] = k_termios->c_cc[canon ? VEOF : VMIN]; \ - k_termio.c_cc[_VEOL] = k_termios->c_cc[canon ? VEOL : VTIME]; \ - k_termio.c_cc[_VEOL2] = k_termios->c_cc[VEOL2]; \ - k_termio.c_cc[_VSWTC] = k_termios->c_cc[VSWTC]; \ - \ - copy_to_user(u_termio, &k_termio, sizeof(k_termio)); \ -}) - -#define user_termios_to_kernel_termios(k, u) \ - copy_from_user(k, u, sizeof(struct termios2)) - -#define kernel_termios_to_user_termios(u, k) \ - copy_to_user(u, k, sizeof(struct termios2)) - -#define user_termios_to_kernel_termios_1(k, u) \ - copy_from_user(k, u, sizeof(struct termios)) - -#define kernel_termios_to_user_termios_1(u, k) \ - copy_to_user(u, k, sizeof(struct termios)) - -#endif /* _ALPHA_TERMIOS_H */ diff --git a/arch/alpha/include/asm/thread_info.h b/arch/alpha/include/asm/thread_info.h index fdc485d7787a..4a4d00b37986 100644 --- a/arch/alpha/include/asm/thread_info.h +++ b/arch/alpha/include/asm/thread_info.h @@ -26,6 +26,7 @@ struct thread_info { int bpt_nsaved; unsigned long bpt_addr[2]; /* breakpoint handling */ unsigned int bpt_insn[2]; + unsigned long fp[32]; }; /* @@ -41,6 +42,8 @@ struct thread_info { register struct thread_info *__current_thread_info __asm__("$8"); #define current_thread_info() __current_thread_info +register unsigned long *current_stack_pointer __asm__ ("$30"); + #endif /* __ASSEMBLY__ */ /* Thread information allocation. */ @@ -75,16 +78,15 @@ register struct thread_info *__current_thread_info __asm__("$8"); /* Work to do on interrupt/exception return. */ #define _TIF_WORK_MASK (_TIF_SIGPENDING | _TIF_NEED_RESCHED | \ - _TIF_NOTIFY_RESUME) - -/* Work to do on any return to userspace. */ -#define _TIF_ALLWORK_MASK (_TIF_WORK_MASK \ - | _TIF_SYSCALL_TRACE) + _TIF_NOTIFY_RESUME | _TIF_NOTIFY_SIGNAL) #define TS_UAC_NOPRINT 0x0001 /* ! Preserve the following three */ #define TS_UAC_NOFIX 0x0002 /* ! flags as they match */ #define TS_UAC_SIGBUS 0x0004 /* ! userspace part of 'osf_sysinfo' */ +#define TS_SAVED_FP 0x0008 +#define TS_RESTORE_FP 0x0010 + #define SET_UNALIGN_CTL(task,value) ({ \ __u32 status = task_thread_info(task)->status & ~UAC_BITMASK; \ if (value & PR_UNALIGN_NOPRINT) \ @@ -108,5 +110,17 @@ register struct thread_info *__current_thread_info __asm__("$8"); put_user(res, (int __user *)(value)); \ }) +#ifndef __ASSEMBLY__ +extern void __save_fpu(void); + +static inline void save_fpu(void) +{ + if (!(current_thread_info()->status & TS_SAVED_FP)) { + current_thread_info()->status |= TS_SAVED_FP; + __save_fpu(); + } +} +#endif + #endif /* __KERNEL__ */ #endif /* _ALPHA_THREAD_INFO_H */ diff --git a/arch/alpha/include/asm/unistd.h b/arch/alpha/include/asm/unistd.h index 986f5da9b7d8..caabd92ea709 100644 --- a/arch/alpha/include/asm/unistd.h +++ b/arch/alpha/include/asm/unistd.h @@ -4,7 +4,7 @@ #include <uapi/asm/unistd.h> -#define NR_SYSCALLS __NR_syscalls +#define NR_syscalls __NR_syscalls #define __ARCH_WANT_NEW_STAT #define __ARCH_WANT_OLD_READDIR diff --git a/arch/alpha/include/uapi/asm/mman.h b/arch/alpha/include/uapi/asm/mman.h index 4aa996423b0d..763929e814e9 100644 --- a/arch/alpha/include/uapi/asm/mman.h +++ b/arch/alpha/include/uapi/asm/mman.h @@ -76,6 +76,8 @@ #define MADV_DONTNEED_LOCKED 24 /* like DONTNEED, but drop locked pages too */ +#define MADV_COLLAPSE 25 /* Synchronous hugepage collapse */ + /* compatibility flags */ #define MAP_FILE 0 diff --git a/arch/alpha/include/uapi/asm/ptrace.h b/arch/alpha/include/uapi/asm/ptrace.h index c29194181025..5ca45934fcbb 100644 --- a/arch/alpha/include/uapi/asm/ptrace.h +++ b/arch/alpha/include/uapi/asm/ptrace.h @@ -64,7 +64,9 @@ struct switch_stack { unsigned long r14; unsigned long r15; unsigned long r26; +#ifndef __KERNEL__ unsigned long fp[32]; /* fp[31] is fpcr */ +#endif }; diff --git a/arch/alpha/include/uapi/asm/socket.h b/arch/alpha/include/uapi/asm/socket.h index 739891b94136..e94f621903fe 100644 --- a/arch/alpha/include/uapi/asm/socket.h +++ b/arch/alpha/include/uapi/asm/socket.h @@ -137,6 +137,9 @@ #define SO_RCVMARK 75 +#define SO_PASSPIDFD 76 +#define SO_PEERPIDFD 77 + #if !defined(__KERNEL__) #if __BITS_PER_LONG == 64 diff --git a/arch/alpha/kernel/Makefile b/arch/alpha/kernel/Makefile index 5a74581bf0ee..fb4efec7cbc7 100644 --- a/arch/alpha/kernel/Makefile +++ b/arch/alpha/kernel/Makefile @@ -3,13 +3,13 @@ # Makefile for the linux kernel. # -extra-y := head.o vmlinux.lds +extra-y := vmlinux.lds asflags-y := $(KBUILD_CFLAGS) ccflags-y := -Wno-sign-compare -obj-y := entry.o traps.o process.o osf_sys.o irq.o \ +obj-y := head.o entry.o traps.o process.o osf_sys.o irq.o \ irq_alpha.o signal.o setup.o ptrace.o time.o \ - systbls.o err_common.o io.o bugs.o + systbls.o err_common.o io.o bugs.o termios.o obj-$(CONFIG_VGA_HOSE) += console.o obj-$(CONFIG_SMP) += smp.o @@ -47,10 +47,6 @@ else # Misc support obj-$(CONFIG_ALPHA_SRM) += srmcons.o -ifdef CONFIG_BINFMT_AOUT -obj-y += binfmt_loader.o -endif - # Core logic support obj-$(CONFIG_ALPHA_APECS) += core_apecs.o obj-$(CONFIG_ALPHA_CIA) += core_cia.o diff --git a/arch/alpha/kernel/asm-offsets.c b/arch/alpha/kernel/asm-offsets.c index 2e125e5c1508..bf1eedd27cf7 100644 --- a/arch/alpha/kernel/asm-offsets.c +++ b/arch/alpha/kernel/asm-offsets.c @@ -12,11 +12,13 @@ #include <linux/kbuild.h> #include <asm/io.h> -void foo(void) +static void __used foo(void) { DEFINE(TI_TASK, offsetof(struct thread_info, task)); DEFINE(TI_FLAGS, offsetof(struct thread_info, flags)); DEFINE(TI_CPU, offsetof(struct thread_info, cpu)); + DEFINE(TI_FP, offsetof(struct thread_info, fp)); + DEFINE(TI_STATUS, offsetof(struct thread_info, status)); BLANK(); DEFINE(TASK_BLOCKED, offsetof(struct task_struct, blocked)); diff --git a/arch/alpha/kernel/binfmt_loader.c b/arch/alpha/kernel/binfmt_loader.c deleted file mode 100644 index e4be7a543ecf..000000000000 --- a/arch/alpha/kernel/binfmt_loader.c +++ /dev/null @@ -1,46 +0,0 @@ -// SPDX-License-Identifier: GPL-2.0 -#include <linux/init.h> -#include <linux/fs.h> -#include <linux/file.h> -#include <linux/mm_types.h> -#include <linux/binfmts.h> -#include <linux/a.out.h> - -static int load_binary(struct linux_binprm *bprm) -{ - struct exec *eh = (struct exec *)bprm->buf; - unsigned long loader; - struct file *file; - int retval; - - if (eh->fh.f_magic != 0x183 || (eh->fh.f_flags & 0x3000) != 0x3000) - return -ENOEXEC; - - if (bprm->loader) - return -ENOEXEC; - - loader = bprm->vma->vm_end - sizeof(void *); - - file = open_exec("/sbin/loader"); - retval = PTR_ERR(file); - if (IS_ERR(file)) - return retval; - - /* Remember if the application is TASO. */ - bprm->taso = eh->ah.entry < 0x100000000UL; - - bprm->interpreter = file; - bprm->loader = loader; - return 0; -} - -static struct linux_binfmt loader_format = { - .load_binary = load_binary, -}; - -static int __init init_loader_binfmt(void) -{ - insert_binfmt(&loader_format); - return 0; -} -arch_initcall(init_loader_binfmt); diff --git a/arch/alpha/kernel/core_cia.c b/arch/alpha/kernel/core_cia.c index f489170201c3..12926e9538b8 100644 --- a/arch/alpha/kernel/core_cia.c +++ b/arch/alpha/kernel/core_cia.c @@ -527,7 +527,7 @@ verify_tb_operation(void) if (use_tbia_try2) { alpha_mv.mv_pci_tbi = cia_pci_tbi_try2; - /* Tags 0-3 must be disabled if we use this workaraund. */ + /* Tags 0-3 must be disabled if we use this workaround. */ wmb(); *(vip)CIA_IOC_TB_TAGn(0) = 2; *(vip)CIA_IOC_TB_TAGn(1) = 2; diff --git a/arch/alpha/kernel/core_marvel.c b/arch/alpha/kernel/core_marvel.c index 1efca79ac83c..e9348aec4649 100644 --- a/arch/alpha/kernel/core_marvel.c +++ b/arch/alpha/kernel/core_marvel.c @@ -803,7 +803,7 @@ void __iomem *marvel_ioportmap (unsigned long addr) return (void __iomem *)addr; } -unsigned int +u8 marvel_ioread8(const void __iomem *xaddr) { unsigned long addr = (unsigned long) xaddr; diff --git a/arch/alpha/kernel/entry.S b/arch/alpha/kernel/entry.S index e227f3a29a43..eb51f93a70c8 100644 --- a/arch/alpha/kernel/entry.S +++ b/arch/alpha/kernel/entry.S @@ -17,7 +17,7 @@ /* Stack offsets. */ #define SP_OFF 184 -#define SWITCH_STACK_SIZE 320 +#define SWITCH_STACK_SIZE 64 .macro CFI_START_OSF_FRAME func .align 4 @@ -159,7 +159,6 @@ .cfi_rel_offset $13, 32 .cfi_rel_offset $14, 40 .cfi_rel_offset $15, 48 - /* We don't really care about the FP registers for debugging. */ .endm .macro UNDO_SWITCH_STACK @@ -454,7 +453,7 @@ entSys: SAVE_ALL lda $8, 0x3fff bic $sp, $8, $8 - lda $4, NR_SYSCALLS($31) + lda $4, NR_syscalls($31) stq $16, SP_OFF+24($sp) lda $5, sys_call_table lda $27, sys_ni_syscall @@ -469,13 +468,16 @@ entSys: #ifdef CONFIG_AUDITSYSCALL lda $6, _TIF_SYSCALL_TRACE | _TIF_SYSCALL_AUDIT and $3, $6, $3 -#endif bne $3, strace +#else + blbs $3, strace /* check for SYSCALL_TRACE in disguise */ +#endif beq $4, 1f ldq $27, 0($5) 1: jsr $26, ($27), sys_ni_syscall ldgp $gp, 0($26) blt $0, $syscall_error /* the call failed */ +$ret_success: stq $0, 0($sp) stq $31, 72($sp) /* a3=0 => no error */ @@ -495,6 +497,10 @@ ret_to_user: and $17, _TIF_WORK_MASK, $2 bne $2, work_pending restore_all: + ldl $2, TI_STATUS($8) + and $2, TS_SAVED_FP | TS_RESTORE_FP, $3 + bne $3, restore_fpu +restore_other: .cfi_remember_state RESTORE_ALL call_pal PAL_rti @@ -503,7 +509,7 @@ ret_to_kernel: .cfi_restore_state lda $16, 7 call_pal PAL_swpipl - br restore_all + br restore_other .align 3 $syscall_error: @@ -525,11 +531,6 @@ $syscall_error: stq $1, 72($sp) /* a3 for return */ br ret_from_sys_call -$ret_success: - stq $0, 0($sp) - stq $31, 72($sp) /* a3=0 => no error */ - br ret_from_sys_call - /* * Do all cleanup when returning from all interrupts and system calls. * @@ -572,6 +573,14 @@ $work_notifysig: .type strace, @function strace: /* set up signal stack, call syscall_trace */ + // NB: if anyone adds preemption, this block will need to be protected + ldl $1, TI_STATUS($8) + and $1, TS_SAVED_FP, $3 + or $1, TS_SAVED_FP, $2 + bne $3, 1f + stl $2, TI_STATUS($8) + bsr $26, __save_fpu +1: DO_SWITCH_STACK jsr $26, syscall_trace_enter /* returns the syscall number */ UNDO_SWITCH_STACK @@ -585,7 +594,7 @@ strace: ldq $21, 88($sp) /* get the system call pointer.. */ - lda $1, NR_SYSCALLS($31) + lda $1, NR_syscalls($31) lda $2, sys_call_table lda $27, sys_ni_syscall cmpult $0, $1, $1 @@ -598,8 +607,8 @@ ret_from_straced: /* check return.. */ blt $0, $strace_error /* the call failed */ - stq $31, 72($sp) /* a3=0 => no error */ $strace_success: + stq $31, 72($sp) /* a3=0 => no error */ stq $0, 0($sp) /* save return value */ DO_SWITCH_STACK @@ -651,40 +660,6 @@ do_switch_stack: stq $14, 40($sp) stq $15, 48($sp) stq $26, 56($sp) - stt $f0, 64($sp) - stt $f1, 72($sp) - stt $f2, 80($sp) - stt $f3, 88($sp) - stt $f4, 96($sp) - stt $f5, 104($sp) - stt $f6, 112($sp) - stt $f7, 120($sp) - stt $f8, 128($sp) - stt $f9, 136($sp) - stt $f10, 144($sp) - stt $f11, 152($sp) - stt $f12, 160($sp) - stt $f13, 168($sp) - stt $f14, 176($sp) - stt $f15, 184($sp) - stt $f16, 192($sp) - stt $f17, 200($sp) - stt $f18, 208($sp) - stt $f19, 216($sp) - stt $f20, 224($sp) - stt $f21, 232($sp) - stt $f22, 240($sp) - stt $f23, 248($sp) - stt $f24, 256($sp) - stt $f25, 264($sp) - stt $f26, 272($sp) - stt $f27, 280($sp) - mf_fpcr $f0 # get fpcr - stt $f28, 288($sp) - stt $f29, 296($sp) - stt $f30, 304($sp) - stt $f0, 312($sp) # save fpcr in slot of $f31 - ldt $f0, 64($sp) # dont let "do_switch_stack" change fp state. ret $31, ($1), 1 .cfi_endproc .size do_switch_stack, .-do_switch_stack @@ -703,54 +678,71 @@ undo_switch_stack: ldq $14, 40($sp) ldq $15, 48($sp) ldq $26, 56($sp) - ldt $f30, 312($sp) # get saved fpcr - ldt $f0, 64($sp) - ldt $f1, 72($sp) - ldt $f2, 80($sp) - ldt $f3, 88($sp) - mt_fpcr $f30 # install saved fpcr - ldt $f4, 96($sp) - ldt $f5, 104($sp) - ldt $f6, 112($sp) - ldt $f7, 120($sp) - ldt $f8, 128($sp) - ldt $f9, 136($sp) - ldt $f10, 144($sp) - ldt $f11, 152($sp) - ldt $f12, 160($sp) - ldt $f13, 168($sp) - ldt $f14, 176($sp) - ldt $f15, 184($sp) - ldt $f16, 192($sp) - ldt $f17, 200($sp) - ldt $f18, 208($sp) - ldt $f19, 216($sp) - ldt $f20, 224($sp) - ldt $f21, 232($sp) - ldt $f22, 240($sp) - ldt $f23, 248($sp) - ldt $f24, 256($sp) - ldt $f25, 264($sp) - ldt $f26, 272($sp) - ldt $f27, 280($sp) - ldt $f28, 288($sp) - ldt $f29, 296($sp) - ldt $f30, 304($sp) lda $sp, SWITCH_STACK_SIZE($sp) ret $31, ($1), 1 .cfi_endproc .size undo_switch_stack, .-undo_switch_stack + +#define FR(n) n * 8 + TI_FP($8) + .align 4 + .globl __save_fpu + .type __save_fpu, @function +__save_fpu: +#define V(n) stt $f##n, FR(n) + V( 0); V( 1); V( 2); V( 3) + V( 4); V( 5); V( 6); V( 7) + V( 8); V( 9); V(10); V(11) + V(12); V(13); V(14); V(15) + V(16); V(17); V(18); V(19) + V(20); V(21); V(22); V(23) + V(24); V(25); V(26); V(27) + mf_fpcr $f0 # get fpcr + V(28); V(29); V(30) + stt $f0, FR(31) # save fpcr in slot of $f31 + ldt $f0, FR(0) # don't let "__save_fpu" change fp state. + ret +#undef V + .size __save_fpu, .-__save_fpu + + .align 4 +restore_fpu: + and $3, TS_RESTORE_FP, $3 + bic $2, TS_SAVED_FP | TS_RESTORE_FP, $2 + beq $3, 1f +#define V(n) ldt $f##n, FR(n) + ldt $f30, FR(31) # get saved fpcr + V( 0); V( 1); V( 2); V( 3) + mt_fpcr $f30 # install saved fpcr + V( 4); V( 5); V( 6); V( 7) + V( 8); V( 9); V(10); V(11) + V(12); V(13); V(14); V(15) + V(16); V(17); V(18); V(19) + V(20); V(21); V(22); V(23) + V(24); V(25); V(26); V(27) + V(28); V(29); V(30) +1: stl $2, TI_STATUS($8) + br restore_other +#undef V + /* * The meat of the context switch code. */ - .align 4 .globl alpha_switch_to .type alpha_switch_to, @function .cfi_startproc alpha_switch_to: DO_SWITCH_STACK + ldl $1, TI_STATUS($8) + and $1, TS_RESTORE_FP, $3 + bne $3, 1f + or $1, TS_RESTORE_FP | TS_SAVED_FP, $2 + and $1, TS_SAVED_FP, $3 + stl $2, TI_STATUS($8) + bne $3, 1f + bsr $26, __save_fpu +1: call_pal PAL_swpctx lda $8, 0x3fff UNDO_SWITCH_STACK @@ -768,7 +760,7 @@ alpha_switch_to: .align 4 .ent ret_from_fork ret_from_fork: - lda $26, ret_from_sys_call + lda $26, ret_to_user mov $17, $16 jmp $31, schedule_tail .end ret_from_fork @@ -801,6 +793,14 @@ ret_from_kernel_thread: alpha_\name: .prologue 0 bsr $1, do_switch_stack + // NB: if anyone adds preemption, this block will need to be protected + ldl $1, TI_STATUS($8) + and $1, TS_SAVED_FP, $3 + or $1, TS_SAVED_FP, $2 + bne $3, 1f + stl $2, TI_STATUS($8) + bsr $26, __save_fpu +1: jsr $26, sys_\name ldq $26, 56($sp) lda $sp, SWITCH_STACK_SIZE($sp) diff --git a/arch/alpha/kernel/io.c b/arch/alpha/kernel/io.c index 838586abb1e0..eda09778268f 100644 --- a/arch/alpha/kernel/io.c +++ b/arch/alpha/kernel/io.c @@ -41,6 +41,15 @@ unsigned int ioread32(const void __iomem *addr) return ret; } +u64 ioread64(const void __iomem *addr) +{ + unsigned int ret; + mb(); + ret = IO_CONCAT(__IO_PREFIX,ioread64)(addr); + mb(); + return ret; +} + void iowrite8(u8 b, void __iomem *addr) { mb(); @@ -59,12 +68,20 @@ void iowrite32(u32 b, void __iomem *addr) IO_CONCAT(__IO_PREFIX,iowrite32)(b, addr); } +void iowrite64(u64 b, void __iomem *addr) +{ + mb(); + IO_CONCAT(__IO_PREFIX,iowrite64)(b, addr); +} + EXPORT_SYMBOL(ioread8); EXPORT_SYMBOL(ioread16); EXPORT_SYMBOL(ioread32); +EXPORT_SYMBOL(ioread64); EXPORT_SYMBOL(iowrite8); EXPORT_SYMBOL(iowrite16); EXPORT_SYMBOL(iowrite32); +EXPORT_SYMBOL(iowrite64); u8 inb(unsigned long port) { diff --git a/arch/alpha/kernel/machvec_impl.h b/arch/alpha/kernel/machvec_impl.h index 393d5d6ca5d2..c2ebcb39e589 100644 --- a/arch/alpha/kernel/machvec_impl.h +++ b/arch/alpha/kernel/machvec_impl.h @@ -78,9 +78,11 @@ .mv_ioread8 = CAT(low,_ioread8), \ .mv_ioread16 = CAT(low,_ioread16), \ .mv_ioread32 = CAT(low,_ioread32), \ + .mv_ioread64 = CAT(low,_ioread64), \ .mv_iowrite8 = CAT(low,_iowrite8), \ .mv_iowrite16 = CAT(low,_iowrite16), \ .mv_iowrite32 = CAT(low,_iowrite32), \ + .mv_iowrite64 = CAT(low,_iowrite64), \ .mv_readb = CAT(low,_readb), \ .mv_readw = CAT(low,_readw), \ .mv_readl = CAT(low,_readl), \ diff --git a/arch/alpha/kernel/module.c b/arch/alpha/kernel/module.c index 5b60c248de9e..cbefa5a77384 100644 --- a/arch/alpha/kernel/module.c +++ b/arch/alpha/kernel/module.c @@ -146,10 +146,8 @@ apply_relocate_add(Elf64_Shdr *sechdrs, const char *strtab, base = (void *)sechdrs[sechdrs[relsec].sh_info].sh_addr; symtab = (Elf64_Sym *)sechdrs[symindex].sh_addr; - /* The small sections were sorted to the end of the segment. - The following should definitely cover them. */ - gp = (u64)me->core_layout.base + me->core_layout.size - 0x8000; got = sechdrs[me->arch.gotsecindex].sh_addr; + gp = got + 0x8000; for (i = 0; i < n; i++) { unsigned long r_sym = ELF64_R_SYM (rela[i].r_info); diff --git a/arch/alpha/kernel/osf_sys.c b/arch/alpha/kernel/osf_sys.c index d257293401e2..5db88b627439 100644 --- a/arch/alpha/kernel/osf_sys.c +++ b/arch/alpha/kernel/osf_sys.c @@ -97,7 +97,7 @@ struct osf_dirent { unsigned int d_ino; unsigned short d_reclen; unsigned short d_namlen; - char d_name[1]; + char d_name[]; }; struct osf_dirent_callback { @@ -108,7 +108,7 @@ struct osf_dirent_callback { int error; }; -static int +static bool osf_filldir(struct dir_context *ctx, const char *name, int namlen, loff_t offset, u64 ino, unsigned int d_type) { @@ -120,11 +120,11 @@ osf_filldir(struct dir_context *ctx, const char *name, int namlen, buf->error = -EINVAL; /* only used if we fail */ if (reclen > buf->count) - return -EINVAL; + return false; d_ino = ino; if (sizeof(d_ino) < sizeof(ino) && d_ino != ino) { buf->error = -EOVERFLOW; - return -EOVERFLOW; + return false; } if (buf->basep) { if (put_user(offset, buf->basep)) @@ -141,10 +141,10 @@ osf_filldir(struct dir_context *ctx, const char *name, int namlen, dirent = (void __user *)dirent + reclen; buf->dirent = dirent; buf->count -= reclen; - return 0; + return true; Efault: buf->error = -EFAULT; - return -EFAULT; + return false; } SYSCALL_DEFINE4(osf_getdirentries, unsigned int, fd, @@ -522,7 +522,7 @@ SYSCALL_DEFINE4(osf_mount, unsigned long, typenr, const char __user *, path, break; default: retval = -EINVAL; - printk("osf_mount(%ld, %x)\n", typenr, flag); + printk_ratelimited("osf_mount(%ld, %x)\n", typenr, flag); } return retval; @@ -1014,8 +1014,6 @@ SYSCALL_DEFINE2(osf_settimeofday, struct timeval32 __user *, tv, return do_sys_settimeofday64(tv ? &kts : NULL, tz ? &ktz : NULL); } -asmlinkage long sys_ni_posix_timers(void); - SYSCALL_DEFINE2(osf_utimes, const char __user *, filename, struct timeval32 __user *, tvs) { @@ -1278,48 +1276,6 @@ arch_get_unmapped_area(struct file *filp, unsigned long addr, return addr; } -#ifdef CONFIG_OSF4_COMPAT -/* Clear top 32 bits of iov_len in the user's buffer for - compatibility with old versions of OSF/1 where iov_len - was defined as int. */ -static int -osf_fix_iov_len(const struct iovec __user *iov, unsigned long count) -{ - unsigned long i; - - for (i = 0 ; i < count ; i++) { - int __user *iov_len_high = (int __user *)&iov[i].iov_len + 1; - - if (put_user(0, iov_len_high)) - return -EFAULT; - } - return 0; -} -#endif - -SYSCALL_DEFINE3(osf_readv, unsigned long, fd, - const struct iovec __user *, vector, unsigned long, count) -{ -#ifdef CONFIG_OSF4_COMPAT - if (unlikely(personality(current->personality) == PER_OSF4)) - if (osf_fix_iov_len(vector, count)) - return -EFAULT; -#endif - - return sys_readv(fd, vector, count); -} - -SYSCALL_DEFINE3(osf_writev, unsigned long, fd, - const struct iovec __user *, vector, unsigned long, count) -{ -#ifdef CONFIG_OSF4_COMPAT - if (unlikely(personality(current->personality) == PER_OSF4)) - if (osf_fix_iov_len(vector, count)) - return -EFAULT; -#endif - return sys_writev(fd, vector, count); -} - SYSCALL_DEFINE2(osf_getpriority, int, which, int, who) { int prio = sys_getpriority(which, who); diff --git a/arch/alpha/kernel/pci.c b/arch/alpha/kernel/pci.c index 64fbfb0763b2..4458eb7f44f0 100644 --- a/arch/alpha/kernel/pci.c +++ b/arch/alpha/kernel/pci.c @@ -288,11 +288,10 @@ pcibios_claim_one_bus(struct pci_bus *b) struct pci_bus *child_bus; list_for_each_entry(dev, &b->devices, bus_list) { + struct resource *r; int i; - for (i = 0; i < PCI_NUM_RESOURCES; i++) { - struct resource *r = &dev->resource[i]; - + pci_dev_for_each_resource(dev, r, i) { if (r->parent || !r->start || !r->flags) continue; if (pci_has_flag(PCI_PROBE_ONLY) || diff --git a/arch/alpha/kernel/pci_iommu.c b/arch/alpha/kernel/pci_iommu.c index e83a02ed5267..c81183935e97 100644 --- a/arch/alpha/kernel/pci_iommu.c +++ b/arch/alpha/kernel/pci_iommu.c @@ -127,10 +127,12 @@ again: goto again; } - if (ptes[p+i]) - p = ALIGN(p + i + 1, mask + 1), i = 0; - else + if (ptes[p+i]) { + p = ALIGN(p + i + 1, mask + 1); + i = 0; + } else { i = i + 1; + } } if (i < n) { diff --git a/arch/alpha/kernel/perf_event.c b/arch/alpha/kernel/perf_event.c index efcf7321701b..ccdb508c1516 100644 --- a/arch/alpha/kernel/perf_event.c +++ b/arch/alpha/kernel/perf_event.c @@ -689,8 +689,6 @@ static int __hw_perf_event_init(struct perf_event *event) */ static int alpha_pmu_event_init(struct perf_event *event) { - int err; - /* does not support taken branch sampling */ if (has_branch_stack(event)) return -EOPNOTSUPP; @@ -709,9 +707,7 @@ static int alpha_pmu_event_init(struct perf_event *event) return -ENODEV; /* Do the real initialisation work. */ - err = __hw_perf_event_init(event); - - return err; + return __hw_perf_event_init(event); } /* diff --git a/arch/alpha/kernel/process.c b/arch/alpha/kernel/process.c index e2e25f8b5e76..582d96548385 100644 --- a/arch/alpha/kernel/process.c +++ b/arch/alpha/kernel/process.c @@ -9,6 +9,7 @@ * This file handles the architecture-dependent parts of process handling. */ +#include <linux/cpu.h> #include <linux/errno.h> #include <linux/module.h> #include <linux/sched.h> @@ -57,12 +58,12 @@ EXPORT_SYMBOL(pm_power_off); void arch_cpu_idle(void) { wtint(0); - raw_local_irq_enable(); } -void arch_cpu_idle_dead(void) +void __noreturn arch_cpu_idle_dead(void) { wtint(INT_MAX); + BUG(); } #endif /* ALPHA_WTINT */ @@ -74,7 +75,7 @@ struct halt_info { static void common_shutdown_1(void *generic_ptr) { - struct halt_info *how = (struct halt_info *)generic_ptr; + struct halt_info *how = generic_ptr; struct percpu_struct *cpup; unsigned long *pflags, flags; int cpuid = smp_processor_id(); @@ -134,7 +135,7 @@ common_shutdown_1(void *generic_ptr) #ifdef CONFIG_DUMMY_CONSOLE /* If we've gotten here after SysRq-b, leave interrupt context before taking over the console. */ - if (in_irq()) + if (in_hardirq()) irq_exit(); /* This has the effect of resetting the VGA video origin. */ console_lock(); @@ -225,11 +226,6 @@ flush_thread(void) current_thread_info()->pcb.unique = 0; } -void -release_thread(struct task_struct *dead_task) -{ -} - /* * Copy architecture-specific thread state */ @@ -249,6 +245,7 @@ int copy_thread(struct task_struct *p, const struct kernel_clone_args *args) childstack = ((struct switch_stack *) childregs) - 1; childti->pcb.ksp = (unsigned long) childstack; childti->pcb.flags = 1; /* set FEN, clear everything else */ + childti->status |= TS_SAVED_FP | TS_RESTORE_FP; if (unlikely(args->fn)) { /* kernel thread */ @@ -258,6 +255,7 @@ int copy_thread(struct task_struct *p, const struct kernel_clone_args *args) childstack->r9 = (unsigned long) args->fn; childstack->r10 = (unsigned long) args->fn_arg; childregs->hae = alpha_mv.hae_cache; + memset(childti->fp, '\0', sizeof(childti->fp)); childti->pcb.usp = 0; return 0; } @@ -338,14 +336,11 @@ dump_elf_task(elf_greg_t *dest, struct task_struct *task) } EXPORT_SYMBOL(dump_elf_task); -int -dump_elf_task_fp(elf_fpreg_t *dest, struct task_struct *task) +int elf_core_copy_task_fpregs(struct task_struct *t, elf_fpregset_t *fpu) { - struct switch_stack *sw = (struct switch_stack *)task_pt_regs(task) - 1; - memcpy(dest, sw->fp, 32 * 8); + memcpy(fpu, task_thread_info(t)->fp, 32 * 8); return 1; } -EXPORT_SYMBOL(dump_elf_task_fp); /* * Return saved PC of a blocked thread. This assumes the frame diff --git a/arch/alpha/kernel/proto.h b/arch/alpha/kernel/proto.h index 5816a31c1b38..2c89c1c55712 100644 --- a/arch/alpha/kernel/proto.h +++ b/arch/alpha/kernel/proto.h @@ -1,5 +1,6 @@ /* SPDX-License-Identifier: GPL-2.0 */ #include <linux/interrupt.h> +#include <linux/screen_info.h> #include <linux/io.h> /* Prototypes of functions used across modules here in this directory. */ @@ -113,6 +114,7 @@ extern int boot_cpuid; #ifdef CONFIG_VERBOSE_MCHECK extern unsigned long alpha_verbose_mcheck; #endif +extern struct screen_info vgacon_screen_info; /* srmcons.c */ #if defined(CONFIG_ALPHA_GENERIC) || defined(CONFIG_ALPHA_SRM) diff --git a/arch/alpha/kernel/ptrace.c b/arch/alpha/kernel/ptrace.c index a1a239ea002d..fde4c68e7a0b 100644 --- a/arch/alpha/kernel/ptrace.c +++ b/arch/alpha/kernel/ptrace.c @@ -78,6 +78,8 @@ enum { (PAGE_SIZE*2 - sizeof(struct pt_regs) - sizeof(struct switch_stack) \ + offsetof(struct switch_stack, reg)) +#define FP_REG(reg) (offsetof(struct thread_info, reg)) + static int regoff[] = { PT_REG( r0), PT_REG( r1), PT_REG( r2), PT_REG( r3), PT_REG( r4), PT_REG( r5), PT_REG( r6), PT_REG( r7), @@ -87,14 +89,14 @@ static int regoff[] = { PT_REG( r20), PT_REG( r21), PT_REG( r22), PT_REG( r23), PT_REG( r24), PT_REG( r25), PT_REG( r26), PT_REG( r27), PT_REG( r28), PT_REG( gp), -1, -1, - SW_REG(fp[ 0]), SW_REG(fp[ 1]), SW_REG(fp[ 2]), SW_REG(fp[ 3]), - SW_REG(fp[ 4]), SW_REG(fp[ 5]), SW_REG(fp[ 6]), SW_REG(fp[ 7]), - SW_REG(fp[ 8]), SW_REG(fp[ 9]), SW_REG(fp[10]), SW_REG(fp[11]), - SW_REG(fp[12]), SW_REG(fp[13]), SW_REG(fp[14]), SW_REG(fp[15]), - SW_REG(fp[16]), SW_REG(fp[17]), SW_REG(fp[18]), SW_REG(fp[19]), - SW_REG(fp[20]), SW_REG(fp[21]), SW_REG(fp[22]), SW_REG(fp[23]), - SW_REG(fp[24]), SW_REG(fp[25]), SW_REG(fp[26]), SW_REG(fp[27]), - SW_REG(fp[28]), SW_REG(fp[29]), SW_REG(fp[30]), SW_REG(fp[31]), + FP_REG(fp[ 0]), FP_REG(fp[ 1]), FP_REG(fp[ 2]), FP_REG(fp[ 3]), + FP_REG(fp[ 4]), FP_REG(fp[ 5]), FP_REG(fp[ 6]), FP_REG(fp[ 7]), + FP_REG(fp[ 8]), FP_REG(fp[ 9]), FP_REG(fp[10]), FP_REG(fp[11]), + FP_REG(fp[12]), FP_REG(fp[13]), FP_REG(fp[14]), FP_REG(fp[15]), + FP_REG(fp[16]), FP_REG(fp[17]), FP_REG(fp[18]), FP_REG(fp[19]), + FP_REG(fp[20]), FP_REG(fp[21]), FP_REG(fp[22]), FP_REG(fp[23]), + FP_REG(fp[24]), FP_REG(fp[25]), FP_REG(fp[26]), FP_REG(fp[27]), + FP_REG(fp[28]), FP_REG(fp[29]), FP_REG(fp[30]), FP_REG(fp[31]), PT_REG( pc) }; diff --git a/arch/alpha/kernel/rtc.c b/arch/alpha/kernel/rtc.c index fb3025396ac9..cfdf90bc8b3f 100644 --- a/arch/alpha/kernel/rtc.c +++ b/arch/alpha/kernel/rtc.c @@ -80,7 +80,7 @@ init_rtc_epoch(void) static int alpha_rtc_read_time(struct device *dev, struct rtc_time *tm) { - int ret = mc146818_get_time(tm); + int ret = mc146818_get_time(tm, 10); if (ret < 0) { dev_err_ratelimited(dev, "unable to read current time\n"); diff --git a/arch/alpha/kernel/setup.c b/arch/alpha/kernel/setup.c index b4fbbba30aa2..0738f9396f95 100644 --- a/arch/alpha/kernel/setup.c +++ b/arch/alpha/kernel/setup.c @@ -131,13 +131,14 @@ static void determine_cpu_caches (unsigned int); static char __initdata command_line[COMMAND_LINE_SIZE]; +#ifdef CONFIG_VGA_CONSOLE /* * The format of "screen_info" is strange, and due to early * i386-setup code. This is just enough to make the console * code think we're on a VGA color display. */ -struct screen_info screen_info = { +struct screen_info vgacon_screen_info = { .orig_x = 0, .orig_y = 25, .orig_video_cols = 80, @@ -145,8 +146,7 @@ struct screen_info screen_info = { .orig_video_isVGA = 1, .orig_video_points = 16 }; - -EXPORT_SYMBOL(screen_info); +#endif /* * The direct map I/O window, if any. This should be the same @@ -385,8 +385,7 @@ setup_memory(void *kernel_end) #endif /* CONFIG_BLK_DEV_INITRD */ } -int __init -page_is_ram(unsigned long pfn) +int page_is_ram(unsigned long pfn) { struct memclust_struct * cluster; struct memdesc_struct * memdesc; @@ -422,7 +421,7 @@ register_cpus(void) arch_initcall(register_cpus); #ifdef CONFIG_MAGIC_SYSRQ -static void sysrq_reboot_handler(int unused) +static void sysrq_reboot_handler(u8 unused) { machine_halt(); } @@ -491,9 +490,9 @@ setup_arch(char **cmdline_p) boot flags depending on the boot mode, we need some shorthand. This should do for installation. */ if (strcmp(COMMAND_LINE, "INSTALL") == 0) { - strlcpy(command_line, "root=/dev/fd0 load_ramdisk=1", sizeof command_line); + strscpy(command_line, "root=/dev/fd0 load_ramdisk=1", sizeof(command_line)); } else { - strlcpy(command_line, COMMAND_LINE, sizeof command_line); + strscpy(command_line, COMMAND_LINE, sizeof(command_line)); } strcpy(boot_command_line, command_line); *cmdline_p = command_line; @@ -653,12 +652,12 @@ setup_arch(char **cmdline_p) #ifdef CONFIG_VT #if defined(CONFIG_VGA_CONSOLE) - conswitchp = &vga_con; + vgacon_register_screen(&vgacon_screen_info); #endif #endif /* Default root filesystem to sda2. */ - ROOT_DEV = Root_SDA2; + ROOT_DEV = MKDEV(SCSI_DISK0_MAJOR, 2); #ifdef CONFIG_EISA /* FIXME: only set this when we actually have EISA in this box? */ diff --git a/arch/alpha/kernel/signal.c b/arch/alpha/kernel/signal.c index 6f47f256fe80..e62d1d461b1f 100644 --- a/arch/alpha/kernel/signal.c +++ b/arch/alpha/kernel/signal.c @@ -150,9 +150,10 @@ restore_sigcontext(struct sigcontext __user *sc, struct pt_regs *regs) { unsigned long usp; struct switch_stack *sw = (struct switch_stack *)regs - 1; - long i, err = __get_user(regs->pc, &sc->sc_pc); + long err = __get_user(regs->pc, &sc->sc_pc); current->restart_block.fn = do_no_restart_syscall; + current_thread_info()->status |= TS_SAVED_FP | TS_RESTORE_FP; sw->r26 = (unsigned long) ret_from_sys_call; @@ -189,9 +190,9 @@ restore_sigcontext(struct sigcontext __user *sc, struct pt_regs *regs) err |= __get_user(usp, sc->sc_regs+30); wrusp(usp); - for (i = 0; i < 31; i++) - err |= __get_user(sw->fp[i], sc->sc_fpregs+i); - err |= __get_user(sw->fp[31], &sc->sc_fpcr); + err |= __copy_from_user(current_thread_info()->fp, + sc->sc_fpregs, 31 * 8); + err |= __get_user(current_thread_info()->fp[31], &sc->sc_fpcr); return err; } @@ -272,7 +273,7 @@ setup_sigcontext(struct sigcontext __user *sc, struct pt_regs *regs, unsigned long mask, unsigned long sp) { struct switch_stack *sw = (struct switch_stack *)regs - 1; - long i, err = 0; + long err = 0; err |= __put_user(on_sig_stack((unsigned long)sc), &sc->sc_onstack); err |= __put_user(mask, &sc->sc_mask); @@ -312,10 +313,10 @@ setup_sigcontext(struct sigcontext __user *sc, struct pt_regs *regs, err |= __put_user(sp, sc->sc_regs+30); err |= __put_user(0, sc->sc_regs+31); - for (i = 0; i < 31; i++) - err |= __put_user(sw->fp[i], sc->sc_fpregs+i); + err |= __copy_to_user(sc->sc_fpregs, + current_thread_info()->fp, 31 * 8); err |= __put_user(0, sc->sc_fpregs+31); - err |= __put_user(sw->fp[31], &sc->sc_fpcr); + err |= __put_user(current_thread_info()->fp[31], &sc->sc_fpcr); err |= __put_user(regs->trap_a0, &sc->sc_traparg_a0); err |= __put_user(regs->trap_a1, &sc->sc_traparg_a1); @@ -528,6 +529,9 @@ do_work_pending(struct pt_regs *regs, unsigned long thread_flags, } else { local_irq_enable(); if (thread_flags & (_TIF_SIGPENDING|_TIF_NOTIFY_SIGNAL)) { + preempt_disable(); + save_fpu(); + preempt_enable(); do_signal(regs, r0, r19); r0 = 0; } else { diff --git a/arch/alpha/kernel/smp.c b/arch/alpha/kernel/smp.c index cb64e4797d2a..8e9dd63b220c 100644 --- a/arch/alpha/kernel/smp.c +++ b/arch/alpha/kernel/smp.c @@ -467,11 +467,6 @@ smp_prepare_cpus(unsigned int max_cpus) smp_num_cpus = smp_num_probed; } -void -smp_prepare_boot_cpu(void) -{ -} - int __cpu_up(unsigned int cpu, struct task_struct *tidle) { @@ -497,12 +492,6 @@ smp_cpus_done(unsigned int max_cpus) ((bogosum + 2500) / (5000/HZ)) % 100); } -int -setup_profiling_timer(unsigned int multiplier) -{ - return -EINVAL; -} - static void send_ipi_message(const struct cpumask *to_whom, enum ipi_message_type operation) { @@ -568,7 +557,7 @@ handle_ipi(struct pt_regs *regs) } void -smp_send_reschedule(int cpu) +arch_smp_send_reschedule(int cpu) { #ifdef DEBUG_IPI_MSG if (cpu == hard_smp_processor_id()) @@ -634,7 +623,7 @@ flush_tlb_all(void) static void ipi_flush_tlb_mm(void *x) { - struct mm_struct *mm = (struct mm_struct *) x; + struct mm_struct *mm = x; if (mm == current->active_mm && !asn_locked()) flush_tlb_current(mm); else @@ -676,7 +665,7 @@ struct flush_tlb_page_struct { static void ipi_flush_tlb_page(void *x) { - struct flush_tlb_page_struct *data = (struct flush_tlb_page_struct *)x; + struct flush_tlb_page_struct *data = x; struct mm_struct * mm = data->mm; if (mm == current->active_mm && !asn_locked()) diff --git a/arch/alpha/kernel/srmcons.c b/arch/alpha/kernel/srmcons.c index 6dc952b0df4a..feaf89f6936b 100644 --- a/arch/alpha/kernel/srmcons.c +++ b/arch/alpha/kernel/srmcons.c @@ -53,7 +53,7 @@ srmcons_do_receive_chars(struct tty_port *port) do { result.as_long = callback_getc(0); if (result.bits.status < 2) { - tty_insert_flip_char(port, (char)result.bits.c, 0); + tty_insert_flip_char(port, (u8)result.bits.c, 0); count++; } } while((result.bits.status & 1) && (++loops < 10)); @@ -88,30 +88,27 @@ srmcons_receive_chars(struct timer_list *t) } /* called with callback_lock held */ -static int -srmcons_do_write(struct tty_port *port, const char *buf, int count) +static void +srmcons_do_write(struct tty_port *port, const u8 *buf, size_t count) { - static char str_cr[1] = "\r"; - long c, remaining = count; + size_t c; srmcons_result result; - char *cur; - int need_cr; - for (cur = (char *)buf; remaining > 0; ) { - need_cr = 0; + while (count > 0) { + bool need_cr = false; /* * Break it up into reasonable size chunks to allow a chance * for input to get in */ - for (c = 0; c < min_t(long, 128L, remaining) && !need_cr; c++) - if (cur[c] == '\n') - need_cr = 1; + for (c = 0; c < min_t(size_t, 128U, count) && !need_cr; c++) + if (buf[c] == '\n') + need_cr = true; while (c > 0) { - result.as_long = callback_puts(0, cur, c); + result.as_long = callback_puts(0, buf, c); c -= result.bits.c; - remaining -= result.bits.c; - cur += result.bits.c; + count -= result.bits.c; + buf += result.bits.c; /* * Check for pending input iff a tty port was provided @@ -121,22 +118,20 @@ srmcons_do_write(struct tty_port *port, const char *buf, int count) } while (need_cr) { - result.as_long = callback_puts(0, str_cr, 1); + result.as_long = callback_puts(0, "\r", 1); if (result.bits.c > 0) - need_cr = 0; + need_cr = false; } } - return count; } -static int -srmcons_write(struct tty_struct *tty, - const unsigned char *buf, int count) +static ssize_t +srmcons_write(struct tty_struct *tty, const u8 *buf, size_t count) { unsigned long flags; spin_lock_irqsave(&srmcons_callback_lock, flags); - srmcons_do_write(tty->port, (const char *) buf, count); + srmcons_do_write(tty->port, buf, count); spin_unlock_irqrestore(&srmcons_callback_lock, flags); return count; diff --git a/arch/alpha/kernel/sys_miata.c b/arch/alpha/kernel/sys_miata.c index e1bee8f84c58..33b2798de8fc 100644 --- a/arch/alpha/kernel/sys_miata.c +++ b/arch/alpha/kernel/sys_miata.c @@ -183,16 +183,17 @@ miata_map_irq(const struct pci_dev *dev, u8 slot, u8 pin) the 2nd 8259 controller. So we have to check for it first. */ if((slot == 7) && (PCI_FUNC(dev->devfn) == 3)) { - u8 irq=0; struct pci_dev *pdev = pci_get_slot(dev->bus, dev->devfn & ~7); - if(pdev == NULL || pci_read_config_byte(pdev, 0x40,&irq) != PCIBIOS_SUCCESSFUL) { - pci_dev_put(pdev); + u8 irq = 0; + int ret; + + if (!pdev) return -1; - } - else { - pci_dev_put(pdev); - return irq; - } + + ret = pci_read_config_byte(pdev, 0x40, &irq); + pci_dev_put(pdev); + + return ret == PCIBIOS_SUCCESSFUL ? irq : -1; } return COMMON_TABLE_LOOKUP; diff --git a/arch/alpha/kernel/sys_sio.c b/arch/alpha/kernel/sys_sio.c index 7c420d8dac53..086488ed83a7 100644 --- a/arch/alpha/kernel/sys_sio.c +++ b/arch/alpha/kernel/sys_sio.c @@ -57,11 +57,13 @@ sio_init_irq(void) static inline void __init alphabook1_init_arch(void) { +#ifdef CONFIG_VGA_CONSOLE /* The AlphaBook1 has LCD video fixed at 800x600, 37 rows and 100 cols. */ - screen_info.orig_y = 37; - screen_info.orig_video_cols = 100; - screen_info.orig_video_lines = 37; + vgacon_screen_info.orig_y = 37; + vgacon_screen_info.orig_video_cols = 100; + vgacon_screen_info.orig_video_lines = 37; +#endif lca_init_arch(); } diff --git a/arch/alpha/kernel/syscalls/syscall.tbl b/arch/alpha/kernel/syscalls/syscall.tbl index 3515bc4f16a4..8ff110826ce2 100644 --- a/arch/alpha/kernel/syscalls/syscall.tbl +++ b/arch/alpha/kernel/syscalls/syscall.tbl @@ -125,8 +125,8 @@ 116 common osf_gettimeofday sys_osf_gettimeofday 117 common osf_getrusage sys_osf_getrusage 118 common getsockopt sys_getsockopt -120 common readv sys_osf_readv -121 common writev sys_osf_writev +120 common readv sys_readv +121 common writev sys_writev 122 common osf_settimeofday sys_osf_settimeofday 123 common fchown sys_fchown 124 common fchmod sys_fchmod @@ -334,7 +334,7 @@ 401 common io_submit sys_io_submit 402 common io_cancel sys_io_cancel 405 common exit_group sys_exit_group -406 common lookup_dcookie sys_lookup_dcookie +406 common lookup_dcookie sys_ni_syscall 407 common epoll_create sys_epoll_create 408 common epoll_ctl sys_epoll_ctl 409 common epoll_wait sys_epoll_wait @@ -490,3 +490,14 @@ 558 common process_mrelease sys_process_mrelease 559 common futex_waitv sys_futex_waitv 560 common set_mempolicy_home_node sys_ni_syscall +561 common cachestat sys_cachestat +562 common fchmodat2 sys_fchmodat2 +563 common map_shadow_stack sys_map_shadow_stack +564 common futex_wake sys_futex_wake +565 common futex_wait sys_futex_wait +566 common futex_requeue sys_futex_requeue +567 common statmount sys_statmount +568 common listmount sys_listmount +569 common lsm_get_self_attr sys_lsm_get_self_attr +570 common lsm_set_self_attr sys_lsm_set_self_attr +571 common lsm_list_modules sys_lsm_list_modules diff --git a/arch/alpha/kernel/termios.c b/arch/alpha/kernel/termios.c new file mode 100644 index 000000000000..a4c29a22edf7 --- /dev/null +++ b/arch/alpha/kernel/termios.c @@ -0,0 +1,56 @@ +// SPDX-License-Identifier: GPL-2.0 +#include <linux/termios_internal.h> + +int user_termio_to_kernel_termios(struct ktermios *termios, + struct termio __user *termio) +{ + struct termio v; + bool canon; + + if (copy_from_user(&v, termio, sizeof(struct termio))) + return -EFAULT; + + termios->c_iflag = (0xffff0000 & termios->c_iflag) | v.c_iflag; + termios->c_oflag = (0xffff0000 & termios->c_oflag) | v.c_oflag; + termios->c_cflag = (0xffff0000 & termios->c_cflag) | v.c_cflag; + termios->c_lflag = (0xffff0000 & termios->c_lflag) | v.c_lflag; + termios->c_line = (0xffff0000 & termios->c_lflag) | v.c_line; + + canon = v.c_lflag & ICANON; + termios->c_cc[VINTR] = v.c_cc[_VINTR]; + termios->c_cc[VQUIT] = v.c_cc[_VQUIT]; + termios->c_cc[VERASE] = v.c_cc[_VERASE]; + termios->c_cc[VKILL] = v.c_cc[_VKILL]; + termios->c_cc[VEOL2] = v.c_cc[_VEOL2]; + termios->c_cc[VSWTC] = v.c_cc[_VSWTC]; + termios->c_cc[canon ? VEOF : VMIN] = v.c_cc[_VEOF]; + termios->c_cc[canon ? VEOL : VTIME] = v.c_cc[_VEOL]; + + return 0; +} + +int kernel_termios_to_user_termio(struct termio __user *termio, + struct ktermios *termios) +{ + struct termio v; + bool canon; + + memset(&v, 0, sizeof(struct termio)); + v.c_iflag = termios->c_iflag; + v.c_oflag = termios->c_oflag; + v.c_cflag = termios->c_cflag; + v.c_lflag = termios->c_lflag; + v.c_line = termios->c_line; + + canon = v.c_lflag & ICANON; + v.c_cc[_VINTR] = termios->c_cc[VINTR]; + v.c_cc[_VQUIT] = termios->c_cc[VQUIT]; + v.c_cc[_VERASE] = termios->c_cc[VERASE]; + v.c_cc[_VKILL] = termios->c_cc[VKILL]; + v.c_cc[_VEOF] = termios->c_cc[canon ? VEOF : VMIN]; + v.c_cc[_VEOL] = termios->c_cc[canon ? VEOL : VTIME]; + v.c_cc[_VEOL2] = termios->c_cc[VEOL2]; + v.c_cc[_VSWTC] = termios->c_cc[VSWTC]; + + return copy_to_user(termio, &v, sizeof(struct termio)); +} diff --git a/arch/alpha/kernel/traps.c b/arch/alpha/kernel/traps.c index 8a66fe544c69..7fc72aeb7398 100644 --- a/arch/alpha/kernel/traps.c +++ b/arch/alpha/kernel/traps.c @@ -9,6 +9,7 @@ * This file initializes the trap entry points */ +#include <linux/cpu.h> #include <linux/jiffies.h> #include <linux/mm.h> #include <linux/sched/signal.h> @@ -233,7 +234,21 @@ do_entIF(unsigned long type, struct pt_regs *regs) { int signo, code; - if ((regs->ps & ~IPL_MAX) == 0) { + if (type == 3) { /* FEN fault */ + /* Irritating users can call PAL_clrfen to disable the + FPU for the process. The kernel will then trap in + do_switch_stack and undo_switch_stack when we try + to save and restore the FP registers. + + Given that GCC by default generates code that uses the + FP registers, PAL_clrfen is not useful except for DoS + attacks. So turn the bleeding FPU back on and be done + with it. */ + current_thread_info()->pcb.flags |= 1; + __reload_thread(¤t_thread_info()->pcb); + return; + } + if (!user_mode(regs)) { if (type == 1) { const unsigned int *data = (const unsigned int *) regs->pc; @@ -366,20 +381,6 @@ do_entIF(unsigned long type, struct pt_regs *regs) } break; - case 3: /* FEN fault */ - /* Irritating users can call PAL_clrfen to disable the - FPU for the process. The kernel will then trap in - do_switch_stack and undo_switch_stack when we try - to save and restore the FP registers. - - Given that GCC by default generates code that uses the - FP registers, PAL_clrfen is not useful except for DoS - attacks. So turn the bleeding FPU back on and be done - with it. */ - current_thread_info()->pcb.flags |= 1; - __reload_thread(¤t_thread_info()->pcb); - return; - case 5: /* illoc */ default: /* unexpected instruction-fault type */ ; diff --git a/arch/alpha/kernel/vmlinux.lds.S b/arch/alpha/kernel/vmlinux.lds.S index 5b78d640725d..2efa7dfc798a 100644 --- a/arch/alpha/kernel/vmlinux.lds.S +++ b/arch/alpha/kernel/vmlinux.lds.S @@ -27,7 +27,6 @@ SECTIONS HEAD_TEXT TEXT_TEXT SCHED_TEXT - CPUIDLE_TEXT LOCK_TEXT *(.fixup) *(.gnu.warning) diff --git a/arch/alpha/lib/Makefile b/arch/alpha/lib/Makefile index 1cc74f7b50ef..6a779b9018fd 100644 --- a/arch/alpha/lib/Makefile +++ b/arch/alpha/lib/Makefile @@ -4,7 +4,6 @@ # asflags-y := $(KBUILD_CFLAGS) -ccflags-y := -Werror # Many of these routines have implementations tuned for ev6. # Choose them iff we're targeting ev6 specifically. diff --git a/arch/alpha/lib/callback_srm.S b/arch/alpha/lib/callback_srm.S index b13c4a231f1b..36b63f295170 100644 --- a/arch/alpha/lib/callback_srm.S +++ b/arch/alpha/lib/callback_srm.S @@ -3,8 +3,8 @@ * arch/alpha/lib/callback_srm.S */ +#include <linux/export.h> #include <asm/console.h> -#include <asm/export.h> .text #define HWRPB_CRB_OFFSET 0xc0 diff --git a/arch/alpha/lib/clear_page.S b/arch/alpha/lib/clear_page.S index ce02de7b0493..af70ee309a33 100644 --- a/arch/alpha/lib/clear_page.S +++ b/arch/alpha/lib/clear_page.S @@ -4,7 +4,7 @@ * * Zero an entire page. */ -#include <asm/export.h> +#include <linux/export.h> .text .align 4 .global clear_page diff --git a/arch/alpha/lib/clear_user.S b/arch/alpha/lib/clear_user.S index db6c6ca45896..848eb60a0010 100644 --- a/arch/alpha/lib/clear_user.S +++ b/arch/alpha/lib/clear_user.S @@ -10,7 +10,7 @@ * a successful copy). There is also some rather minor exception setup * stuff. */ -#include <asm/export.h> +#include <linux/export.h> /* Allow an exception for an insn; exit if we get one. */ #define EX(x,y...) \ diff --git a/arch/alpha/lib/copy_page.S b/arch/alpha/lib/copy_page.S index 5439a30c77d0..1c444fdad9a5 100644 --- a/arch/alpha/lib/copy_page.S +++ b/arch/alpha/lib/copy_page.S @@ -4,7 +4,7 @@ * * Copy an entire page. */ -#include <asm/export.h> +#include <linux/export.h> .text .align 4 .global copy_page diff --git a/arch/alpha/lib/copy_user.S b/arch/alpha/lib/copy_user.S index 32ab0344b185..ef18faafcad6 100644 --- a/arch/alpha/lib/copy_user.S +++ b/arch/alpha/lib/copy_user.S @@ -12,7 +12,7 @@ * exception setup stuff.. */ -#include <asm/export.h> +#include <linux/export.h> /* Allow an exception for an insn; exit if we get one. */ #define EXI(x,y...) \ diff --git a/arch/alpha/lib/csum_ipv6_magic.S b/arch/alpha/lib/csum_ipv6_magic.S index c7b213ab01ab..273c426c3859 100644 --- a/arch/alpha/lib/csum_ipv6_magic.S +++ b/arch/alpha/lib/csum_ipv6_magic.S @@ -13,7 +13,7 @@ * added by Ivan Kokshaysky <ink@jurassic.park.msu.ru> */ -#include <asm/export.h> +#include <linux/export.h> .globl csum_ipv6_magic .align 4 .ent csum_ipv6_magic diff --git a/arch/alpha/lib/divide.S b/arch/alpha/lib/divide.S index 2b60eb45e50b..db01840d76ec 100644 --- a/arch/alpha/lib/divide.S +++ b/arch/alpha/lib/divide.S @@ -46,7 +46,7 @@ * $28 - compare status */ -#include <asm/export.h> +#include <linux/export.h> #define halt .long 0 /* diff --git a/arch/alpha/lib/ev6-clear_page.S b/arch/alpha/lib/ev6-clear_page.S index 325864c81586..a534d9ff7161 100644 --- a/arch/alpha/lib/ev6-clear_page.S +++ b/arch/alpha/lib/ev6-clear_page.S @@ -4,7 +4,7 @@ * * Zero an entire page. */ -#include <asm/export.h> +#include <linux/export.h> .text .align 4 .global clear_page diff --git a/arch/alpha/lib/ev6-clear_user.S b/arch/alpha/lib/ev6-clear_user.S index 7e644f83cdf2..af776cc45f91 100644 --- a/arch/alpha/lib/ev6-clear_user.S +++ b/arch/alpha/lib/ev6-clear_user.S @@ -29,7 +29,7 @@ * want to leave a hole (and we also want to avoid repeating lots of work) */ -#include <asm/export.h> +#include <linux/export.h> /* Allow an exception for an insn; exit if we get one. */ #define EX(x,y...) \ 99: x,##y; \ diff --git a/arch/alpha/lib/ev6-copy_page.S b/arch/alpha/lib/ev6-copy_page.S index fd7212c8dcf1..36be5113b7b7 100644 --- a/arch/alpha/lib/ev6-copy_page.S +++ b/arch/alpha/lib/ev6-copy_page.S @@ -57,7 +57,7 @@ destination pages are in the dcache, but it is my guess that this is less important than the dcache miss case. */ -#include <asm/export.h> +#include <linux/export.h> .text .align 4 .global copy_page diff --git a/arch/alpha/lib/ev6-copy_user.S b/arch/alpha/lib/ev6-copy_user.S index f3e433754397..b9b19710c364 100644 --- a/arch/alpha/lib/ev6-copy_user.S +++ b/arch/alpha/lib/ev6-copy_user.S @@ -23,7 +23,7 @@ * L - lower subcluster; L0 - subcluster L0; L1 - subcluster L1 */ -#include <asm/export.h> +#include <linux/export.h> /* Allow an exception for an insn; exit if we get one. */ #define EXI(x,y...) \ 99: x,##y; \ diff --git a/arch/alpha/lib/ev6-csum_ipv6_magic.S b/arch/alpha/lib/ev6-csum_ipv6_magic.S index 9a73f90700a1..2ee548be98e3 100644 --- a/arch/alpha/lib/ev6-csum_ipv6_magic.S +++ b/arch/alpha/lib/ev6-csum_ipv6_magic.S @@ -53,7 +53,7 @@ * may cause additional delay in rare cases (load-load replay traps). */ -#include <asm/export.h> +#include <linux/export.h> .globl csum_ipv6_magic .align 4 .ent csum_ipv6_magic diff --git a/arch/alpha/lib/ev6-divide.S b/arch/alpha/lib/ev6-divide.S index 137ff1a07356..b73a6d26362e 100644 --- a/arch/alpha/lib/ev6-divide.S +++ b/arch/alpha/lib/ev6-divide.S @@ -56,7 +56,7 @@ * Try not to change the actual algorithm if possible for consistency. */ -#include <asm/export.h> +#include <linux/export.h> #define halt .long 0 /* diff --git a/arch/alpha/lib/ev6-memchr.S b/arch/alpha/lib/ev6-memchr.S index 56bf9e14eeee..f75ba43e61e3 100644 --- a/arch/alpha/lib/ev6-memchr.S +++ b/arch/alpha/lib/ev6-memchr.S @@ -28,7 +28,7 @@ * L - lower subcluster; L0 - subcluster L0; L1 - subcluster L1 * Try not to change the actual algorithm if possible for consistency. */ -#include <asm/export.h> +#include <linux/export.h> .set noreorder .set noat diff --git a/arch/alpha/lib/ev6-memcpy.S b/arch/alpha/lib/ev6-memcpy.S index ffbd056b6eb2..3ef43c26c8af 100644 --- a/arch/alpha/lib/ev6-memcpy.S +++ b/arch/alpha/lib/ev6-memcpy.S @@ -20,7 +20,7 @@ * Temp usage notes: * $1,$2, - scratch */ -#include <asm/export.h> +#include <linux/export.h> .set noreorder .set noat diff --git a/arch/alpha/lib/ev6-memset.S b/arch/alpha/lib/ev6-memset.S index 1cfcfbbea6f0..89d7809da4cc 100644 --- a/arch/alpha/lib/ev6-memset.S +++ b/arch/alpha/lib/ev6-memset.S @@ -27,7 +27,7 @@ * as fixes will need to be made in multiple places. The performance gain * is worth it. */ -#include <asm/export.h> +#include <linux/export.h> .set noat .set noreorder .text diff --git a/arch/alpha/lib/ev67-strcat.S b/arch/alpha/lib/ev67-strcat.S index ec3096a9e8d4..f8c7305b11d6 100644 --- a/arch/alpha/lib/ev67-strcat.S +++ b/arch/alpha/lib/ev67-strcat.S @@ -20,7 +20,7 @@ * string once. */ -#include <asm/export.h> +#include <linux/export.h> .text .align 4 diff --git a/arch/alpha/lib/ev67-strchr.S b/arch/alpha/lib/ev67-strchr.S index fbf89e0b6dc3..97a7cb475309 100644 --- a/arch/alpha/lib/ev67-strchr.S +++ b/arch/alpha/lib/ev67-strchr.S @@ -16,7 +16,7 @@ * L - lower subcluster; L0 - subcluster L0; L1 - subcluster L1 * Try not to change the actual algorithm if possible for consistency. */ -#include <asm/export.h> +#include <linux/export.h> #include <asm/regdef.h> .set noreorder diff --git a/arch/alpha/lib/ev67-strlen.S b/arch/alpha/lib/ev67-strlen.S index b73106ffbbc7..3d9078807ab4 100644 --- a/arch/alpha/lib/ev67-strlen.S +++ b/arch/alpha/lib/ev67-strlen.S @@ -18,7 +18,7 @@ * U - upper subcluster; U0 - subcluster U0; U1 - subcluster U1 * L - lower subcluster; L0 - subcluster L0; L1 - subcluster L1 */ -#include <asm/export.h> +#include <linux/export.h> .set noreorder .set noat diff --git a/arch/alpha/lib/ev67-strncat.S b/arch/alpha/lib/ev67-strncat.S index ceb0ca528789..8f313233e3a7 100644 --- a/arch/alpha/lib/ev67-strncat.S +++ b/arch/alpha/lib/ev67-strncat.S @@ -21,7 +21,7 @@ * Try not to change the actual algorithm if possible for consistency. */ -#include <asm/export.h> +#include <linux/export.h> .text .align 4 diff --git a/arch/alpha/lib/ev67-strrchr.S b/arch/alpha/lib/ev67-strrchr.S index 7f80e398530f..ae7355f9ec56 100644 --- a/arch/alpha/lib/ev67-strrchr.S +++ b/arch/alpha/lib/ev67-strrchr.S @@ -19,7 +19,7 @@ * L - lower subcluster; L0 - subcluster L0; L1 - subcluster L1 */ -#include <asm/export.h> +#include <linux/export.h> #include <asm/regdef.h> .set noreorder diff --git a/arch/alpha/lib/fpreg.c b/arch/alpha/lib/fpreg.c index 34fea465645b..7c08b225261c 100644 --- a/arch/alpha/lib/fpreg.c +++ b/arch/alpha/lib/fpreg.c @@ -7,6 +7,8 @@ #include <linux/compiler.h> #include <linux/export.h> +#include <linux/preempt.h> +#include <asm/thread_info.h> #if defined(CONFIG_ALPHA_EV6) || defined(CONFIG_ALPHA_EV67) #define STT(reg,val) asm volatile ("ftoit $f"#reg",%0" : "=r"(val)); @@ -19,7 +21,12 @@ alpha_read_fp_reg (unsigned long reg) { unsigned long val; - switch (reg) { + if (unlikely(reg >= 32)) + return 0; + preempt_disable(); + if (current_thread_info()->status & TS_SAVED_FP) + val = current_thread_info()->fp[reg]; + else switch (reg) { case 0: STT( 0, val); break; case 1: STT( 1, val); break; case 2: STT( 2, val); break; @@ -52,8 +59,8 @@ alpha_read_fp_reg (unsigned long reg) case 29: STT(29, val); break; case 30: STT(30, val); break; case 31: STT(31, val); break; - default: return 0; } + preempt_enable(); return val; } EXPORT_SYMBOL(alpha_read_fp_reg); @@ -67,7 +74,14 @@ EXPORT_SYMBOL(alpha_read_fp_reg); void alpha_write_fp_reg (unsigned long reg, unsigned long val) { - switch (reg) { + if (unlikely(reg >= 32)) + return; + + preempt_disable(); + if (current_thread_info()->status & TS_SAVED_FP) { + current_thread_info()->status |= TS_RESTORE_FP; + current_thread_info()->fp[reg] = val; + } else switch (reg) { case 0: LDT( 0, val); break; case 1: LDT( 1, val); break; case 2: LDT( 2, val); break; @@ -101,6 +115,7 @@ alpha_write_fp_reg (unsigned long reg, unsigned long val) case 30: LDT(30, val); break; case 31: LDT(31, val); break; } + preempt_enable(); } EXPORT_SYMBOL(alpha_write_fp_reg); @@ -115,7 +130,14 @@ alpha_read_fp_reg_s (unsigned long reg) { unsigned long val; - switch (reg) { + if (unlikely(reg >= 32)) + return 0; + + preempt_disable(); + if (current_thread_info()->status & TS_SAVED_FP) { + LDT(0, current_thread_info()->fp[reg]); + STS(0, val); + } else switch (reg) { case 0: STS( 0, val); break; case 1: STS( 1, val); break; case 2: STS( 2, val); break; @@ -148,8 +170,8 @@ alpha_read_fp_reg_s (unsigned long reg) case 29: STS(29, val); break; case 30: STS(30, val); break; case 31: STS(31, val); break; - default: return 0; } + preempt_enable(); return val; } EXPORT_SYMBOL(alpha_read_fp_reg_s); @@ -163,7 +185,15 @@ EXPORT_SYMBOL(alpha_read_fp_reg_s); void alpha_write_fp_reg_s (unsigned long reg, unsigned long val) { - switch (reg) { + if (unlikely(reg >= 32)) + return; + + preempt_disable(); + if (current_thread_info()->status & TS_SAVED_FP) { + current_thread_info()->status |= TS_RESTORE_FP; + LDS(0, val); + STT(0, current_thread_info()->fp[reg]); + } else switch (reg) { case 0: LDS( 0, val); break; case 1: LDS( 1, val); break; case 2: LDS( 2, val); break; @@ -197,5 +227,6 @@ alpha_write_fp_reg_s (unsigned long reg, unsigned long val) case 30: LDS(30, val); break; case 31: LDS(31, val); break; } + preempt_enable(); } EXPORT_SYMBOL(alpha_write_fp_reg_s); diff --git a/arch/alpha/lib/memchr.S b/arch/alpha/lib/memchr.S index c13d3eca2e05..45366e32feee 100644 --- a/arch/alpha/lib/memchr.S +++ b/arch/alpha/lib/memchr.S @@ -31,7 +31,7 @@ For correctness consider that: - only minimum number of quadwords may be accessed - the third argument is an unsigned long */ -#include <asm/export.h> +#include <linux/export.h> .set noreorder .set noat diff --git a/arch/alpha/lib/memmove.S b/arch/alpha/lib/memmove.S index 42d1922d0edf..3a27689e3390 100644 --- a/arch/alpha/lib/memmove.S +++ b/arch/alpha/lib/memmove.S @@ -7,7 +7,7 @@ * This is hand-massaged output from the original memcpy.c. We defer to * memcpy whenever possible; the backwards copy loops are not unrolled. */ -#include <asm/export.h> +#include <linux/export.h> .set noat .set noreorder .text diff --git a/arch/alpha/lib/memset.S b/arch/alpha/lib/memset.S index 00393e30df25..9075d6918346 100644 --- a/arch/alpha/lib/memset.S +++ b/arch/alpha/lib/memset.S @@ -14,7 +14,7 @@ * The scheduling comments are according to the EV5 documentation (and done by * hand, so they might well be incorrect, please do tell me about it..) */ -#include <asm/export.h> +#include <linux/export.h> .set noat .set noreorder .text diff --git a/arch/alpha/lib/stacktrace.c b/arch/alpha/lib/stacktrace.c index 62454a7810e2..2b1176dd5174 100644 --- a/arch/alpha/lib/stacktrace.c +++ b/arch/alpha/lib/stacktrace.c @@ -92,7 +92,7 @@ stacktrace(void) { instr * ret_pc; instr * prologue = (instr *)stacktrace; - register unsigned char * sp __asm__ ("$30"); + unsigned char *sp = (unsigned char *)current_stack_pointer; printk("\tstack trace:\n"); do { diff --git a/arch/alpha/lib/strcat.S b/arch/alpha/lib/strcat.S index 055877dccd27..62b90ebbcf44 100644 --- a/arch/alpha/lib/strcat.S +++ b/arch/alpha/lib/strcat.S @@ -5,7 +5,7 @@ * * Append a null-terminated string from SRC to DST. */ -#include <asm/export.h> +#include <linux/export.h> .text diff --git a/arch/alpha/lib/strchr.S b/arch/alpha/lib/strchr.S index 17871dd00280..68c54ff50dfe 100644 --- a/arch/alpha/lib/strchr.S +++ b/arch/alpha/lib/strchr.S @@ -6,7 +6,7 @@ * Return the address of a given character within a null-terminated * string, or null if it is not found. */ -#include <asm/export.h> +#include <linux/export.h> #include <asm/regdef.h> .set noreorder diff --git a/arch/alpha/lib/strcpy.S b/arch/alpha/lib/strcpy.S index cb74ad23a90d..d8773ba77525 100644 --- a/arch/alpha/lib/strcpy.S +++ b/arch/alpha/lib/strcpy.S @@ -6,7 +6,7 @@ * Copy a null-terminated string from SRC to DST. Return a pointer * to the null-terminator in the source. */ -#include <asm/export.h> +#include <linux/export.h> .text .align 3 diff --git a/arch/alpha/lib/strlen.S b/arch/alpha/lib/strlen.S index dd882fe4d7e3..4fc6a6ff24cd 100644 --- a/arch/alpha/lib/strlen.S +++ b/arch/alpha/lib/strlen.S @@ -12,7 +12,7 @@ * do this instead of the 9 instructions that * binary search needs). */ -#include <asm/export.h> +#include <linux/export.h> .set noreorder .set noat diff --git a/arch/alpha/lib/strncat.S b/arch/alpha/lib/strncat.S index 522fee3e26ac..a913a7c84a39 100644 --- a/arch/alpha/lib/strncat.S +++ b/arch/alpha/lib/strncat.S @@ -10,7 +10,7 @@ * past count, whereas libc may write to count+1. This follows the generic * implementation in lib/string.c and is, IMHO, more sensible. */ -#include <asm/export.h> +#include <linux/export.h> .text .align 3 diff --git a/arch/alpha/lib/strncpy.S b/arch/alpha/lib/strncpy.S index cc57fad8b7ca..cb90cf022df3 100644 --- a/arch/alpha/lib/strncpy.S +++ b/arch/alpha/lib/strncpy.S @@ -11,7 +11,7 @@ * version has cropped that bit o' nastiness as well as assuming that * __stxncpy is in range of a branch. */ -#include <asm/export.h> +#include <linux/export.h> .set noat .set noreorder diff --git a/arch/alpha/lib/strrchr.S b/arch/alpha/lib/strrchr.S index 7650ba99b7e2..dd8e073b6cf2 100644 --- a/arch/alpha/lib/strrchr.S +++ b/arch/alpha/lib/strrchr.S @@ -6,7 +6,7 @@ * Return the address of the last occurrence of a given character * within a null-terminated string, or null if it is not found. */ -#include <asm/export.h> +#include <linux/export.h> #include <asm/regdef.h> .set noreorder diff --git a/arch/alpha/lib/udiv-qrnnd.S b/arch/alpha/lib/udiv-qrnnd.S index b887aa5428e5..96f05918bffe 100644 --- a/arch/alpha/lib/udiv-qrnnd.S +++ b/arch/alpha/lib/udiv-qrnnd.S @@ -25,7 +25,7 @@ # along with GCC; see the file COPYING. If not, write to the # Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, # MA 02111-1307, USA. -#include <asm/export.h> +#include <linux/export.h> .set noreorder .set noat diff --git a/arch/alpha/mm/Makefile b/arch/alpha/mm/Makefile index bd770302eb82..101dbd06b4ce 100644 --- a/arch/alpha/mm/Makefile +++ b/arch/alpha/mm/Makefile @@ -3,6 +3,4 @@ # Makefile for the linux alpha-specific parts of the memory manager. # -ccflags-y := -Werror - obj-y := init.o fault.o diff --git a/arch/alpha/mm/fault.c b/arch/alpha/mm/fault.c index ec20c1004abf..8c9850437e67 100644 --- a/arch/alpha/mm/fault.c +++ b/arch/alpha/mm/fault.c @@ -119,20 +119,12 @@ do_page_fault(unsigned long address, unsigned long mmcsr, flags |= FAULT_FLAG_USER; perf_sw_event(PERF_COUNT_SW_PAGE_FAULTS, 1, regs, address); retry: - mmap_read_lock(mm); - vma = find_vma(mm, address); + vma = lock_mm_and_find_vma(mm, address, regs); if (!vma) - goto bad_area; - if (vma->vm_start <= address) - goto good_area; - if (!(vma->vm_flags & VM_GROWSDOWN)) - goto bad_area; - if (expand_stack(vma, address)) - goto bad_area; + goto bad_area_nosemaphore; /* Ok, we have a good vm_area for this memory access, so we can handle it. */ - good_area: si_code = SEGV_ACCERR; if (cause < 0) { if (!(vma->vm_flags & VM_EXEC)) @@ -152,7 +144,14 @@ retry: the fault. */ fault = handle_mm_fault(vma, address, flags, regs); - if (fault_signal_pending(fault, regs)) + if (fault_signal_pending(fault, regs)) { + if (!user_mode(regs)) + goto no_context; + return; + } + + /* The fault is fully completed (including releasing mmap lock) */ + if (fault & VM_FAULT_COMPLETED) return; if (unlikely(fault & VM_FAULT_ERROR)) { @@ -185,6 +184,7 @@ retry: bad_area: mmap_read_unlock(mm); + bad_area_nosemaphore: if (user_mode(regs)) goto do_sigsegv; diff --git a/arch/alpha/mm/init.c b/arch/alpha/mm/init.c index 7511723b7669..a155180d7a83 100644 --- a/arch/alpha/mm/init.c +++ b/arch/alpha/mm/init.c @@ -280,3 +280,25 @@ mem_init(void) high_memory = (void *) __va(max_low_pfn * PAGE_SIZE); memblock_free_all(); } + +static const pgprot_t protection_map[16] = { + [VM_NONE] = _PAGE_P(_PAGE_FOE | _PAGE_FOW | + _PAGE_FOR), + [VM_READ] = _PAGE_P(_PAGE_FOE | _PAGE_FOW), + [VM_WRITE] = _PAGE_P(_PAGE_FOE), + [VM_WRITE | VM_READ] = _PAGE_P(_PAGE_FOE), + [VM_EXEC] = _PAGE_P(_PAGE_FOW | _PAGE_FOR), + [VM_EXEC | VM_READ] = _PAGE_P(_PAGE_FOW), + [VM_EXEC | VM_WRITE] = _PAGE_P(0), + [VM_EXEC | VM_WRITE | VM_READ] = _PAGE_P(0), + [VM_SHARED] = _PAGE_S(_PAGE_FOE | _PAGE_FOW | + _PAGE_FOR), + [VM_SHARED | VM_READ] = _PAGE_S(_PAGE_FOE | _PAGE_FOW), + [VM_SHARED | VM_WRITE] = _PAGE_S(_PAGE_FOE), + [VM_SHARED | VM_WRITE | VM_READ] = _PAGE_S(_PAGE_FOE), + [VM_SHARED | VM_EXEC] = _PAGE_S(_PAGE_FOW | _PAGE_FOR), + [VM_SHARED | VM_EXEC | VM_READ] = _PAGE_S(_PAGE_FOW), + [VM_SHARED | VM_EXEC | VM_WRITE] = _PAGE_S(0), + [VM_SHARED | VM_EXEC | VM_WRITE | VM_READ] = _PAGE_S(0) +}; +DECLARE_VM_GET_PAGE_PROT |