From cff2b760096d1e6feaa31948e7af4abbefe47822 Mon Sep 17 00:00:00 2001 From: Ulrich Drepper Date: Sat, 11 Feb 2006 17:55:47 -0800 Subject: [PATCH 01/48] [PATCH] fstatat64 support The *at patches introduced fstatat and, due to inusfficient research, I used the newfstat functions generally as the guideline. The result is that on 32-bit platforms we don't have all the information needed to implement fstatat64. This patch modifies the code to pass up 64-bit information if __ARCH_WANT_STAT64 is defined. I renamed the syscall entry point to make this clear. Other archs will continue to use the existing code. On x86-64 the compat code is implemented using a new sys32_ function. this is what is done for the other stat syscalls as well. This patch might break some other archs (those which define __ARCH_WANT_STAT64 and which already wired up the syscall). Yet others might need changes to accomodate the compatibility mode. I really don't want to do that work because all this stat handling is a mess (more so in glibc, but the kernel is also affected). It should be done by the arch maintainers. I'll provide some stand-alone test shortly. Those who are eager could compile glibc and run 'make check' (no installation needed). The patch below has been tested on x86 and x86-64. Signed-off-by: Ulrich Drepper Cc: Christoph Hellwig Cc: Andi Kleen Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- arch/i386/kernel/syscall_table.S | 2 +- arch/x86_64/ia32/ia32entry.S | 2 +- arch/x86_64/ia32/sys_ia32.c | 22 ++++++++++++++++++++++ fs/stat.c | 22 ++++++++++++++++++++++ include/asm-i386/unistd.h | 2 +- include/asm-x86_64/ia32_unistd.h | 2 +- include/linux/syscalls.h | 2 ++ 7 files changed, 50 insertions(+), 4 deletions(-) diff --git a/arch/i386/kernel/syscall_table.S b/arch/i386/kernel/syscall_table.S index 5a8b3fb6d27b..ac687d00a1ce 100644 --- a/arch/i386/kernel/syscall_table.S +++ b/arch/i386/kernel/syscall_table.S @@ -299,7 +299,7 @@ ENTRY(sys_call_table) .long sys_mknodat .long sys_fchownat .long sys_futimesat - .long sys_newfstatat /* 300 */ + .long sys_fstatat64 /* 300 */ .long sys_unlinkat .long sys_renameat .long sys_linkat diff --git a/arch/x86_64/ia32/ia32entry.S b/arch/x86_64/ia32/ia32entry.S index ada4535d0161..00dee176c08e 100644 --- a/arch/x86_64/ia32/ia32entry.S +++ b/arch/x86_64/ia32/ia32entry.S @@ -677,7 +677,7 @@ ia32_sys_call_table: .quad sys_mknodat .quad sys_fchownat .quad compat_sys_futimesat - .quad compat_sys_newfstatat /* 300 */ + .quad sys32_fstatat /* 300 */ .quad sys_unlinkat .quad sys_renameat .quad sys_linkat diff --git a/arch/x86_64/ia32/sys_ia32.c b/arch/x86_64/ia32/sys_ia32.c index 54481af5344a..2bc55af95419 100644 --- a/arch/x86_64/ia32/sys_ia32.c +++ b/arch/x86_64/ia32/sys_ia32.c @@ -180,6 +180,28 @@ sys32_fstat64(unsigned int fd, struct stat64 __user *statbuf) return ret; } +asmlinkage long +sys32_fstatat(unsigned int dfd, char __user *filename, + struct stat64 __user* statbuf, int flag) +{ + struct kstat stat; + int error = -EINVAL; + + if ((flag & ~AT_SYMLINK_NOFOLLOW) != 0) + goto out; + + if (flag & AT_SYMLINK_NOFOLLOW) + error = vfs_lstat_fd(dfd, filename, &stat); + else + error = vfs_stat_fd(dfd, filename, &stat); + + if (!error) + error = cp_stat64(statbuf, &stat); + +out: + return error; +} + /* * Linux/i386 didn't use to be able to handle more than * 4 system call parameters, so these system calls used a memory diff --git a/fs/stat.c b/fs/stat.c index 24211b030f39..9948cc1685a4 100644 --- a/fs/stat.c +++ b/fs/stat.c @@ -261,6 +261,7 @@ asmlinkage long sys_newlstat(char __user *filename, struct stat __user *statbuf) return error; } +#ifndef __ARCH_WANT_STAT64 asmlinkage long sys_newfstatat(int dfd, char __user *filename, struct stat __user *statbuf, int flag) { @@ -281,6 +282,7 @@ asmlinkage long sys_newfstatat(int dfd, char __user *filename, out: return error; } +#endif asmlinkage long sys_newfstat(unsigned int fd, struct stat __user *statbuf) { @@ -395,6 +397,26 @@ asmlinkage long sys_fstat64(unsigned long fd, struct stat64 __user * statbuf) return error; } +asmlinkage long sys_fstatat64(int dfd, char __user *filename, + struct stat64 __user *statbuf, int flag) +{ + struct kstat stat; + int error = -EINVAL; + + if ((flag & ~AT_SYMLINK_NOFOLLOW) != 0) + goto out; + + if (flag & AT_SYMLINK_NOFOLLOW) + error = vfs_lstat_fd(dfd, filename, &stat); + else + error = vfs_stat_fd(dfd, filename, &stat); + + if (!error) + error = cp_new_stat64(&stat, statbuf); + +out: + return error; +} #endif /* __ARCH_WANT_STAT64 */ void inode_add_bytes(struct inode *inode, loff_t bytes) diff --git a/include/asm-i386/unistd.h b/include/asm-i386/unistd.h index cf6f2cd9c514..dc81a55dd94d 100644 --- a/include/asm-i386/unistd.h +++ b/include/asm-i386/unistd.h @@ -305,7 +305,7 @@ #define __NR_mknodat 297 #define __NR_fchownat 298 #define __NR_futimesat 299 -#define __NR_newfstatat 300 +#define __NR_fstatat64 300 #define __NR_unlinkat 301 #define __NR_renameat 302 #define __NR_linkat 303 diff --git a/include/asm-x86_64/ia32_unistd.h b/include/asm-x86_64/ia32_unistd.h index 20468983d453..eeb2bcd635de 100644 --- a/include/asm-x86_64/ia32_unistd.h +++ b/include/asm-x86_64/ia32_unistd.h @@ -305,7 +305,7 @@ #define __NR_ia32_mknodat 297 #define __NR_ia32_fchownat 298 #define __NR_ia32_futimesat 299 -#define __NR_ia32_newfstatat 300 +#define __NR_ia32_fstatat64 300 #define __NR_ia32_unlinkat 301 #define __NR_ia32_renameat 302 #define __NR_ia32_linkat 303 diff --git a/include/linux/syscalls.h b/include/linux/syscalls.h index 3877209d23c3..d73501ba7e44 100644 --- a/include/linux/syscalls.h +++ b/include/linux/syscalls.h @@ -557,6 +557,8 @@ asmlinkage long sys_openat(int dfd, const char __user *filename, int flags, int mode); asmlinkage long sys_newfstatat(int dfd, char __user *filename, struct stat __user *statbuf, int flag); +asmlinkage long sys_fstatat64(int dfd, char __user *filename, + struct stat64 __user *statbuf, int flag); asmlinkage long sys_readlinkat(int dfd, const char __user *path, char __user *buf, int bufsiz); asmlinkage long compat_sys_futimesat(unsigned int dfd, char __user *filename, From e00d82d07fb112446586d225763d3572e64b7abf Mon Sep 17 00:00:00 2001 From: Matt Waddel Date: Sat, 11 Feb 2006 17:55:48 -0800 Subject: [PATCH 02/48] [PATCH] Add wording to m68k .S files to help clarify license info Acked-by: Alan Cox Signed-off-by: Matt Waddel Cc: Roman Zippel Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- arch/m68k/fpsp040/bindec.S | 5 ++--- arch/m68k/fpsp040/binstr.S | 5 ++--- arch/m68k/fpsp040/bugfix.S | 5 ++--- arch/m68k/fpsp040/decbin.S | 5 ++--- arch/m68k/fpsp040/do_func.S | 5 ++--- arch/m68k/fpsp040/fpsp.h | 5 ++--- arch/m68k/fpsp040/gen_except.S | 5 ++--- arch/m68k/fpsp040/get_op.S | 5 ++--- arch/m68k/fpsp040/kernel_ex.S | 5 ++--- arch/m68k/fpsp040/res_func.S | 5 ++--- arch/m68k/fpsp040/round.S | 5 ++--- arch/m68k/fpsp040/sacos.S | 5 ++--- arch/m68k/fpsp040/sasin.S | 5 ++--- arch/m68k/fpsp040/satan.S | 5 ++--- arch/m68k/fpsp040/satanh.S | 5 ++--- arch/m68k/fpsp040/scale.S | 5 ++--- arch/m68k/fpsp040/scosh.S | 5 ++--- arch/m68k/fpsp040/setox.S | 5 ++--- arch/m68k/fpsp040/sgetem.S | 5 ++--- arch/m68k/fpsp040/sint.S | 5 ++--- arch/m68k/fpsp040/skeleton.S | 5 ++--- arch/m68k/fpsp040/slog2.S | 5 ++--- arch/m68k/fpsp040/slogn.S | 5 ++--- arch/m68k/fpsp040/smovecr.S | 5 ++--- arch/m68k/fpsp040/srem_mod.S | 5 ++--- arch/m68k/fpsp040/ssin.S | 5 ++--- arch/m68k/fpsp040/ssinh.S | 5 ++--- arch/m68k/fpsp040/stan.S | 5 ++--- arch/m68k/fpsp040/stanh.S | 5 ++--- arch/m68k/fpsp040/sto_res.S | 5 ++--- arch/m68k/fpsp040/stwotox.S | 5 ++--- arch/m68k/fpsp040/tbldo.S | 5 ++--- arch/m68k/fpsp040/util.S | 5 ++--- arch/m68k/fpsp040/x_bsun.S | 5 ++--- arch/m68k/fpsp040/x_fline.S | 5 ++--- arch/m68k/fpsp040/x_operr.S | 5 ++--- arch/m68k/fpsp040/x_ovfl.S | 5 ++--- arch/m68k/fpsp040/x_snan.S | 5 ++--- arch/m68k/fpsp040/x_store.S | 5 ++--- arch/m68k/fpsp040/x_unfl.S | 5 ++--- arch/m68k/fpsp040/x_unimp.S | 5 ++--- arch/m68k/fpsp040/x_unsupp.S | 5 ++--- 42 files changed, 84 insertions(+), 126 deletions(-) diff --git a/arch/m68k/fpsp040/bindec.S b/arch/m68k/fpsp040/bindec.S index 3ba446a99a12..72f1159cb804 100644 --- a/arch/m68k/fpsp040/bindec.S +++ b/arch/m68k/fpsp040/bindec.S @@ -131,9 +131,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. |BINDEC idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/binstr.S b/arch/m68k/fpsp040/binstr.S index d53555c0a2b6..8a05ba92a8a0 100644 --- a/arch/m68k/fpsp040/binstr.S +++ b/arch/m68k/fpsp040/binstr.S @@ -60,9 +60,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. |BINSTR idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/bugfix.S b/arch/m68k/fpsp040/bugfix.S index 942c4f6f4fd1..3bb9c84bb058 100644 --- a/arch/m68k/fpsp040/bugfix.S +++ b/arch/m68k/fpsp040/bugfix.S @@ -152,9 +152,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. |BUGFIX idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/decbin.S b/arch/m68k/fpsp040/decbin.S index 2160609e328d..16ed796bad87 100644 --- a/arch/m68k/fpsp040/decbin.S +++ b/arch/m68k/fpsp040/decbin.S @@ -69,9 +69,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. |DECBIN idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/do_func.S b/arch/m68k/fpsp040/do_func.S index 81f6a9856dce..3eff99a80413 100644 --- a/arch/m68k/fpsp040/do_func.S +++ b/arch/m68k/fpsp040/do_func.S @@ -22,9 +22,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. DO_FUNC: |idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/fpsp.h b/arch/m68k/fpsp040/fpsp.h index 984a4eb8010a..5df4cd772934 100644 --- a/arch/m68k/fpsp040/fpsp.h +++ b/arch/m68k/fpsp040/fpsp.h @@ -5,9 +5,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. | fpsp.h --- stack frame offsets during FPSP exception handling | diff --git a/arch/m68k/fpsp040/gen_except.S b/arch/m68k/fpsp040/gen_except.S index 401d06f39f73..3642cb7e3641 100644 --- a/arch/m68k/fpsp040/gen_except.S +++ b/arch/m68k/fpsp040/gen_except.S @@ -29,9 +29,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. GEN_EXCEPT: |idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/get_op.S b/arch/m68k/fpsp040/get_op.S index c7c2f3727425..64c36d79ef83 100644 --- a/arch/m68k/fpsp040/get_op.S +++ b/arch/m68k/fpsp040/get_op.S @@ -54,9 +54,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. GET_OP: |idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/kernel_ex.S b/arch/m68k/fpsp040/kernel_ex.S index 476b711967ce..45bcf3455d34 100644 --- a/arch/m68k/fpsp040/kernel_ex.S +++ b/arch/m68k/fpsp040/kernel_ex.S @@ -12,9 +12,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. KERNEL_EX: |idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/res_func.S b/arch/m68k/fpsp040/res_func.S index 8f6b95217865..d9cdf4383545 100644 --- a/arch/m68k/fpsp040/res_func.S +++ b/arch/m68k/fpsp040/res_func.S @@ -16,9 +16,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. RES_FUNC: |idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/round.S b/arch/m68k/fpsp040/round.S index 00f98068783f..f84ae0dd4358 100644 --- a/arch/m68k/fpsp040/round.S +++ b/arch/m68k/fpsp040/round.S @@ -8,9 +8,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. |ROUND idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/sacos.S b/arch/m68k/fpsp040/sacos.S index 83b00ab1c48f..513c7cca7318 100644 --- a/arch/m68k/fpsp040/sacos.S +++ b/arch/m68k/fpsp040/sacos.S @@ -38,9 +38,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. |SACOS idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/sasin.S b/arch/m68k/fpsp040/sasin.S index 5647a6043903..2a269a58ceaa 100644 --- a/arch/m68k/fpsp040/sasin.S +++ b/arch/m68k/fpsp040/sasin.S @@ -38,9 +38,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. |SASIN idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/satan.S b/arch/m68k/fpsp040/satan.S index 20dae222d51e..c8a664998f92 100644 --- a/arch/m68k/fpsp040/satan.S +++ b/arch/m68k/fpsp040/satan.S @@ -43,9 +43,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. |satan idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/satanh.S b/arch/m68k/fpsp040/satanh.S index 20f07810bcda..ba91f77a7571 100644 --- a/arch/m68k/fpsp040/satanh.S +++ b/arch/m68k/fpsp040/satanh.S @@ -45,9 +45,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. |satanh idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/scale.S b/arch/m68k/fpsp040/scale.S index 5c9b805265f2..04829dd4f1f4 100644 --- a/arch/m68k/fpsp040/scale.S +++ b/arch/m68k/fpsp040/scale.S @@ -21,9 +21,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. |SCALE idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/scosh.S b/arch/m68k/fpsp040/scosh.S index e81edbb87642..07d3a4d7c86d 100644 --- a/arch/m68k/fpsp040/scosh.S +++ b/arch/m68k/fpsp040/scosh.S @@ -49,9 +49,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. |SCOSH idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/setox.S b/arch/m68k/fpsp040/setox.S index 0aa75f9bf7d1..145af5447581 100644 --- a/arch/m68k/fpsp040/setox.S +++ b/arch/m68k/fpsp040/setox.S @@ -331,9 +331,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. |setox idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/sgetem.S b/arch/m68k/fpsp040/sgetem.S index 0fcbd045ba75..d9234f4aed57 100644 --- a/arch/m68k/fpsp040/sgetem.S +++ b/arch/m68k/fpsp040/sgetem.S @@ -24,9 +24,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. |SGETEM idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/sint.S b/arch/m68k/fpsp040/sint.S index 0f9bd28e55a0..0e92d4e5d231 100644 --- a/arch/m68k/fpsp040/sint.S +++ b/arch/m68k/fpsp040/sint.S @@ -51,9 +51,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. |SINT idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/skeleton.S b/arch/m68k/fpsp040/skeleton.S index a1629194e3fd..a8f41615d94a 100644 --- a/arch/m68k/fpsp040/skeleton.S +++ b/arch/m68k/fpsp040/skeleton.S @@ -30,9 +30,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. | | Modified for Linux-1.3.x by Jes Sorensen (jds@kom.auc.dk) diff --git a/arch/m68k/fpsp040/slog2.S b/arch/m68k/fpsp040/slog2.S index 517fa4563246..fac2c738382e 100644 --- a/arch/m68k/fpsp040/slog2.S +++ b/arch/m68k/fpsp040/slog2.S @@ -96,9 +96,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. |SLOG2 idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/slogn.S b/arch/m68k/fpsp040/slogn.S index 2aaa0725c035..d98eaf641ec4 100644 --- a/arch/m68k/fpsp040/slogn.S +++ b/arch/m68k/fpsp040/slogn.S @@ -63,9 +63,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. |slogn idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/smovecr.S b/arch/m68k/fpsp040/smovecr.S index a0127fa55e9c..73c36512081b 100644 --- a/arch/m68k/fpsp040/smovecr.S +++ b/arch/m68k/fpsp040/smovecr.S @@ -15,9 +15,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. |SMOVECR idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/srem_mod.S b/arch/m68k/fpsp040/srem_mod.S index 8c8d7f50cc68..a27e70c9a0eb 100644 --- a/arch/m68k/fpsp040/srem_mod.S +++ b/arch/m68k/fpsp040/srem_mod.S @@ -66,9 +66,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. SREM_MOD: |idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/ssin.S b/arch/m68k/fpsp040/ssin.S index 043c91cdd657..a1ef8e01bf06 100644 --- a/arch/m68k/fpsp040/ssin.S +++ b/arch/m68k/fpsp040/ssin.S @@ -83,9 +83,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. |SSIN idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/ssinh.S b/arch/m68k/fpsp040/ssinh.S index c8b3308bb143..8a560edc7653 100644 --- a/arch/m68k/fpsp040/ssinh.S +++ b/arch/m68k/fpsp040/ssinh.S @@ -49,9 +49,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. |SSINH idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/stan.S b/arch/m68k/fpsp040/stan.S index b5c2a196e617..f8553aaececb 100644 --- a/arch/m68k/fpsp040/stan.S +++ b/arch/m68k/fpsp040/stan.S @@ -50,9 +50,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. |STAN idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/stanh.S b/arch/m68k/fpsp040/stanh.S index 33b009802243..7e12e59ee8c7 100644 --- a/arch/m68k/fpsp040/stanh.S +++ b/arch/m68k/fpsp040/stanh.S @@ -49,9 +49,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. |STANH idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/sto_res.S b/arch/m68k/fpsp040/sto_res.S index 0cdca3b060ad..484b47d4eaad 100644 --- a/arch/m68k/fpsp040/sto_res.S +++ b/arch/m68k/fpsp040/sto_res.S @@ -19,9 +19,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. STO_RES: |idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/stwotox.S b/arch/m68k/fpsp040/stwotox.S index 4e3c1407d3df..0d5e6a1436a6 100644 --- a/arch/m68k/fpsp040/stwotox.S +++ b/arch/m68k/fpsp040/stwotox.S @@ -76,9 +76,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. |STWOTOX idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/tbldo.S b/arch/m68k/fpsp040/tbldo.S index fe60cf4d20d7..fd5c37a5a2b9 100644 --- a/arch/m68k/fpsp040/tbldo.S +++ b/arch/m68k/fpsp040/tbldo.S @@ -17,9 +17,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. |TBLDO idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/util.S b/arch/m68k/fpsp040/util.S index 452f3d65857b..65b26fa88c60 100644 --- a/arch/m68k/fpsp040/util.S +++ b/arch/m68k/fpsp040/util.S @@ -16,9 +16,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. |UTIL idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/x_bsun.S b/arch/m68k/fpsp040/x_bsun.S index 039247b09c8b..d5a576bfac79 100644 --- a/arch/m68k/fpsp040/x_bsun.S +++ b/arch/m68k/fpsp040/x_bsun.S @@ -13,9 +13,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. X_BSUN: |idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/x_fline.S b/arch/m68k/fpsp040/x_fline.S index 3917710b0fde..264e126d1db7 100644 --- a/arch/m68k/fpsp040/x_fline.S +++ b/arch/m68k/fpsp040/x_fline.S @@ -13,9 +13,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. X_FLINE: |idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/x_operr.S b/arch/m68k/fpsp040/x_operr.S index b0f54bcb49a7..e2c371c3a45d 100644 --- a/arch/m68k/fpsp040/x_operr.S +++ b/arch/m68k/fpsp040/x_operr.S @@ -43,9 +43,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. X_OPERR: |idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/x_ovfl.S b/arch/m68k/fpsp040/x_ovfl.S index 22cb8b42c7b6..6fe4989ee31f 100644 --- a/arch/m68k/fpsp040/x_ovfl.S +++ b/arch/m68k/fpsp040/x_ovfl.S @@ -35,9 +35,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. X_OVFL: |idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/x_snan.S b/arch/m68k/fpsp040/x_snan.S index 039af573312e..4ed766416378 100644 --- a/arch/m68k/fpsp040/x_snan.S +++ b/arch/m68k/fpsp040/x_snan.S @@ -22,9 +22,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. X_SNAN: |idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/x_store.S b/arch/m68k/fpsp040/x_store.S index 4282fa67d449..402dc0c0ebc0 100644 --- a/arch/m68k/fpsp040/x_store.S +++ b/arch/m68k/fpsp040/x_store.S @@ -11,9 +11,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. X_STORE: |idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/x_unfl.S b/arch/m68k/fpsp040/x_unfl.S index 077fcc230fcc..eb772ff3b812 100644 --- a/arch/m68k/fpsp040/x_unfl.S +++ b/arch/m68k/fpsp040/x_unfl.S @@ -21,9 +21,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. X_UNFL: |idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/x_unimp.S b/arch/m68k/fpsp040/x_unimp.S index 920cb9410e9e..6f382b21228b 100644 --- a/arch/m68k/fpsp040/x_unimp.S +++ b/arch/m68k/fpsp040/x_unimp.S @@ -22,9 +22,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. X_UNIMP: |idnt 2,1 | Motorola 040 Floating Point Software Package diff --git a/arch/m68k/fpsp040/x_unsupp.S b/arch/m68k/fpsp040/x_unsupp.S index 4ec57285b683..d7cf46208c62 100644 --- a/arch/m68k/fpsp040/x_unsupp.S +++ b/arch/m68k/fpsp040/x_unsupp.S @@ -23,9 +23,8 @@ | Copyright (C) Motorola, Inc. 1990 | All Rights Reserved | -| THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF MOTOROLA -| The copyright notice above does not evidence any -| actual or intended publication of such source code. +| For details on the license for this file, please see the +| file, README, in this same directory. X_UNSUPP: |idnt 2,1 | Motorola 040 Floating Point Software Package From 33042a9ff4d126ba944b9dc3076665a2029e0a34 Mon Sep 17 00:00:00 2001 From: Chris McDermott Date: Sat, 11 Feb 2006 17:55:50 -0800 Subject: [PATCH 03/48] [PATCH] x86-64: Fix HPET timer on x460 [description from AK] The IBM Summit 3 chipset doesn't implement the HPET timer replacement option. Since the current Linux code relies on it use a mixed mode with both PIT for the interrupt and HPET counters for the time keeping. That was already implemented, but didn't work properly because it was still using the last interrupt offset in HPET. This resulted in x460 not booting. Fix this up by using the free running HPET counter. Shouldn't affect any other machine because they either use full HPET mode or no HPET at all. TBD needs a similar 32bit fix. Signed-off-by: Andi Kleen Cc: Pallipadi, Venkatesh" Cc: Bob Picco Cc: Bjorn Helgaas Cc: john stultz Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- arch/x86_64/kernel/apic.c | 2 +- arch/x86_64/kernel/time.c | 12 +++++++++--- include/asm-x86_64/hpet.h | 2 ++ 3 files changed, 12 insertions(+), 4 deletions(-) diff --git a/arch/x86_64/kernel/apic.c b/arch/x86_64/kernel/apic.c index 6147770b4347..7a0a3e8d5d72 100644 --- a/arch/x86_64/kernel/apic.c +++ b/arch/x86_64/kernel/apic.c @@ -708,7 +708,7 @@ static void setup_APIC_timer(unsigned int clocks) local_irq_save(flags); /* wait for irq slice */ - if (vxtime.hpet_address) { + if (vxtime.hpet_address && hpet_use_timer) { int trigger = hpet_readl(HPET_T0_CMP); while (hpet_readl(HPET_COUNTER) >= trigger) /* do nothing */ ; diff --git a/arch/x86_64/kernel/time.c b/arch/x86_64/kernel/time.c index dba7237be5c1..3c58c30506a1 100644 --- a/arch/x86_64/kernel/time.c +++ b/arch/x86_64/kernel/time.c @@ -59,7 +59,7 @@ static int notsc __initdata = 0; unsigned int cpu_khz; /* TSC clocks / usec, not used here */ static unsigned long hpet_period; /* fsecs / HPET clock */ unsigned long hpet_tick; /* HPET clocks / interrupt */ -static int hpet_use_timer; /* Use counter of hpet for time keeping, otherwise PIT */ +int hpet_use_timer; /* Use counter of hpet for time keeping, otherwise PIT */ unsigned long vxtime_hz = PIT_TICK_RATE; int report_lost_ticks; /* command line option */ unsigned long long monotonic_base; @@ -326,7 +326,10 @@ static noinline void handle_lost_ticks(int lost, struct pt_regs *regs) print_symbol("rip %s\n", regs->rip); if (vxtime.mode == VXTIME_TSC && vxtime.hpet_address) { printk(KERN_WARNING "Falling back to HPET\n"); - vxtime.last = hpet_readl(HPET_T0_CMP) - hpet_tick; + if (hpet_use_timer) + vxtime.last = hpet_readl(HPET_T0_CMP) - hpet_tick; + else + vxtime.last = hpet_readl(HPET_COUNTER); vxtime.mode = VXTIME_HPET; do_gettimeoffset = do_gettimeoffset_hpet; } @@ -988,7 +991,10 @@ void __init time_init_gtod(void) notsc = 1; if (vxtime.hpet_address && notsc) { timetype = hpet_use_timer ? "HPET" : "PIT/HPET"; - vxtime.last = hpet_readl(HPET_T0_CMP) - hpet_tick; + if (hpet_use_timer) + vxtime.last = hpet_readl(HPET_T0_CMP) - hpet_tick; + else + vxtime.last = hpet_readl(HPET_COUNTER); vxtime.mode = VXTIME_HPET; do_gettimeoffset = do_gettimeoffset_hpet; #ifdef CONFIG_X86_PM_TIMER diff --git a/include/asm-x86_64/hpet.h b/include/asm-x86_64/hpet.h index c20c28f5c7a0..08b75c15269a 100644 --- a/include/asm-x86_64/hpet.h +++ b/include/asm-x86_64/hpet.h @@ -55,6 +55,8 @@ extern int is_hpet_enabled(void); extern int hpet_rtc_timer_init(void); extern int oem_force_hpet_timer(void); +extern int hpet_use_timer; + #ifdef CONFIG_HPET_EMULATE_RTC extern int hpet_mask_rtc_irq_bit(unsigned long bit_mask); extern int hpet_set_rtc_irq_bit(unsigned long bit_mask); From 643a654540579b0dcc7a206a4a7475276a41aff0 Mon Sep 17 00:00:00 2001 From: Andrew Morton Date: Sat, 11 Feb 2006 17:55:52 -0800 Subject: [PATCH 04/48] [PATCH] select: fix returned timeval With David Woodhouse select() presently has a habit of increasing the value of the user's `timeout' argument on return. We were writing back a timeout larger than the original. We _deliberately_ round up, since we know we must wait at _least_ as long as the caller asks us to. The patch adds a couple of helper functions for magnitude comparison of timespecs and of timevals, and uses them to prevent the various poll and select functions from returning a timeout which is larger than the one which was passed in. The patch also fixes a bug in compat_sys_pselect7(): it was adding the new timeout value to the old one and was returning that. It should just return the new timeout value. (We have various handy timespec/timeval-to-from-nsec conversion functions in time.h. But this code open-codes it all). Cc: "David S. Miller" Cc: Andi Kleen Cc: Ulrich Drepper Cc: Thomas Gleixner Cc: george anzinger Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- fs/compat.c | 37 +++++++++++++++++++++++++------------ fs/select.c | 32 +++++++++++++++++++++++--------- include/linux/compat.h | 20 ++++++++++++++++++++ include/linux/time.h | 25 ++++++++++++++++++++++++- 4 files changed, 92 insertions(+), 22 deletions(-) diff --git a/fs/compat.c b/fs/compat.c index 70c5af4cc270..a2ba78bdf7f7 100644 --- a/fs/compat.c +++ b/fs/compat.c @@ -1751,11 +1751,15 @@ asmlinkage long compat_sys_select(int n, compat_ulong_t __user *inp, ret = compat_core_sys_select(n, inp, outp, exp, &timeout); if (tvp) { + struct compat_timeval rtv; + if (current->personality & STICKY_TIMEOUTS) goto sticky; - tv.tv_usec = jiffies_to_usecs(do_div((*(u64*)&timeout), HZ)); - tv.tv_sec = timeout; - if (copy_to_user(tvp, &tv, sizeof(tv))) { + rtv.tv_usec = jiffies_to_usecs(do_div((*(u64*)&timeout), HZ)); + rtv.tv_sec = timeout; + if (compat_timeval_compare(&rtv, &tv) < 0) + rtv = tv; + if (copy_to_user(tvp, &rtv, sizeof(rtv))) { sticky: /* * If an application puts its timeval in read-only @@ -1822,13 +1826,17 @@ asmlinkage long compat_sys_pselect7(int n, compat_ulong_t __user *inp, } while (!ret && !timeout && tsp && (ts.tv_sec || ts.tv_nsec)); if (tsp && !(current->personality & STICKY_TIMEOUTS)) { - ts.tv_sec += timeout / HZ; - ts.tv_nsec += (timeout % HZ) * (1000000000/HZ); - if (ts.tv_nsec >= 1000000000) { - ts.tv_sec++; - ts.tv_nsec -= 1000000000; + struct compat_timespec rts; + + rts.tv_sec = timeout / HZ; + rts.tv_nsec = (timeout % HZ) * (NSEC_PER_SEC/HZ); + if (rts.tv_nsec >= NSEC_PER_SEC) { + rts.tv_sec++; + rts.tv_nsec -= NSEC_PER_SEC; } - (void)copy_to_user(tsp, &ts, sizeof(ts)); + if (compat_timespec_compare(&rts, &ts) < 0) + rts = ts; + copy_to_user(tsp, &rts, sizeof(rts)); } if (ret == -ERESTARTNOHAND) { @@ -1918,12 +1926,17 @@ asmlinkage long compat_sys_ppoll(struct pollfd __user *ufds, sigprocmask(SIG_SETMASK, &sigsaved, NULL); if (tsp && timeout >= 0) { + struct compat_timespec rts; + if (current->personality & STICKY_TIMEOUTS) goto sticky; /* Yes, we know it's actually an s64, but it's also positive. */ - ts.tv_nsec = jiffies_to_usecs(do_div((*(u64*)&timeout), HZ)) * 1000; - ts.tv_sec = timeout; - if (copy_to_user(tsp, &ts, sizeof(ts))) { + rts.tv_nsec = jiffies_to_usecs(do_div((*(u64*)&timeout), HZ)) * + 1000; + rts.tv_sec = timeout; + if (compat_timespec_compare(&rts, &ts) < 0) + rts = ts; + if (copy_to_user(tsp, &rts, sizeof(rts))) { sticky: /* * If an application puts its timeval in read-only diff --git a/fs/select.c b/fs/select.c index bc60a3e14ef3..6ce68a9c8976 100644 --- a/fs/select.c +++ b/fs/select.c @@ -398,11 +398,15 @@ asmlinkage long sys_select(int n, fd_set __user *inp, fd_set __user *outp, ret = core_sys_select(n, inp, outp, exp, &timeout); if (tvp) { + struct timeval rtv; + if (current->personality & STICKY_TIMEOUTS) goto sticky; - tv.tv_usec = jiffies_to_usecs(do_div((*(u64*)&timeout), HZ)); - tv.tv_sec = timeout; - if (copy_to_user(tvp, &tv, sizeof(tv))) { + rtv.tv_usec = jiffies_to_usecs(do_div((*(u64*)&timeout), HZ)); + rtv.tv_sec = timeout; + if (timeval_compare(&rtv, &tv) < 0) + rtv = tv; + if (copy_to_user(tvp, &rtv, sizeof(rtv))) { sticky: /* * If an application puts its timeval in read-only @@ -460,11 +464,16 @@ asmlinkage long sys_pselect7(int n, fd_set __user *inp, fd_set __user *outp, ret = core_sys_select(n, inp, outp, exp, &timeout); if (tsp) { + struct timespec rts; + if (current->personality & STICKY_TIMEOUTS) goto sticky; - ts.tv_nsec = jiffies_to_usecs(do_div((*(u64*)&timeout), HZ)) * 1000; - ts.tv_sec = timeout; - if (copy_to_user(tsp, &ts, sizeof(ts))) { + rts.tv_nsec = jiffies_to_usecs(do_div((*(u64*)&timeout), HZ)) * + 1000; + rts.tv_sec = timeout; + if (timespec_compare(&rts, &ts) < 0) + rts = ts; + if (copy_to_user(tsp, &rts, sizeof(rts))) { sticky: /* * If an application puts its timeval in read-only @@ -758,12 +767,17 @@ asmlinkage long sys_ppoll(struct pollfd __user *ufds, unsigned int nfds, sigprocmask(SIG_SETMASK, &sigsaved, NULL); if (tsp && timeout >= 0) { + struct timespec rts; + if (current->personality & STICKY_TIMEOUTS) goto sticky; /* Yes, we know it's actually an s64, but it's also positive. */ - ts.tv_nsec = jiffies_to_usecs(do_div((*(u64*)&timeout), HZ)) * 1000; - ts.tv_sec = timeout; - if (copy_to_user(tsp, &ts, sizeof(ts))) { + rts.tv_nsec = jiffies_to_usecs(do_div((*(u64*)&timeout), HZ)) * + 1000; + rts.tv_sec = timeout; + if (timespec_compare(&rts, &ts) < 0) + rts = ts; + if (copy_to_user(tsp, &rts, sizeof(rts))) { sticky: /* * If an application puts its timeval in read-only diff --git a/include/linux/compat.h b/include/linux/compat.h index f9ca534787e2..c9ab2a26348c 100644 --- a/include/linux/compat.h +++ b/include/linux/compat.h @@ -161,5 +161,25 @@ int copy_siginfo_to_user32(struct compat_siginfo __user *to, siginfo_t *from); int get_compat_sigevent(struct sigevent *event, const struct compat_sigevent __user *u_event); +static inline int compat_timeval_compare(struct compat_timeval *lhs, + struct compat_timeval *rhs) +{ + if (lhs->tv_sec < rhs->tv_sec) + return -1; + if (lhs->tv_sec > rhs->tv_sec) + return 1; + return lhs->tv_usec - rhs->tv_usec; +} + +static inline int compat_timespec_compare(struct compat_timespec *lhs, + struct compat_timespec *rhs) +{ + if (lhs->tv_sec < rhs->tv_sec) + return -1; + if (lhs->tv_sec > rhs->tv_sec) + return 1; + return lhs->tv_nsec - rhs->tv_nsec; +} + #endif /* CONFIG_COMPAT */ #endif /* _LINUX_COMPAT_H */ diff --git a/include/linux/time.h b/include/linux/time.h index 7b4dc36532bb..d9cdba54b789 100644 --- a/include/linux/time.h +++ b/include/linux/time.h @@ -33,11 +33,34 @@ struct timezone { #define NSEC_PER_SEC 1000000000L #define NSEC_PER_USEC 1000L -static __inline__ int timespec_equal(struct timespec *a, struct timespec *b) +static inline int timespec_equal(struct timespec *a, struct timespec *b) { return (a->tv_sec == b->tv_sec) && (a->tv_nsec == b->tv_nsec); } +/* + * lhs < rhs: return <0 + * lhs == rhs: return 0 + * lhs > rhs: return >0 + */ +static inline int timespec_compare(struct timespec *lhs, struct timespec *rhs) +{ + if (lhs->tv_sec < rhs->tv_sec) + return -1; + if (lhs->tv_sec > rhs->tv_sec) + return 1; + return lhs->tv_nsec - rhs->tv_nsec; +} + +static inline int timeval_compare(struct timeval *lhs, struct timeval *rhs) +{ + if (lhs->tv_sec < rhs->tv_sec) + return -1; + if (lhs->tv_sec > rhs->tv_sec) + return 1; + return lhs->tv_usec - rhs->tv_usec; +} + extern unsigned long mktime(const unsigned int year, const unsigned int mon, const unsigned int day, const unsigned int hour, const unsigned int min, const unsigned int sec); From 80e4342601abfafacb5f20571e40b56d73d10819 Mon Sep 17 00:00:00 2001 From: Christoph Lameter Date: Sat, 11 Feb 2006 17:55:53 -0800 Subject: [PATCH 05/48] [PATCH] zone reclaim: do not check references to a page during zone reclaim shrink_list() and refill_inactive() check all ptes pointing to a page for reference bits in order to decide if the page should be put on the active list. This is not necessary for zone_reclaim since we are only interested in removing unmapped pages. Skip the checks in both functions. Signed-off-by: Christoph Lameter Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- mm/vmscan.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/mm/vmscan.c b/mm/vmscan.c index 5db32fdfaf39..e1c64230ffdd 100644 --- a/mm/vmscan.c +++ b/mm/vmscan.c @@ -443,6 +443,10 @@ static int shrink_list(struct list_head *page_list, struct scan_control *sc) BUG_ON(PageActive(page)); sc->nr_scanned++; + + if (!sc->may_swap && page_mapped(page)) + goto keep_locked; + /* Double the slab pressure for mapped and swapcache pages */ if (page_mapped(page) || PageSwapCache(page)) sc->nr_scanned++; @@ -1231,7 +1235,7 @@ refill_inactive_zone(struct zone *zone, struct scan_control *sc) * Now use this metric to decide whether to start moving mapped memory * onto the inactive list. */ - if (swap_tendency >= 100) + if (swap_tendency >= 100 && sc->may_swap) reclaim_mapped = 1; while (!list_empty(&l_hold)) { From 072eaa5d9cc3e63f567ffd9ad87b36194fdd8010 Mon Sep 17 00:00:00 2001 From: Christoph Lameter Date: Sat, 11 Feb 2006 17:55:54 -0800 Subject: [PATCH 06/48] [PATCH] vmscan: remove duplicate increment of reclaim_in_progress shrink_zone() already increments reclaim_in_progress. No need to do it in balance_pgdat. Signed-off-by: Christoph Lameter Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- mm/vmscan.c | 2 -- 1 file changed, 2 deletions(-) diff --git a/mm/vmscan.c b/mm/vmscan.c index e1c64230ffdd..58ed5125b1a7 100644 --- a/mm/vmscan.c +++ b/mm/vmscan.c @@ -1614,9 +1614,7 @@ static int balance_pgdat(pg_data_t *pgdat, int nr_pages, int order) sc.nr_reclaimed = 0; sc.priority = priority; sc.swap_cluster_max = nr_pages? nr_pages : SWAP_CLUSTER_MAX; - atomic_inc(&zone->reclaim_in_progress); shrink_zone(zone, &sc); - atomic_dec(&zone->reclaim_in_progress); reclaim_state->reclaimed_slab = 0; nr_slab = shrink_slab(sc.nr_scanned, GFP_KERNEL, lru_pages); From 2903fb1694dcb08a3c1d9d823cfae7ba30e66cd3 Mon Sep 17 00:00:00 2001 From: Christoph Lameter Date: Sat, 11 Feb 2006 17:55:55 -0800 Subject: [PATCH 07/48] [PATCH] vmscan: skip reclaim_mapped determination if we do not swap This puts the variables and the way to get to reclaim_mapped in one block. And allows zone_reclaim or other things to skip the determination (maybe this whole block of code does not belong into refill_inactive_zone()?) Signed-off-by: Christoph Lameter Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- mm/vmscan.c | 75 +++++++++++++++++++++++++++++------------------------ 1 file changed, 41 insertions(+), 34 deletions(-) diff --git a/mm/vmscan.c b/mm/vmscan.c index 58ed5125b1a7..1838c15ca4fd 100644 --- a/mm/vmscan.c +++ b/mm/vmscan.c @@ -1195,9 +1195,47 @@ refill_inactive_zone(struct zone *zone, struct scan_control *sc) struct page *page; struct pagevec pvec; int reclaim_mapped = 0; - long mapped_ratio; - long distress; - long swap_tendency; + + if (unlikely(sc->may_swap)) { + long mapped_ratio; + long distress; + long swap_tendency; + + /* + * `distress' is a measure of how much trouble we're having + * reclaiming pages. 0 -> no problems. 100 -> great trouble. + */ + distress = 100 >> zone->prev_priority; + + /* + * The point of this algorithm is to decide when to start + * reclaiming mapped memory instead of just pagecache. Work out + * how much memory + * is mapped. + */ + mapped_ratio = (sc->nr_mapped * 100) / total_memory; + + /* + * Now decide how much we really want to unmap some pages. The + * mapped ratio is downgraded - just because there's a lot of + * mapped memory doesn't necessarily mean that page reclaim + * isn't succeeding. + * + * The distress ratio is important - we don't want to start + * going oom. + * + * A 100% value of vm_swappiness overrides this algorithm + * altogether. + */ + swap_tendency = mapped_ratio / 2 + distress + vm_swappiness; + + /* + * Now use this metric to decide whether to start moving mapped + * memory onto the inactive list. + */ + if (swap_tendency >= 100) + reclaim_mapped = 1; + } lru_add_drain(); spin_lock_irq(&zone->lru_lock); @@ -1207,37 +1245,6 @@ refill_inactive_zone(struct zone *zone, struct scan_control *sc) zone->nr_active -= pgmoved; spin_unlock_irq(&zone->lru_lock); - /* - * `distress' is a measure of how much trouble we're having reclaiming - * pages. 0 -> no problems. 100 -> great trouble. - */ - distress = 100 >> zone->prev_priority; - - /* - * The point of this algorithm is to decide when to start reclaiming - * mapped memory instead of just pagecache. Work out how much memory - * is mapped. - */ - mapped_ratio = (sc->nr_mapped * 100) / total_memory; - - /* - * Now decide how much we really want to unmap some pages. The mapped - * ratio is downgraded - just because there's a lot of mapped memory - * doesn't necessarily mean that page reclaim isn't succeeding. - * - * The distress ratio is important - we don't want to start going oom. - * - * A 100% value of vm_swappiness overrides this algorithm altogether. - */ - swap_tendency = mapped_ratio / 2 + distress + vm_swappiness; - - /* - * Now use this metric to decide whether to start moving mapped memory - * onto the inactive list. - */ - if (swap_tendency >= 100 && sc->may_swap) - reclaim_mapped = 1; - while (!list_empty(&l_hold)) { cond_resched(); page = lru_to_page(&l_hold); From c0cdf1935cf328730fa068e0f39a22e6149555aa Mon Sep 17 00:00:00 2001 From: Ingo Molnar Date: Sat, 11 Feb 2006 17:55:56 -0800 Subject: [PATCH 08/48] [PATCH] x86: print out early faults via early_printk() Lost a few hours debugging an early-bootup fault within printk itself, which manifested itself as a hard to debug early hang. This patch makes it much easier by printing out early faults via early_printk(), which function is a lot simpler than a full printk, and hence more likely to succeed in emergencies. (We do not recover from early faults anyway, so there's no loss from not having these messages in the normal printk buffer.) Signed-off-by: Ingo Molnar Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- arch/i386/kernel/head.S | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/arch/i386/kernel/head.S b/arch/i386/kernel/head.S index 5884469f6bfe..2bee6499edd9 100644 --- a/arch/i386/kernel/head.S +++ b/arch/i386/kernel/head.S @@ -398,7 +398,11 @@ ignore_int: pushl 32(%esp) pushl 40(%esp) pushl $int_msg +#ifdef CONFIG_EARLY_PRINTK + call early_printk +#else call printk +#endif addl $(5*4),%esp popl %ds popl %es From c48d865c50e8626372a52094385fb1f5a2d2a7fd Mon Sep 17 00:00:00 2001 From: Cornelia Huck Date: Sat, 11 Feb 2006 17:55:57 -0800 Subject: [PATCH 09/48] [PATCH] s390: fix locking in __chp_add() and s390_subchannel_remove_chpid() Fix locking in __chp_add() and s390_subchannel_remove_chpid(): Need to disable/enable because they are always called from a thread (and not directly from a machine check...) Signed-off-by: Cornelia Huck Signed-off-by: Heiko Carstens Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/s390/cio/chsc.c | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/drivers/s390/cio/chsc.c b/drivers/s390/cio/chsc.c index 92be75d99a56..8cf9905d484b 100644 --- a/drivers/s390/cio/chsc.c +++ b/drivers/s390/cio/chsc.c @@ -232,7 +232,7 @@ s390_subchannel_remove_chpid(struct device *dev, void *data) return 0; mask = 0x80 >> j; - spin_lock(&sch->lock); + spin_lock_irq(&sch->lock); stsch(sch->schid, &schib); if (!schib.pmcw.dnv) @@ -281,10 +281,10 @@ s390_subchannel_remove_chpid(struct device *dev, void *data) if (sch->driver && sch->driver->verify) sch->driver->verify(&sch->dev); out_unlock: - spin_unlock(&sch->lock); + spin_unlock_irq(&sch->lock); return 0; out_unreg: - spin_unlock(&sch->lock); + spin_unlock_irq(&sch->lock); sch->lpm = 0; if (css_enqueue_subchannel_slow(sch->schid)) { css_clear_subchannel_slow_list(); @@ -652,7 +652,7 @@ __chp_add(struct subchannel_id schid, void *data) if (!sch) /* Check if the subchannel is now available. */ return __chp_add_new_sch(schid); - spin_lock(&sch->lock); + spin_lock_irq(&sch->lock); for (i=0; i<8; i++) if (sch->schib.pmcw.chpid[i] == chp->id) { if (stsch(sch->schid, &sch->schib) != 0) { @@ -674,7 +674,7 @@ __chp_add(struct subchannel_id schid, void *data) if (sch->driver && sch->driver->verify) sch->driver->verify(&sch->dev); - spin_unlock(&sch->lock); + spin_unlock_irq(&sch->lock); put_device(&sch->dev); return 0; } From e6f3601a7275216c48c2635f46b388d970901bb9 Mon Sep 17 00:00:00 2001 From: Heiko Carstens Date: Sat, 11 Feb 2006 17:55:58 -0800 Subject: [PATCH 10/48] [PATCH] s390: update default configuration Switch on CONFIG_DEBUG_FS again. Signed-off-by: Heiko Carstens Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- arch/s390/defconfig | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/arch/s390/defconfig b/arch/s390/defconfig index 3525c91204d4..f8d0cd540a06 100644 --- a/arch/s390/defconfig +++ b/arch/s390/defconfig @@ -1,7 +1,7 @@ # # Automatically generated make config: don't edit -# Linux kernel version: 2.6.16-rc1 -# Thu Jan 19 10:58:53 2006 +# Linux kernel version: 2.6.16-rc2 +# Wed Feb 8 10:44:39 2006 # CONFIG_MMU=y CONFIG_RWSEM_XCHGADD_ALGORITHM=y @@ -12,7 +12,6 @@ CONFIG_S390=y # Code maturity level options # CONFIG_EXPERIMENTAL=y -CONFIG_CLEAN_COMPILE=y CONFIG_LOCK_KERNEL=y CONFIG_INIT_ENV_ARG_LIMIT=32 @@ -154,6 +153,7 @@ CONFIG_NET=y # # Networking options # +# CONFIG_NETDEBUG is not set CONFIG_PACKET=y # CONFIG_PACKET_MMAP is not set CONFIG_UNIX=y @@ -607,6 +607,7 @@ CONFIG_MSDOS_PARTITION=y # Instrumentation Support # # CONFIG_PROFILING is not set +# CONFIG_STATISTICS is not set # # Kernel hacking @@ -624,7 +625,7 @@ CONFIG_DEBUG_MUTEXES=y # CONFIG_DEBUG_SPINLOCK_SLEEP is not set # CONFIG_DEBUG_KOBJECT is not set # CONFIG_DEBUG_INFO is not set -# CONFIG_DEBUG_FS is not set +CONFIG_DEBUG_FS=y # CONFIG_DEBUG_VM is not set CONFIG_FORCED_INLINING=y # CONFIG_RCU_TORTURE_TEST is not set From 25fab9ebac445d57b656f5faabac5a195bed2f82 Mon Sep 17 00:00:00 2001 From: Peter Oberparleiter Date: Sat, 11 Feb 2006 17:55:59 -0800 Subject: [PATCH 11/48] [PATCH] s390: fix sclp memory corruption in tty pages list When the sclp interface takes very long to serve a request, the sclp core driver will report a failed request to the sclp tty driver even though the request is still being processed by the sclp interface. Eventually the sclp interface completes the request and updates some fields in the request buffer which leads to a corrupted tty pages list. The next time function sclp_tty_write_room is called, the corrupted list will be traversed, resulting in an oops. To avoid this remove the busy retry limit and increase retry intervals. Signed-off-by: Peter Oberparleiter Signed-off-by: Heiko Carstens Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/s390/char/sclp.c | 13 +++++-------- 1 file changed, 5 insertions(+), 8 deletions(-) diff --git a/drivers/s390/char/sclp.c b/drivers/s390/char/sclp.c index ceb0e474fde4..4138564402b8 100644 --- a/drivers/s390/char/sclp.c +++ b/drivers/s390/char/sclp.c @@ -85,11 +85,10 @@ static volatile enum sclp_mask_state_t { /* Maximum retry counts */ #define SCLP_INIT_RETRY 3 #define SCLP_MASK_RETRY 3 -#define SCLP_REQUEST_RETRY 3 /* Timeout intervals in seconds.*/ -#define SCLP_BUSY_INTERVAL 2 -#define SCLP_RETRY_INTERVAL 5 +#define SCLP_BUSY_INTERVAL 10 +#define SCLP_RETRY_INTERVAL 15 static void sclp_process_queue(void); static int sclp_init_mask(int calculate); @@ -153,11 +152,9 @@ __sclp_start_request(struct sclp_req *req) if (sclp_running_state != sclp_running_state_idle) return 0; del_timer(&sclp_request_timer); - if (req->start_count <= SCLP_REQUEST_RETRY) { - rc = service_call(req->command, req->sccb); - req->start_count++; - } else - rc = -EIO; + rc = service_call(req->command, req->sccb); + req->start_count++; + if (rc == 0) { /* Sucessfully started request */ req->status = SCLP_REQ_RUNNING; From 9733e2407ad2237867cb13c04e7d619397fa3090 Mon Sep 17 00:00:00 2001 From: Heiko Carstens Date: Sat, 11 Feb 2006 17:56:00 -0800 Subject: [PATCH 12/48] [PATCH] s390: earlier initialization of cpu_possible_map Initiliazing of cpu_possible_map was done in smp_prepare_cpus which is way too late. Therefore assign a static value to cpu_possible_map, since we don't have access to max_cpus in setup_arch. Signed-off-by: Heiko Carstens Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- arch/s390/kernel/smp.c | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/arch/s390/kernel/smp.c b/arch/s390/kernel/smp.c index cbfcfd02a43a..0d1ad5dbe2b1 100644 --- a/arch/s390/kernel/smp.c +++ b/arch/s390/kernel/smp.c @@ -52,7 +52,7 @@ extern volatile int __cpu_logical_map[]; struct _lowcore *lowcore_ptr[NR_CPUS]; cpumask_t cpu_online_map; -cpumask_t cpu_possible_map; +cpumask_t cpu_possible_map = CPU_MASK_ALL; static struct task_struct *current_set[NR_CPUS]; @@ -514,9 +514,6 @@ __init smp_check_cpus(unsigned int max_cpus) num_cpus++; } - for (cpu = 1; cpu < max_cpus; cpu++) - cpu_set(cpu, cpu_possible_map); - printk("Detected %d CPU's\n",(int) num_cpus); printk("Boot cpu address %2X\n", boot_cpu_addr); } @@ -810,7 +807,6 @@ void __devinit smp_prepare_boot_cpu(void) cpu_set(0, cpu_online_map); cpu_set(0, cpu_present_map); - cpu_set(0, cpu_possible_map); S390_lowcore.percpu_offset = __per_cpu_offset[0]; current_set[0] = current; } From 5238da45f345898a8bfcd14e53b0431fcee36a04 Mon Sep 17 00:00:00 2001 From: Heiko Carstens Date: Sat, 11 Feb 2006 17:56:01 -0800 Subject: [PATCH 13/48] [PATCH] s390: update maintainers file Update URL for s390 and add maintainers for s390 networking and zfcp driver. Signed-off-by: Heiko Carstens Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- MAINTAINERS | 18 +++++++++++++++++- 1 file changed, 17 insertions(+), 1 deletion(-) diff --git a/MAINTAINERS b/MAINTAINERS index b22db521cec1..9c592aa0280c 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -2232,7 +2232,23 @@ P: Martin Schwidefsky M: schwidefsky@de.ibm.com M: linux390@de.ibm.com L: linux-390@vm.marist.edu -W: http://oss.software.ibm.com/developerworks/opensource/linux390 +W: http://www.ibm.com/developerworks/linux/linux390/ +S: Supported + +S390 NETWORK DRIVERS +P: Frank Pavlic +M: fpavlic@de.ibm.com +M: linux390@de.ibm.com +L: linux-390@vm.marist.edu +W: http://www.ibm.com/developerworks/linux/linux390/ +S: Supported + +S390 ZFCP DRIVER +P: Andreas Herrmann +M: aherrman@de.ibm.com +M: linux390@de.ibm.com +L: linux-390@vm.marist.edu +W: http://www.ibm.com/developerworks/linux/linux390/ S: Supported SAA7146 VIDEO4LINUX-2 DRIVER From a386fba2516b5404864647906219ced57bf2f2b7 Mon Sep 17 00:00:00 2001 From: Heiko Carstens Date: Sat, 11 Feb 2006 17:56:01 -0800 Subject: [PATCH 14/48] [PATCH] s390: fix non smp build of kexec Add missing smp_cpu_not_running define to avoid build warnings in the non smp case. Signed-off-by: Heiko Carstens Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- arch/s390/kernel/machine_kexec.c | 5 +++-- include/asm-s390/smp.h | 1 + 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/arch/s390/kernel/machine_kexec.c b/arch/s390/kernel/machine_kexec.c index f0ed5c642c74..bad81b5832db 100644 --- a/arch/s390/kernel/machine_kexec.c +++ b/arch/s390/kernel/machine_kexec.c @@ -12,15 +12,16 @@ * on the S390 architecture. */ -#include -#include #include #include #include #include +#include +#include #include #include #include +#include static void kexec_halt_all_cpus(void *); diff --git a/include/asm-s390/smp.h b/include/asm-s390/smp.h index a2ae7628bbaa..9c6e9c300eb9 100644 --- a/include/asm-s390/smp.h +++ b/include/asm-s390/smp.h @@ -101,6 +101,7 @@ smp_call_function_on(void (*func) (void *info), void *info, func(info); return 0; } +#define smp_cpu_not_running(cpu) 1 #define smp_get_cpu(cpu) ({ 0; }) #define smp_put_cpu(cpu) ({ 0; }) #endif From e7684277f6882a23cfb734cb7450c3a469e6e8b1 Mon Sep 17 00:00:00 2001 From: Heiko Carstens Date: Sat, 11 Feb 2006 17:56:02 -0800 Subject: [PATCH 15/48] [PATCH] s390: add support for unshare system call Add support for unshare system call. Signed-off-by: Heiko Carstens Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- arch/s390/kernel/compat_wrapper.S | 5 +++++ arch/s390/kernel/syscalls.S | 1 + include/asm-s390/unistd.h | 3 ++- 3 files changed, 8 insertions(+), 1 deletion(-) diff --git a/arch/s390/kernel/compat_wrapper.S b/arch/s390/kernel/compat_wrapper.S index 83b33fe1923c..38a6ef5ec624 100644 --- a/arch/s390/kernel/compat_wrapper.S +++ b/arch/s390/kernel/compat_wrapper.S @@ -1602,3 +1602,8 @@ compat_sys_ppoll_wrapper: llgtr %r5,%r5 # const sigset_t * llgfr %r6,%r6 # size_t jg compat_sys_ppoll + + .globl sys_unshare_wrapper +sys_unshare_wrapper: + llgfr %r2,%r2 # unsigned long + jg sys_unshare diff --git a/arch/s390/kernel/syscalls.S b/arch/s390/kernel/syscalls.S index 3280345efacd..e86a4debb160 100644 --- a/arch/s390/kernel/syscalls.S +++ b/arch/s390/kernel/syscalls.S @@ -311,3 +311,4 @@ SYSCALL(sys_fchmodat,sys_fchmodat,sys_fchmodat_wrapper) SYSCALL(sys_faccessat,sys_faccessat,sys_faccessat_wrapper) /* 300 */ SYSCALL(sys_pselect6,sys_pselect6,compat_sys_pselect6_wrapper) SYSCALL(sys_ppoll,sys_ppoll,compat_sys_ppoll_wrapper) +SYSCALL(sys_unshare,sys_unshare,sys_unshare_wrapper) diff --git a/include/asm-s390/unistd.h b/include/asm-s390/unistd.h index 29a9f357eb9e..0a2f6664c4cf 100644 --- a/include/asm-s390/unistd.h +++ b/include/asm-s390/unistd.h @@ -295,8 +295,9 @@ #define __NR_faccessat 300 #define __NR_pselect6 301 #define __NR_ppoll 302 +#define __NR_unshare 303 -#define NR_syscalls 303 +#define NR_syscalls 304 /* * There are some system calls that are not present on 64 bit, some From 0defa3c19e7792001df09d6fa5ab461d3599ff6d Mon Sep 17 00:00:00 2001 From: Heiko Carstens Date: Sat, 11 Feb 2006 17:56:03 -0800 Subject: [PATCH 16/48] [PATCH] s390: add #ifdef __KERNEL__ to asm-s390/setup.h Based on a patch from Maximilian Attems . Nothing in asm-s390/setup.h is of interest for user space. Signed-off-by: Heiko Carstens Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- include/asm-s390/setup.h | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/include/asm-s390/setup.h b/include/asm-s390/setup.h index 348a88137445..da3fd4a7bb32 100644 --- a/include/asm-s390/setup.h +++ b/include/asm-s390/setup.h @@ -8,6 +8,8 @@ #ifndef _ASM_S390_SETUP_H #define _ASM_S390_SETUP_H +#ifdef __KERNEL__ + #include #define PARMAREA 0x10400 @@ -114,7 +116,7 @@ extern u16 ipl_devno; IPL_PARMBLOCK_ORIGIN) #define IPL_PARMBLOCK_SIZE (IPL_PARMBLOCK_START->hdr.length) -#else +#else /* __ASSEMBLY__ */ #ifndef __s390x__ #define IPL_DEVICE 0x10404 @@ -127,6 +129,6 @@ extern u16 ipl_devno; #endif /* __s390x__ */ #define COMMAND_LINE 0x10480 -#endif - -#endif +#endif /* __ASSEMBLY__ */ +#endif /* __KERNEL__ */ +#endif /* _ASM_S390_SETUP_H */ From ef1bea9e2a5a72d2c3362522e0a09099406732ff Mon Sep 17 00:00:00 2001 From: Eric Paris Date: Sat, 11 Feb 2006 17:56:04 -0800 Subject: [PATCH 17/48] [PATCH] s390: remove one set of brackets in __constant_test_bit() Right now in __constant_test_bit for the s390 there is an extra set of () surrounding the calculation. This patch simply removes one set of () that is surrounding the whole clause. Signed-off-by: Eric Paris Signed-off-by: Heiko Carstens Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- include/asm-s390/bitops.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/include/asm-s390/bitops.h b/include/asm-s390/bitops.h index 61232760cc3b..3628899f48bb 100644 --- a/include/asm-s390/bitops.h +++ b/include/asm-s390/bitops.h @@ -518,8 +518,8 @@ static inline int __test_bit(unsigned long nr, const volatile unsigned long *ptr static inline int __constant_test_bit(unsigned long nr, const volatile unsigned long *addr) { - return ((((volatile char *) addr) - [(nr^(__BITOPS_WORDSIZE-8))>>3] & (1<<(nr&7)))) != 0; + return (((volatile char *) addr) + [(nr^(__BITOPS_WORDSIZE-8))>>3] & (1<<(nr&7))) != 0; } #define test_bit(nr,addr) \ From 1d30883942cfe8a1e3f88f8b7f4c292aeba3db5a Mon Sep 17 00:00:00 2001 From: Andrew Morton Date: Sat, 11 Feb 2006 17:56:05 -0800 Subject: [PATCH 18/48] [PATCH] tipar fixes - tipar_open(): fix unsigned comparison - tipar_open(): don't permit NULL pardevice (probably unneeded given the above fix). - tipar_init_module(): handle the situation where parport_register_driver() failed to register any devices (parport_register_driver() drops the ->attach return value on the floor). This probably makes fixes #1 and #2 unneeded. - tipar_init_module(): fix various error-path resource leaks. Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/char/tipar.c | 15 ++++++++++++--- 1 file changed, 12 insertions(+), 3 deletions(-) diff --git a/drivers/char/tipar.c b/drivers/char/tipar.c index 41a94bc79f67..eb2eb3e12d6a 100644 --- a/drivers/char/tipar.c +++ b/drivers/char/tipar.c @@ -250,12 +250,17 @@ tipar_open(struct inode *inode, struct file *file) { unsigned int minor = iminor(inode) - TIPAR_MINOR; - if (minor > tp_count - 1) + if (tp_count == 0 || minor > tp_count - 1) return -ENXIO; if (test_and_set_bit(minor, &opened)) return -EBUSY; + if (!table[minor].dev) { + printk(KERN_ERR "%s: NULL device for minor %u\n", + __FUNCTION__, minor); + return -ENXIO; + } parport_claim_or_block(table[minor].dev); init_ti_parallel(minor); parport_release(table[minor].dev); @@ -510,16 +515,20 @@ tipar_init_module(void) err = PTR_ERR(tipar_class); goto out_chrdev; } - if (parport_register_driver(&tipar_driver)) { + if (parport_register_driver(&tipar_driver) || tp_count == 0) { printk(KERN_ERR "tipar: unable to register with parport\n"); err = -EIO; - goto out; + goto out_class; } err = 0; goto out; +out_class: + class_destroy(tipar_class); + out_chrdev: + devfs_remove("ticables/par"); unregister_chrdev(TIPAR_MAJOR, "tipar"); out: return err; From 891e5e5edaf13216f9f4c2710aebd066b1d98583 Mon Sep 17 00:00:00 2001 From: Adrian Bunk Date: Sat, 11 Feb 2006 17:56:05 -0800 Subject: [PATCH 19/48] [PATCH] drivers/video/Kconfig: remove unused BUS_I2C option The BUS_I2C option is neither available (since there is no VISWS option in the kernel) nor does it have any effect - so why not remove it? Based on a report by Jean-Luc Leger . Signed-off-by: Adrian Bunk Cc: "Antonino A. Daplas" Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/video/Kconfig | 5 ----- 1 file changed, 5 deletions(-) diff --git a/drivers/video/Kconfig b/drivers/video/Kconfig index 3e153d313bb0..e64ed16bd42f 100644 --- a/drivers/video/Kconfig +++ b/drivers/video/Kconfig @@ -525,11 +525,6 @@ config FB_GBE_MEM This is the amount of memory reserved for the framebuffer, which can be any value between 1MB and 8MB. -config BUS_I2C - bool - depends on (FB = y) && VISWS - default y - config FB_SUN3 bool "Sun3 framebuffer support" depends on (FB = y) && (SUN3 || SUN3X) && BROKEN From bc7fc0601b3eb2254f080492f3fd69e319ed32d0 Mon Sep 17 00:00:00 2001 From: "Antonino A. Daplas" Date: Sat, 11 Feb 2006 17:56:07 -0800 Subject: [PATCH 20/48] [PATCH] nvidiafb: Add support for Geforce4 MX 4000 Add support for Geforce4 MX 4000 (0x185) Signed-off-by: Antonino Daplas Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/video/nvidia/nvidia.c | 2 ++ include/linux/pci_ids.h | 1 + 2 files changed, 3 insertions(+) diff --git a/drivers/video/nvidia/nvidia.c b/drivers/video/nvidia/nvidia.c index dbcb8962e57d..a7c4e5e8ead6 100644 --- a/drivers/video/nvidia/nvidia.c +++ b/drivers/video/nvidia/nvidia.c @@ -138,6 +138,8 @@ static struct pci_device_id nvidiafb_pci_tbl[] = { PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0}, {PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE4_MX_420_8X, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0}, + {PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE4_MX_4000, + PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0}, {PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE4_448_GO, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0}, {PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE4_488_GO, diff --git a/include/linux/pci_ids.h b/include/linux/pci_ids.h index 7a61ccdcbc4b..82b83da25d77 100644 --- a/include/linux/pci_ids.h +++ b/include/linux/pci_ids.h @@ -1087,6 +1087,7 @@ #define PCI_DEVICE_ID_NVIDIA_GEFORCE4_MX_440_8X 0x0181 #define PCI_DEVICE_ID_NVIDIA_GEFORCE4_MX_440SE_8X 0x0182 #define PCI_DEVICE_ID_NVIDIA_GEFORCE4_MX_420_8X 0x0183 +#define PCI_DEVICE_ID_NVIDIA_GEFORCE4_MX_4000 0x0185 #define PCI_DEVICE_ID_NVIDIA_GEFORCE4_448_GO 0x0186 #define PCI_DEVICE_ID_NVIDIA_GEFORCE4_488_GO 0x0187 #define PCI_DEVICE_ID_NVIDIA_QUADRO4_580_XGL 0x0188 From bc6d7fdf460ec5292d66bb551dbfa49ca682bebf Mon Sep 17 00:00:00 2001 From: Andrew Morton Date: Sat, 11 Feb 2006 17:56:08 -0800 Subject: [PATCH 21/48] [PATCH] fbdev: video_setup() warning fix drivers/video/fbmem.c:1567: warning: 'video_setup' defined but not used Acked-by: "Antonino A. Daplas" Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/video/fbmem.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/drivers/video/fbmem.c b/drivers/video/fbmem.c index d2dede6ed3e5..996c7b58564e 100644 --- a/drivers/video/fbmem.c +++ b/drivers/video/fbmem.c @@ -1550,6 +1550,7 @@ int fb_get_options(char *name, char **option) return retval; } +#ifndef MODULE /** * video_setup - process command line options * @options: string of options @@ -1593,6 +1594,7 @@ static int __init video_setup(char *options) return 0; } __setup("video=", video_setup); +#endif /* * Visible symbols for modules From 3a69e5791379a7c7d23c531a7679428300bb5072 Mon Sep 17 00:00:00 2001 From: Ian Campbell Date: Mon, 7 Nov 2005 10:21:24 +0000 Subject: [PATCH 22/48] [WATCHDOG] sa1100_wdt.c sparse clean (2) The following makes drivers/char/watchdog/sa1100_wdt.c sparse clean. (similar to the other watchdog drivers) Signed-off-by: Ian Campbell Signed-off-by: Wim Van Sebroeck --- drivers/char/watchdog/sa1100_wdt.c | 12 +++++++----- 1 file changed, 7 insertions(+), 5 deletions(-) diff --git a/drivers/char/watchdog/sa1100_wdt.c b/drivers/char/watchdog/sa1100_wdt.c index b474ea52d6e8..522a9370db94 100644 --- a/drivers/char/watchdog/sa1100_wdt.c +++ b/drivers/char/watchdog/sa1100_wdt.c @@ -93,23 +93,25 @@ static int sa1100dog_ioctl(struct inode *inode, struct file *file, { int ret = -ENOIOCTLCMD; int time; + void __user *argp = (void __user *)arg; + int __user *p = argp; switch (cmd) { case WDIOC_GETSUPPORT: - ret = copy_to_user((struct watchdog_info __user *)arg, &ident, + ret = copy_to_user(argp, &ident, sizeof(ident)) ? -EFAULT : 0; break; case WDIOC_GETSTATUS: - ret = put_user(0, (int __user *)arg); + ret = put_user(0, p); break; case WDIOC_GETBOOTSTATUS: - ret = put_user(boot_status, (int __user *)arg); + ret = put_user(boot_status, p); break; case WDIOC_SETTIMEOUT: - ret = get_user(time, (int __user *)arg); + ret = get_user(time, p); if (ret) break; @@ -123,7 +125,7 @@ static int sa1100dog_ioctl(struct inode *inode, struct file *file, /*fall through*/ case WDIOC_GETTIMEOUT: - ret = put_user(pre_margin / OSCR_FREQ, (int __user *)arg); + ret = put_user(pre_margin / OSCR_FREQ, p); break; case WDIOC_KEEPALIVE: From fd41fa616f21efc36eb80696475ceb33ea047a6a Mon Sep 17 00:00:00 2001 From: Wim Van Sebroeck Date: Sat, 10 Dec 2005 14:22:37 +0100 Subject: [PATCH 23/48] [WATCHDOG] pcwd.c add comments + tabs add extra comments for the include files changes spaces by tabs where it is appropriate. Signed-off-by: Wim Van Sebroeck --- drivers/char/watchdog/pcwd.c | 71 +++++++++++++++++++----------------- 1 file changed, 37 insertions(+), 34 deletions(-) diff --git a/drivers/char/watchdog/pcwd.c b/drivers/char/watchdog/pcwd.c index 37c9e13ad3ac..85c94b205df1 100644 --- a/drivers/char/watchdog/pcwd.c +++ b/drivers/char/watchdog/pcwd.c @@ -49,27 +49,30 @@ * More info available at http://www.berkprod.com/ or http://www.pcwatchdog.com/ */ -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include +#include /* For CONFIG_WATCHDOG_NOWAYOUT/... */ +#include /* For module specific items */ +#include /* For new moduleparam's */ +#include /* For standard types (like size_t) */ +#include /* For the -ENODEV/... values */ +#include /* For printk/panic/... */ +#include /* For mdelay function */ +#include /* For timer related operations */ +#include /* For jiffies stuff */ +#include /* For MODULE_ALIAS_MISCDEV(WATCHDOG_MINOR) */ +#include /* For the watchdog specific items */ +#include /* For notifier support */ +#include /* For reboot_notifier stuff */ +#include /* For __init/__exit/... */ +#include /* For file operations */ +#include /* For io-port access */ +#include /* For spin_lock/spin_unlock/... */ #include /* TASK_INTERRUPTIBLE, set_current_state() and friends */ -#include -#include +#include /* For kmalloc */ +#include /* For copy_to_user/put_user/... */ +#include /* For inb/outb/... */ + +/* Module and version information */ #define WD_VER "1.16 (06/12/2004)" #define PFX "pcwd: " @@ -84,7 +87,7 @@ #define PCWD_REVISION_C 2 /* - * These are the defines that describe the control status bits for the + * These are the defines that describe the control status #1 bits for the * PC Watchdog card, revision A. */ #define WD_WDRST 0x01 /* Previously reset state */ @@ -94,7 +97,7 @@ #define WD_SRLY2 0x80 /* Software external relay triggered */ /* - * These are the defines that describe the control status bits for the + * These are the defines that describe the control status #1 bits for the * PC Watchdog card, revision C. */ #define WD_REVC_WTRP 0x01 /* Watchdog Trip status */ @@ -106,15 +109,15 @@ #define ISA_COMMAND_TIMEOUT 1000 /* Watchdog's internal commands */ -#define CMD_ISA_IDLE 0x00 -#define CMD_ISA_VERSION_INTEGER 0x01 -#define CMD_ISA_VERSION_TENTH 0x02 -#define CMD_ISA_VERSION_HUNDRETH 0x03 -#define CMD_ISA_VERSION_MINOR 0x04 -#define CMD_ISA_SWITCH_SETTINGS 0x05 -#define CMD_ISA_DELAY_TIME_2SECS 0x0A -#define CMD_ISA_DELAY_TIME_4SECS 0x0B -#define CMD_ISA_DELAY_TIME_8SECS 0x0C +#define CMD_ISA_IDLE 0x00 +#define CMD_ISA_VERSION_INTEGER 0x01 +#define CMD_ISA_VERSION_TENTH 0x02 +#define CMD_ISA_VERSION_HUNDRETH 0x03 +#define CMD_ISA_VERSION_MINOR 0x04 +#define CMD_ISA_SWITCH_SETTINGS 0x05 +#define CMD_ISA_DELAY_TIME_2SECS 0x0A +#define CMD_ISA_DELAY_TIME_4SECS 0x0B +#define CMD_ISA_DELAY_TIME_8SECS 0x0C /* * We are using an kernel timer to do the pinging of the watchdog @@ -767,10 +770,10 @@ static int __devinit pcwatchdog_init(int base_addr) printk(KERN_INFO PFX "No previous trip detected - Cold boot or reset\n"); /* Check that the heartbeat value is within it's range ; if not reset to the default */ - if (pcwd_set_heartbeat(heartbeat)) { - pcwd_set_heartbeat(WATCHDOG_HEARTBEAT); - printk(KERN_INFO PFX "heartbeat value must be 2<=heartbeat<=7200, using %d\n", - WATCHDOG_HEARTBEAT); + if (pcwd_set_heartbeat(heartbeat)) { + pcwd_set_heartbeat(WATCHDOG_HEARTBEAT); + printk(KERN_INFO PFX "heartbeat value must be 2<=heartbeat<=7200, using %d\n", + WATCHDOG_HEARTBEAT); } ret = register_reboot_notifier(&pcwd_notifier); From f1c3a0567aa5086e755e58385740f9ece911c06e Mon Sep 17 00:00:00 2001 From: Wim Van Sebroeck Date: Sat, 10 Dec 2005 14:36:24 +0100 Subject: [PATCH 24/48] [WATCHDOG] pcwd.c card_found-- fix. When doing a __devexit from a card we should also decrement the cards_found counter. Signed-off-by: Wim Van Sebroeck --- drivers/char/watchdog/pcwd.c | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/char/watchdog/pcwd.c b/drivers/char/watchdog/pcwd.c index 85c94b205df1..3329cbffdb34 100644 --- a/drivers/char/watchdog/pcwd.c +++ b/drivers/char/watchdog/pcwd.c @@ -828,6 +828,7 @@ static void __devexit pcwatchdog_exit(void) unregister_reboot_notifier(&pcwd_notifier); release_region(current_readport, (revision == PCWD_REVISION_A) ? 2 : 4); current_readport = 0x0000; + cards_found--; } /* From a2be8786006ec0d21dcb1d322fc480b85ea82c66 Mon Sep 17 00:00:00 2001 From: Wim Van Sebroeck Date: Mon, 9 Jan 2006 21:53:33 +0100 Subject: [PATCH 25/48] [WATCHDOG] pcwd.c private data struct patch more private data of the card to one struct. Signed-off-by: Wim Van Sebroeck --- drivers/char/watchdog/pcwd.c | 206 ++++++++++++++++++----------------- 1 file changed, 104 insertions(+), 102 deletions(-) diff --git a/drivers/char/watchdog/pcwd.c b/drivers/char/watchdog/pcwd.c index 3329cbffdb34..1112ec8e61f3 100644 --- a/drivers/char/watchdog/pcwd.c +++ b/drivers/char/watchdog/pcwd.c @@ -73,7 +73,7 @@ #include /* For inb/outb/... */ /* Module and version information */ -#define WD_VER "1.16 (06/12/2004)" +#define WD_VER "1.16 (03/01/2006)" #define PFX "pcwd: " /* @@ -133,15 +133,17 @@ static int cards_found; /* internal variables */ static atomic_t open_allowed = ATOMIC_INIT(1); static char expect_close; -static struct timer_list timer; -static unsigned long next_heartbeat; static int temp_panic; -static int revision; /* The card's revision */ -static int supports_temp; /* Wether or not the card has a temperature device */ -static int command_mode; /* Wether or not the card is in command mode */ -static int initial_status; /* The card's boot status */ -static int current_readport; /* The cards I/O address */ -static spinlock_t io_lock; +static struct { /* this is private data for each ISA-PC watchdog card */ + int revision; /* The card's revision */ + int supports_temp; /* Wether or not the card has a temperature device */ + int command_mode; /* Wether or not the card is in command mode */ + int boot_status; /* The card's boot status */ + int io_addr; /* The cards I/O address */ + spinlock_t io_lock; /* the lock for io operations */ + struct timer_list timer; /* The timer that pings the watchdog */ + unsigned long next_heartbeat; /* the next_heartbeat for the timer */ +} pcwd_private; /* module parameters */ #define WATCHDOG_HEARTBEAT 60 /* 60 sec default heartbeat */ @@ -165,13 +167,13 @@ static int send_isa_command(int cmd) /* The WCMD bit must be 1 and the command is only 4 bits in size */ control_status = (cmd & 0x0F) | 0x80; - outb_p(control_status, current_readport + 2); + outb_p(control_status, pcwd_private.io_addr + 2); udelay(ISA_COMMAND_TIMEOUT); - port0 = inb_p(current_readport); + port0 = inb_p(pcwd_private.io_addr); for (i = 0; i < 25; ++i) { last_port0 = port0; - port0 = inb_p(current_readport); + port0 = inb_p(pcwd_private.io_addr); if (port0 == last_port0) break; /* Data is stable */ @@ -187,7 +189,7 @@ static int set_command_mode(void) int i, found=0, count=0; /* Set the card into command mode */ - spin_lock(&io_lock); + spin_lock(&pcwd_private.io_lock); while ((!found) && (count < 3)) { i = send_isa_command(CMD_ISA_IDLE); @@ -195,15 +197,15 @@ static int set_command_mode(void) found = 1; else if (i == 0xF3) { /* Card does not like what we've done to it */ - outb_p(0x00, current_readport + 2); + outb_p(0x00, pcwd_private.io_addr + 2); udelay(1200); /* Spec says wait 1ms */ - outb_p(0x00, current_readport + 2); + outb_p(0x00, pcwd_private.io_addr + 2); udelay(ISA_COMMAND_TIMEOUT); } count++; } - spin_unlock(&io_lock); - command_mode = found; + spin_unlock(&pcwd_private.io_lock); + pcwd_private.command_mode = found; return(found); } @@ -211,12 +213,12 @@ static int set_command_mode(void) static void unset_command_mode(void) { /* Set the card into normal mode */ - spin_lock(&io_lock); - outb_p(0x00, current_readport + 2); + spin_lock(&pcwd_private.io_lock); + outb_p(0x00, pcwd_private.io_addr + 2); udelay(ISA_COMMAND_TIMEOUT); - spin_unlock(&io_lock); + spin_unlock(&pcwd_private.io_lock); - command_mode = 0; + pcwd_private.command_mode = 0; } static void pcwd_timer_ping(unsigned long data) @@ -225,25 +227,25 @@ static void pcwd_timer_ping(unsigned long data) /* If we got a heartbeat pulse within the WDT_INTERVAL * we agree to ping the WDT */ - if(time_before(jiffies, next_heartbeat)) { + if(time_before(jiffies, pcwd_private.next_heartbeat)) { /* Ping the watchdog */ - spin_lock(&io_lock); - if (revision == PCWD_REVISION_A) { + spin_lock(&pcwd_private.io_lock); + if (pcwd_private.revision == PCWD_REVISION_A) { /* Rev A cards are reset by setting the WD_WDRST bit in register 1 */ - wdrst_stat = inb_p(current_readport); + wdrst_stat = inb_p(pcwd_private.io_addr); wdrst_stat &= 0x0F; wdrst_stat |= WD_WDRST; - outb_p(wdrst_stat, current_readport + 1); + outb_p(wdrst_stat, pcwd_private.io_addr + 1); } else { /* Re-trigger watchdog by writing to port 0 */ - outb_p(0x00, current_readport); + outb_p(0x00, pcwd_private.io_addr); } /* Re-set the timer interval */ - mod_timer(&timer, jiffies + WDT_INTERVAL); + mod_timer(&pcwd_private.timer, jiffies + WDT_INTERVAL); - spin_unlock(&io_lock); + spin_unlock(&pcwd_private.io_lock); } else { printk(KERN_WARNING PFX "Heartbeat lost! Will not ping the watchdog\n"); } @@ -253,18 +255,18 @@ static int pcwd_start(void) { int stat_reg; - next_heartbeat = jiffies + (heartbeat * HZ); + pcwd_private.next_heartbeat = jiffies + (heartbeat * HZ); /* Start the timer */ - mod_timer(&timer, jiffies + WDT_INTERVAL); + mod_timer(&pcwd_private.timer, jiffies + WDT_INTERVAL); /* Enable the port */ - if (revision == PCWD_REVISION_C) { - spin_lock(&io_lock); - outb_p(0x00, current_readport + 3); + if (pcwd_private.revision == PCWD_REVISION_C) { + spin_lock(&pcwd_private.io_lock); + outb_p(0x00, pcwd_private.io_addr + 3); udelay(ISA_COMMAND_TIMEOUT); - stat_reg = inb_p(current_readport + 2); - spin_unlock(&io_lock); + stat_reg = inb_p(pcwd_private.io_addr + 2); + spin_unlock(&pcwd_private.io_lock); if (stat_reg & 0x10) { printk(KERN_INFO PFX "Could not start watchdog\n"); return -EIO; @@ -278,17 +280,17 @@ static int pcwd_stop(void) int stat_reg; /* Stop the timer */ - del_timer(&timer); + del_timer(&pcwd_private.timer); /* Disable the board */ - if (revision == PCWD_REVISION_C) { - spin_lock(&io_lock); - outb_p(0xA5, current_readport + 3); + if (pcwd_private.revision == PCWD_REVISION_C) { + spin_lock(&pcwd_private.io_lock); + outb_p(0xA5, pcwd_private.io_addr + 3); udelay(ISA_COMMAND_TIMEOUT); - outb_p(0xA5, current_readport + 3); + outb_p(0xA5, pcwd_private.io_addr + 3); udelay(ISA_COMMAND_TIMEOUT); - stat_reg = inb_p(current_readport + 2); - spin_unlock(&io_lock); + stat_reg = inb_p(pcwd_private.io_addr + 2); + spin_unlock(&pcwd_private.io_lock); if ((stat_reg & 0x10) == 0) { printk(KERN_INFO PFX "Could not stop watchdog\n"); return -EIO; @@ -300,7 +302,7 @@ static int pcwd_stop(void) static int pcwd_keepalive(void) { /* user land ping */ - next_heartbeat = jiffies + (heartbeat * HZ); + pcwd_private.next_heartbeat = jiffies + (heartbeat * HZ); return 0; } @@ -318,23 +320,23 @@ static int pcwd_get_status(int *status) int card_status; *status=0; - spin_lock(&io_lock); - if (revision == PCWD_REVISION_A) + spin_lock(&pcwd_private.io_lock); + if (pcwd_private.revision == PCWD_REVISION_A) /* Rev A cards return status information from * the base register, which is used for the * temperature in other cards. */ - card_status = inb(current_readport); + card_status = inb(pcwd_private.io_addr); else { /* Rev C cards return card status in the base * address + 1 register. And use different bits * to indicate a card initiated reset, and an * over-temperature condition. And the reboot * status can be reset. */ - card_status = inb(current_readport + 1); + card_status = inb(pcwd_private.io_addr + 1); } - spin_unlock(&io_lock); + spin_unlock(&pcwd_private.io_lock); - if (revision == PCWD_REVISION_A) { + if (pcwd_private.revision == PCWD_REVISION_A) { if (card_status & WD_WDRST) *status |= WDIOF_CARDRESET; @@ -363,10 +365,10 @@ static int pcwd_get_status(int *status) static int pcwd_clear_status(void) { - if (revision == PCWD_REVISION_C) { - spin_lock(&io_lock); - outb_p(0x00, current_readport + 1); /* clear reset status */ - spin_unlock(&io_lock); + if (pcwd_private.revision == PCWD_REVISION_C) { + spin_lock(&pcwd_private.io_lock); + outb_p(0x00, pcwd_private.io_addr + 1); /* clear reset status */ + spin_unlock(&pcwd_private.io_lock); } return 0; } @@ -374,20 +376,20 @@ static int pcwd_clear_status(void) static int pcwd_get_temperature(int *temperature) { /* check that port 0 gives temperature info and no command results */ - if (command_mode) + if (pcwd_private.command_mode) return -1; *temperature = 0; - if (!supports_temp) + if (!pcwd_private.supports_temp) return -ENODEV; /* * Convert celsius to fahrenheit, since this was * the decided 'standard' for this return value. */ - spin_lock(&io_lock); - *temperature = ((inb(current_readport)) * 9 / 5) + 32; - spin_unlock(&io_lock); + spin_lock(&pcwd_private.io_lock); + *temperature = ((inb(pcwd_private.io_addr)) * 9 / 5) + 32; + spin_unlock(&pcwd_private.io_lock); return 0; } @@ -428,7 +430,7 @@ static int pcwd_ioctl(struct inode *inode, struct file *file, return put_user(status, argp); case WDIOC_GETBOOTSTATUS: - return put_user(initial_status, argp); + return put_user(pcwd_private.boot_status, argp); case WDIOC_GETTEMP: if (pcwd_get_temperature(&temperature)) @@ -437,7 +439,7 @@ static int pcwd_ioctl(struct inode *inode, struct file *file, return put_user(temperature, argp); case WDIOC_SETOPTIONS: - if (revision == PCWD_REVISION_C) + if (pcwd_private.revision == PCWD_REVISION_C) { if(copy_from_user(&rv, argp, sizeof(int))) return -EFAULT; @@ -553,7 +555,7 @@ static ssize_t pcwd_temp_read(struct file *file, char __user *buf, size_t count, static int pcwd_temp_open(struct inode *inode, struct file *file) { - if (!supports_temp) + if (!pcwd_private.supports_temp) return -ENODEV; return nonseekable_open(inode, file); @@ -621,21 +623,21 @@ static struct notifier_block pcwd_notifier = { static inline void get_support(void) { - if (inb(current_readport) != 0xF0) - supports_temp = 1; + if (inb(pcwd_private.io_addr) != 0xF0) + pcwd_private.supports_temp = 1; } static inline int get_revision(void) { int r = PCWD_REVISION_C; - spin_lock(&io_lock); + spin_lock(&pcwd_private.io_lock); /* REV A cards use only 2 io ports; test * presumes a floating bus reads as 0xff. */ - if ((inb(current_readport + 2) == 0xFF) || - (inb(current_readport + 3) == 0xFF)) + if ((inb(pcwd_private.io_addr + 2) == 0xFF) || + (inb(pcwd_private.io_addr + 3) == 0xFF)) r=PCWD_REVISION_A; - spin_unlock(&io_lock); + spin_unlock(&pcwd_private.io_lock); return r; } @@ -695,32 +697,32 @@ static int __devinit pcwatchdog_init(int base_addr) printk(KERN_ERR PFX "No I/O-Address for card detected\n"); return -ENODEV; } - current_readport = base_addr; + pcwd_private.io_addr = base_addr; /* Check card's revision */ - revision = get_revision(); + pcwd_private.revision = get_revision(); - if (!request_region(current_readport, (revision == PCWD_REVISION_A) ? 2 : 4, "PCWD")) { + if (!request_region(pcwd_private.io_addr, (pcwd_private.revision == PCWD_REVISION_A) ? 2 : 4, "PCWD")) { printk(KERN_ERR PFX "I/O address 0x%04x already in use\n", - current_readport); - current_readport = 0x0000; + pcwd_private.io_addr); + pcwd_private.io_addr = 0x0000; return -EIO; } /* Initial variables */ - supports_temp = 0; + pcwd_private.supports_temp = 0; temp_panic = 0; - initial_status = 0x0000; + pcwd_private.boot_status = 0x0000; /* get the boot_status */ - pcwd_get_status(&initial_status); + pcwd_get_status(&pcwd_private.boot_status); /* clear the "card caused reboot" flag */ pcwd_clear_status(); - init_timer(&timer); - timer.function = pcwd_timer_ping; - timer.data = 0; + init_timer(&pcwd_private.timer); + pcwd_private.timer.function = pcwd_timer_ping; + pcwd_private.timer.data = 0; /* Disable the board */ pcwd_stop(); @@ -729,12 +731,12 @@ static int __devinit pcwatchdog_init(int base_addr) get_support(); /* Get some extra info from the hardware (in command/debug/diag mode) */ - if (revision == PCWD_REVISION_A) - printk(KERN_INFO PFX "ISA-PC Watchdog (REV.A) detected at port 0x%04x\n", current_readport); - else if (revision == PCWD_REVISION_C) { + if (pcwd_private.revision == PCWD_REVISION_A) + printk(KERN_INFO PFX "ISA-PC Watchdog (REV.A) detected at port 0x%04x\n", pcwd_private.io_addr); + else if (pcwd_private.revision == PCWD_REVISION_C) { firmware = get_firmware(); printk(KERN_INFO PFX "ISA-PC Watchdog (REV.C) detected at port 0x%04x (Firmware version: %s)\n", - current_readport, firmware); + pcwd_private.io_addr, firmware); kfree(firmware); option_switches = get_option_switches(); printk(KERN_INFO PFX "Option switches (0x%02x): Temperature Reset Enable=%s, Power On Delay=%s\n", @@ -750,23 +752,23 @@ static int __devinit pcwatchdog_init(int base_addr) } else { /* Should NEVER happen, unless get_revision() fails. */ printk(KERN_INFO PFX "Unable to get revision\n"); - release_region(current_readport, (revision == PCWD_REVISION_A) ? 2 : 4); - current_readport = 0x0000; + release_region(pcwd_private.io_addr, (pcwd_private.revision == PCWD_REVISION_A) ? 2 : 4); + pcwd_private.io_addr = 0x0000; return -1; } - if (supports_temp) + if (pcwd_private.supports_temp) printk(KERN_INFO PFX "Temperature Option Detected\n"); - if (initial_status & WDIOF_CARDRESET) + if (pcwd_private.boot_status & WDIOF_CARDRESET) printk(KERN_INFO PFX "Previous reboot was caused by the card\n"); - if (initial_status & WDIOF_OVERHEAT) { + if (pcwd_private.boot_status & WDIOF_OVERHEAT) { printk(KERN_EMERG PFX "Card senses a CPU Overheat. Panicking!\n"); printk(KERN_EMERG PFX "CPU Overheat\n"); } - if (initial_status == 0) + if (pcwd_private.boot_status == 0) printk(KERN_INFO PFX "No previous trip detected - Cold boot or reset\n"); /* Check that the heartbeat value is within it's range ; if not reset to the default */ @@ -780,19 +782,19 @@ static int __devinit pcwatchdog_init(int base_addr) if (ret) { printk(KERN_ERR PFX "cannot register reboot notifier (err=%d)\n", ret); - release_region(current_readport, (revision == PCWD_REVISION_A) ? 2 : 4); - current_readport = 0x0000; + release_region(pcwd_private.io_addr, (pcwd_private.revision == PCWD_REVISION_A) ? 2 : 4); + pcwd_private.io_addr = 0x0000; return ret; } - if (supports_temp) { + if (pcwd_private.supports_temp) { ret = misc_register(&temp_miscdev); if (ret) { printk(KERN_ERR PFX "cannot register miscdev on minor=%d (err=%d)\n", TEMP_MINOR, ret); unregister_reboot_notifier(&pcwd_notifier); - release_region(current_readport, (revision == PCWD_REVISION_A) ? 2 : 4); - current_readport = 0x0000; + release_region(pcwd_private.io_addr, (pcwd_private.revision == PCWD_REVISION_A) ? 2 : 4); + pcwd_private.io_addr = 0x0000; return ret; } } @@ -801,11 +803,11 @@ static int __devinit pcwatchdog_init(int base_addr) if (ret) { printk(KERN_ERR PFX "cannot register miscdev on minor=%d (err=%d)\n", WATCHDOG_MINOR, ret); - if (supports_temp) + if (pcwd_private.supports_temp) misc_deregister(&temp_miscdev); unregister_reboot_notifier(&pcwd_notifier); - release_region(current_readport, (revision == PCWD_REVISION_A) ? 2 : 4); - current_readport = 0x0000; + release_region(pcwd_private.io_addr, (pcwd_private.revision == PCWD_REVISION_A) ? 2 : 4); + pcwd_private.io_addr = 0x0000; return ret; } @@ -823,11 +825,11 @@ static void __devexit pcwatchdog_exit(void) /* Deregister */ misc_deregister(&pcwd_miscdev); - if (supports_temp) + if (pcwd_private.supports_temp) misc_deregister(&temp_miscdev); unregister_reboot_notifier(&pcwd_notifier); - release_region(current_readport, (revision == PCWD_REVISION_A) ? 2 : 4); - current_readport = 0x0000; + release_region(pcwd_private.io_addr, (pcwd_private.revision == PCWD_REVISION_A) ? 2 : 4); + pcwd_private.io_addr = 0x0000; cards_found--; } @@ -891,7 +893,7 @@ static int __init pcwd_init_module(void) { int i, found = 0; - spin_lock_init(&io_lock); + spin_lock_init(&pcwd_private.io_lock); for (i = 0; pcwd_ioports[i] != 0; i++) { if (pcwd_checkcard(pcwd_ioports[i])) { @@ -910,7 +912,7 @@ static int __init pcwd_init_module(void) static void __exit pcwd_cleanup_module(void) { - if (current_readport) + if (pcwd_private.io_addr) pcwatchdog_exit(); return; } From 8f0235dccc3f7bffc32abcef2aec3d1b15c61927 Mon Sep 17 00:00:00 2001 From: Wim Van Sebroeck Date: Mon, 9 Jan 2006 21:56:09 +0100 Subject: [PATCH 26/48] [WATCHDOG] pcwd.c Control Status #2 patch Add Control Status #2 bits (with defines) Signed-off-by: Wim Van Sebroeck --- drivers/char/watchdog/pcwd.c | 24 +++++++++++++----------- 1 file changed, 13 insertions(+), 11 deletions(-) diff --git a/drivers/char/watchdog/pcwd.c b/drivers/char/watchdog/pcwd.c index 1112ec8e61f3..0635cd724365 100644 --- a/drivers/char/watchdog/pcwd.c +++ b/drivers/char/watchdog/pcwd.c @@ -87,22 +87,24 @@ #define PCWD_REVISION_C 2 /* - * These are the defines that describe the control status #1 bits for the - * PC Watchdog card, revision A. - */ + * These are the defines that describe the control status bits for the + * PCI-PC Watchdog card. +*/ +/* Port 1 : Control Status #1 for the PC Watchdog card, revision A. */ #define WD_WDRST 0x01 /* Previously reset state */ #define WD_T110 0x02 /* Temperature overheat sense */ #define WD_HRTBT 0x04 /* Heartbeat sense */ #define WD_RLY2 0x08 /* External relay triggered */ #define WD_SRLY2 0x80 /* Software external relay triggered */ - -/* - * These are the defines that describe the control status #1 bits for the - * PC Watchdog card, revision C. - */ +/* Port 1 : Control Status #1 for the PC Watchdog card, revision C. */ #define WD_REVC_WTRP 0x01 /* Watchdog Trip status */ #define WD_REVC_HRBT 0x02 /* Watchdog Heartbeat */ #define WD_REVC_TTRP 0x04 /* Temperature Trip status */ +/* Port 2 : Control Status #2 */ +#define WD_WDIS 0x10 /* Watchdog Disabled */ +#define WD_ENTP 0x20 /* Watchdog Enable Temperature Trip */ +#define WD_SSEL 0x40 /* Watchdog Switch Select (1:SW1 <-> 0:SW2) */ +#define WD_WCMD 0x80 /* Watchdog Command Mode */ /* max. time we give an ISA watchdog card to process a command */ /* 500ms for each 4 bit response (according to spec.) */ @@ -166,7 +168,7 @@ static int send_isa_command(int cmd) int port0, last_port0; /* Double read for stabilising */ /* The WCMD bit must be 1 and the command is only 4 bits in size */ - control_status = (cmd & 0x0F) | 0x80; + control_status = (cmd & 0x0F) | WD_WCMD; outb_p(control_status, pcwd_private.io_addr + 2); udelay(ISA_COMMAND_TIMEOUT); @@ -267,7 +269,7 @@ static int pcwd_start(void) udelay(ISA_COMMAND_TIMEOUT); stat_reg = inb_p(pcwd_private.io_addr + 2); spin_unlock(&pcwd_private.io_lock); - if (stat_reg & 0x10) { + if (stat_reg & WD_WDIS) { printk(KERN_INFO PFX "Could not start watchdog\n"); return -EIO; } @@ -291,7 +293,7 @@ static int pcwd_stop(void) udelay(ISA_COMMAND_TIMEOUT); stat_reg = inb_p(pcwd_private.io_addr + 2); spin_unlock(&pcwd_private.io_lock); - if ((stat_reg & 0x10) == 0) { + if ((stat_reg & WD_WDIS) == 0) { printk(KERN_INFO PFX "Could not stop watchdog\n"); return -EIO; } From 85875211acc94ecb76fe04fbebc6aca12b6da60d Mon Sep 17 00:00:00 2001 From: Wim Van Sebroeck Date: Mon, 9 Jan 2006 21:59:39 +0100 Subject: [PATCH 27/48] [WATCHDOG] pcwd.c move get_support to pcwd_check_temperature_support Rename get_support function to pcwd_check_temperature_support so that it is clearer what the function does. Signed-off-by: Wim Van Sebroeck --- drivers/char/watchdog/pcwd.c | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/drivers/char/watchdog/pcwd.c b/drivers/char/watchdog/pcwd.c index 0635cd724365..0549b2e89966 100644 --- a/drivers/char/watchdog/pcwd.c +++ b/drivers/char/watchdog/pcwd.c @@ -223,6 +223,12 @@ static void unset_command_mode(void) pcwd_private.command_mode = 0; } +static inline void pcwd_check_temperature_support(void) +{ + if (inb(pcwd_private.io_addr) != 0xF0) + pcwd_private.supports_temp = 1; +} + static void pcwd_timer_ping(unsigned long data) { int wdrst_stat; @@ -623,12 +629,6 @@ static struct notifier_block pcwd_notifier = { * Init & exit routines */ -static inline void get_support(void) -{ - if (inb(pcwd_private.io_addr) != 0xF0) - pcwd_private.supports_temp = 1; -} - static inline int get_revision(void) { int r = PCWD_REVISION_C; @@ -730,7 +730,7 @@ static int __devinit pcwatchdog_init(int base_addr) pcwd_stop(); /* Check whether or not the card supports the temperature device */ - get_support(); + pcwd_check_temperature_support(); /* Get some extra info from the hardware (in command/debug/diag mode) */ if (pcwd_private.revision == PCWD_REVISION_A) From af3b38d99d7d52340cf59a06ff90d90e0fa25b6d Mon Sep 17 00:00:00 2001 From: Wim Van Sebroeck Date: Mon, 9 Jan 2006 22:03:41 +0100 Subject: [PATCH 28/48] [WATCHDOG] pcwd.c show card info patch Put all code for showing the card's boot info in one sub-routine. Signed-off-by: Wim Van Sebroeck --- drivers/char/watchdog/pcwd.c | 157 ++++++++++++++++++----------------- 1 file changed, 79 insertions(+), 78 deletions(-) diff --git a/drivers/char/watchdog/pcwd.c b/drivers/char/watchdog/pcwd.c index 0549b2e89966..f8f80d52d4de 100644 --- a/drivers/char/watchdog/pcwd.c +++ b/drivers/char/watchdog/pcwd.c @@ -229,6 +229,83 @@ static inline void pcwd_check_temperature_support(void) pcwd_private.supports_temp = 1; } +static inline char *get_firmware(void) +{ + int one, ten, hund, minor; + char *ret; + + ret = kmalloc(6, GFP_KERNEL); + if(ret == NULL) + return NULL; + + if (set_command_mode()) { + one = send_isa_command(CMD_ISA_VERSION_INTEGER); + ten = send_isa_command(CMD_ISA_VERSION_TENTH); + hund = send_isa_command(CMD_ISA_VERSION_HUNDRETH); + minor = send_isa_command(CMD_ISA_VERSION_MINOR); + sprintf(ret, "%c.%c%c%c", one, ten, hund, minor); + } + else + sprintf(ret, "ERROR"); + + unset_command_mode(); + return(ret); +} + +static inline int pcwd_get_option_switches(void) +{ + int option_switches=0; + + if (set_command_mode()) { + /* Get switch settings */ + option_switches = send_isa_command(CMD_ISA_SWITCH_SETTINGS); + } + + unset_command_mode(); + return(option_switches); +} + +static void pcwd_show_card_info(void) +{ + char *firmware; + int option_switches; + + /* Get some extra info from the hardware (in command/debug/diag mode) */ + if (pcwd_private.revision == PCWD_REVISION_A) + printk(KERN_INFO PFX "ISA-PC Watchdog (REV.A) detected at port 0x%04x\n", pcwd_private.io_addr); + else if (pcwd_private.revision == PCWD_REVISION_C) { + firmware = get_firmware(); + printk(KERN_INFO PFX "ISA-PC Watchdog (REV.C) detected at port 0x%04x (Firmware version: %s)\n", + pcwd_private.io_addr, firmware); + kfree(firmware); + option_switches = pcwd_get_option_switches(); + printk(KERN_INFO PFX "Option switches (0x%02x): Temperature Reset Enable=%s, Power On Delay=%s\n", + option_switches, + ((option_switches & 0x10) ? "ON" : "OFF"), + ((option_switches & 0x08) ? "ON" : "OFF")); + + /* Reprogram internal heartbeat to 2 seconds */ + if (set_command_mode()) { + send_isa_command(CMD_ISA_DELAY_TIME_2SECS); + unset_command_mode(); + } + } + + if (pcwd_private.supports_temp) + printk(KERN_INFO PFX "Temperature Option Detected\n"); + + if (pcwd_private.boot_status & WDIOF_CARDRESET) + printk(KERN_INFO PFX "Previous reboot was caused by the card\n"); + + if (pcwd_private.boot_status & WDIOF_OVERHEAT) { + printk(KERN_EMERG PFX "Card senses a CPU Overheat. Panicking!\n"); + printk(KERN_EMERG PFX "CPU Overheat\n"); + } + + if (pcwd_private.boot_status == 0) + printk(KERN_INFO PFX "No previous trip detected - Cold boot or reset\n"); +} + static void pcwd_timer_ping(unsigned long data) { int wdrst_stat; @@ -644,47 +721,9 @@ static inline int get_revision(void) return r; } -static inline char *get_firmware(void) -{ - int one, ten, hund, minor; - char *ret; - - ret = kmalloc(6, GFP_KERNEL); - if(ret == NULL) - return NULL; - - if (set_command_mode()) { - one = send_isa_command(CMD_ISA_VERSION_INTEGER); - ten = send_isa_command(CMD_ISA_VERSION_TENTH); - hund = send_isa_command(CMD_ISA_VERSION_HUNDRETH); - minor = send_isa_command(CMD_ISA_VERSION_MINOR); - sprintf(ret, "%c.%c%c%c", one, ten, hund, minor); - } - else - sprintf(ret, "ERROR"); - - unset_command_mode(); - return(ret); -} - -static inline int get_option_switches(void) -{ - int rv=0; - - if (set_command_mode()) { - /* Get switch settings */ - rv = send_isa_command(CMD_ISA_SWITCH_SETTINGS); - } - - unset_command_mode(); - return(rv); -} - static int __devinit pcwatchdog_init(int base_addr) { int ret; - char *firmware; - int option_switches; cards_found++; if (cards_found == 1) @@ -732,46 +771,8 @@ static int __devinit pcwatchdog_init(int base_addr) /* Check whether or not the card supports the temperature device */ pcwd_check_temperature_support(); - /* Get some extra info from the hardware (in command/debug/diag mode) */ - if (pcwd_private.revision == PCWD_REVISION_A) - printk(KERN_INFO PFX "ISA-PC Watchdog (REV.A) detected at port 0x%04x\n", pcwd_private.io_addr); - else if (pcwd_private.revision == PCWD_REVISION_C) { - firmware = get_firmware(); - printk(KERN_INFO PFX "ISA-PC Watchdog (REV.C) detected at port 0x%04x (Firmware version: %s)\n", - pcwd_private.io_addr, firmware); - kfree(firmware); - option_switches = get_option_switches(); - printk(KERN_INFO PFX "Option switches (0x%02x): Temperature Reset Enable=%s, Power On Delay=%s\n", - option_switches, - ((option_switches & 0x10) ? "ON" : "OFF"), - ((option_switches & 0x08) ? "ON" : "OFF")); - - /* Reprogram internal heartbeat to 2 seconds */ - if (set_command_mode()) { - send_isa_command(CMD_ISA_DELAY_TIME_2SECS); - unset_command_mode(); - } - } else { - /* Should NEVER happen, unless get_revision() fails. */ - printk(KERN_INFO PFX "Unable to get revision\n"); - release_region(pcwd_private.io_addr, (pcwd_private.revision == PCWD_REVISION_A) ? 2 : 4); - pcwd_private.io_addr = 0x0000; - return -1; - } - - if (pcwd_private.supports_temp) - printk(KERN_INFO PFX "Temperature Option Detected\n"); - - if (pcwd_private.boot_status & WDIOF_CARDRESET) - printk(KERN_INFO PFX "Previous reboot was caused by the card\n"); - - if (pcwd_private.boot_status & WDIOF_OVERHEAT) { - printk(KERN_EMERG PFX "Card senses a CPU Overheat. Panicking!\n"); - printk(KERN_EMERG PFX "CPU Overheat\n"); - } - - if (pcwd_private.boot_status == 0) - printk(KERN_INFO PFX "No previous trip detected - Cold boot or reset\n"); + /* Show info about the card itself */ + pcwd_show_card_info(); /* Check that the heartbeat value is within it's range ; if not reset to the default */ if (pcwd_set_heartbeat(heartbeat)) { From a7122f916978a6cd58b765949cb315aabcddf151 Mon Sep 17 00:00:00 2001 From: Wim Van Sebroeck Date: Mon, 9 Jan 2006 22:07:22 +0100 Subject: [PATCH 29/48] [WATCHDOG] pcwd.c - update module version info Update the module version defines. Signed-off-by: Wim Van Sebroeck --- drivers/char/watchdog/pcwd.c | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) diff --git a/drivers/char/watchdog/pcwd.c b/drivers/char/watchdog/pcwd.c index f8f80d52d4de..8d6b249ad66b 100644 --- a/drivers/char/watchdog/pcwd.c +++ b/drivers/char/watchdog/pcwd.c @@ -73,8 +73,13 @@ #include /* For inb/outb/... */ /* Module and version information */ -#define WD_VER "1.16 (03/01/2006)" -#define PFX "pcwd: " +#define WATCHDOG_VERSION "1.16" +#define WATCHDOG_DATE "03 Jan 2006" +#define WATCHDOG_DRIVER_NAME "ISA-PC Watchdog" +#define WATCHDOG_NAME "pcwd" +#define PFX WATCHDOG_NAME ": " +#define DRIVER_VERSION WATCHDOG_DRIVER_NAME " driver, v" WATCHDOG_VERSION " (" WATCHDOG_DATE ")\n" +#define WD_VER WATCHDOG_VERSION " (" WATCHDOG_DATE ")" /* * It should be noted that PCWD_REVISION_B was removed because A and B From 19bf9cbf6b313ae79a0c7278ccaa9c72c86931bd Mon Sep 17 00:00:00 2001 From: Heiko Carstens Date: Sun, 12 Feb 2006 12:35:03 +0100 Subject: [PATCH 30/48] [PATCH] s390: fstatat64 support Add fstatat64 support to s390 in order to follow changes with commit cff2b760096d1e6feaa31948e7af4abbefe47822 . Also fixes compilation for 31 bit. Signed-off-by: Heiko Carstens Signed-off-by: Linus Torvalds --- arch/s390/kernel/compat_linux.c | 20 ++++++++++++++++++++ arch/s390/kernel/compat_wrapper.S | 8 ++++---- arch/s390/kernel/syscalls.S | 2 +- include/asm-s390/unistd.h | 4 +++- 4 files changed, 28 insertions(+), 6 deletions(-) diff --git a/arch/s390/kernel/compat_linux.c b/arch/s390/kernel/compat_linux.c index cc20f0e3a7d3..2d021626c1a6 100644 --- a/arch/s390/kernel/compat_linux.c +++ b/arch/s390/kernel/compat_linux.c @@ -905,6 +905,26 @@ asmlinkage long sys32_fstat64(unsigned long fd, struct stat64_emu31 __user * sta return ret; } +asmlinkage long sys32_fstatat(unsigned int dfd, char __user *filename, + struct stat64_emu31 __user* statbuf, int flag) +{ + struct kstat stat; + int error = -EINVAL; + + if ((flag & ~AT_SYMLINK_NOFOLLOW) != 0) + goto out; + + if (flag & AT_SYMLINK_NOFOLLOW) + error = vfs_lstat_fd(dfd, filename, &stat); + else + error = vfs_stat_fd(dfd, filename, &stat); + + if (!error) + error = cp_stat64(statbuf, &stat); +out: + return error; +} + /* * Linux/i386 didn't use to be able to handle more than * 4 system call parameters, so these system calls used a memory diff --git a/arch/s390/kernel/compat_wrapper.S b/arch/s390/kernel/compat_wrapper.S index 38a6ef5ec624..dd2d6c3e8df8 100644 --- a/arch/s390/kernel/compat_wrapper.S +++ b/arch/s390/kernel/compat_wrapper.S @@ -1523,13 +1523,13 @@ compat_sys_futimesat_wrapper: llgtr %r4,%r4 # struct timeval * jg compat_sys_futimesat - .globl compat_sys_newfstatat_wrapper -compat_sys_newfstatat_wrapper: + .globl sys32_fstatat_wrapper +sys32_fstatat_wrapper: llgfr %r2,%r2 # unsigned int llgtr %r3,%r3 # char * - llgtr %r4,%r4 # struct stat * + llgtr %r4,%r4 # struct stat64 * lgfr %r5,%r5 # int - jg compat_sys_newfstatat + jg sys32_fstatat .globl sys_unlinkat_wrapper sys_unlinkat_wrapper: diff --git a/arch/s390/kernel/syscalls.S b/arch/s390/kernel/syscalls.S index e86a4debb160..84921fe8d266 100644 --- a/arch/s390/kernel/syscalls.S +++ b/arch/s390/kernel/syscalls.S @@ -301,7 +301,7 @@ SYSCALL(sys_mkdirat,sys_mkdirat,sys_mkdirat_wrapper) SYSCALL(sys_mknodat,sys_mknodat,sys_mknodat_wrapper) /* 290 */ SYSCALL(sys_fchownat,sys_fchownat,sys_fchownat_wrapper) SYSCALL(sys_futimesat,sys_futimesat,compat_sys_futimesat_wrapper) -SYSCALL(sys_newfstatat,sys_newfstatat,compat_sys_newfstatat_wrapper) +SYSCALL(sys_fstatat64,sys_newfstatat,sys32_fstatat_wrapper) SYSCALL(sys_unlinkat,sys_unlinkat,sys_unlinkat_wrapper) SYSCALL(sys_renameat,sys_renameat,sys_renameat_wrapper) /* 295 */ SYSCALL(sys_linkat,sys_linkat,sys_linkat_wrapper) diff --git a/include/asm-s390/unistd.h b/include/asm-s390/unistd.h index 0a2f6664c4cf..657d582e8149 100644 --- a/include/asm-s390/unistd.h +++ b/include/asm-s390/unistd.h @@ -285,7 +285,7 @@ #define __NR_mknodat 290 #define __NR_fchownat 291 #define __NR_futimesat 292 -#define __NR_newfstatat 293 +#define __NR_fstatat64 293 #define __NR_unlinkat 294 #define __NR_renameat 295 #define __NR_linkat 296 @@ -359,6 +359,7 @@ #undef __NR_fcntl64 #undef __NR_sendfile64 #undef __NR_fadvise64_64 +#undef __NR_fstatat64 #define __NR_select 142 #define __NR_getrlimit 191 /* SuS compliant getrlimit */ @@ -381,6 +382,7 @@ #define __NR_setgid 214 #define __NR_setfsuid 215 #define __NR_setfsgid 216 +#define __NR_newfstatat 293 #endif From 06ab78222bd119a0a3d8a1f89997ce902a219703 Mon Sep 17 00:00:00 2001 From: Tejun Heo Date: Sun, 12 Feb 2006 15:01:49 +0900 Subject: [PATCH 31/48] [PATCH] libata: allow ->probe_reset to return ATA_DEV_UNKNOWN This patch makes ata_bus_probe() normalize classes[] returned by ->probe_reset such that ->probe_reset can return ATA_DEV_UNKNOWN. This eases implementation of ->probe_reset's which don't directly use ata_drive_probe_reset(). Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik --- drivers/scsi/libata-core.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/drivers/scsi/libata-core.c b/drivers/scsi/libata-core.c index cef85e515c4c..9ddb568267e1 100644 --- a/drivers/scsi/libata-core.c +++ b/drivers/scsi/libata-core.c @@ -1142,8 +1142,11 @@ static int ata_bus_probe(struct ata_port *ap) rc = ap->ops->probe_reset(ap, classes); if (rc == 0) { - for (i = 0; i < ATA_MAX_DEVICES; i++) + for (i = 0; i < ATA_MAX_DEVICES; i++) { + if (classes[i] == ATA_DEV_UNKNOWN) + classes[i] = ATA_DEV_NONE; ap->device[i].class = classes[i]; + } } else { printk(KERN_ERR "ata%u: probe reset failed, " "disabling port\n", ap->id); From 48f80e12abbc1e9034e54614c30e7c304209ce99 Mon Sep 17 00:00:00 2001 From: Tejun Heo Date: Sun, 12 Feb 2006 19:05:07 +0900 Subject: [PATCH 32/48] [PATCH] ata_piix: kill spurious assignment in piix_sata_probe() In piix_sata_probe(), mask gets assigned unnecessarily at the beginning of the function. Kill the assignment. Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik --- drivers/scsi/ata_piix.c | 3 --- 1 file changed, 3 deletions(-) diff --git a/drivers/scsi/ata_piix.c b/drivers/scsi/ata_piix.c index 4933ba284885..8e0529601730 100644 --- a/drivers/scsi/ata_piix.c +++ b/drivers/scsi/ata_piix.c @@ -415,9 +415,6 @@ static int piix_sata_probe (struct ata_port *ap) int orig_mask, mask, i; u8 pcs; - mask = (PIIX_PORT_PRESENT << ap->hard_port_no) | - (PIIX_PORT_ENABLED << ap->hard_port_no); - pci_read_config_byte(pdev, ICH5_PCS, &pcs); orig_mask = (int) pcs & 0xff; From 0e949ff304a7ca07db38c17fbbf3ead1085d7bbf Mon Sep 17 00:00:00 2001 From: Tejun Heo Date: Sun, 12 Feb 2006 22:47:04 +0900 Subject: [PATCH 33/48] [PATCH] libata: implement ata_dev_id_c_string() ata_dev_id_c_string() reads ATA string from the specified offset of the given IDENTIFY PAGE and puts it in the specified buffer in trimmed and NULL-terminated form. The caller must supply a buffer which is one byte larger than the maximum size of the target ID string. Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik --- drivers/scsi/libata-core.c | 29 +++++++++++++++++++++++++++++ include/linux/libata.h | 2 ++ 2 files changed, 31 insertions(+) diff --git a/drivers/scsi/libata-core.c b/drivers/scsi/libata-core.c index 9ddb568267e1..7e410299d67a 100644 --- a/drivers/scsi/libata-core.c +++ b/drivers/scsi/libata-core.c @@ -519,6 +519,34 @@ void ata_dev_id_string(const u16 *id, unsigned char *s, } } +/** + * ata_dev_id_c_string - Convert IDENTIFY DEVICE page into C string + * @id: IDENTIFY DEVICE results we will examine + * @s: string into which data is output + * @ofs: offset into identify device page + * @len: length of string to return. must be an odd number. + * + * This function is identical to ata_dev_id_string except that it + * trims trailing spaces and terminates the resulting string with + * null. @len must be actual maximum length (even number) + 1. + * + * LOCKING: + * caller. + */ +void ata_dev_id_c_string(const u16 *id, unsigned char *s, + unsigned int ofs, unsigned int len) +{ + unsigned char *p; + + WARN_ON(!(len & 1)); + + ata_dev_id_string(id, s, ofs, len - 1); + + p = s + strnlen(s, len - 1); + while (p > s && p[-1] == ' ') + p--; + *p = '\0'; +} /** * ata_noop_dev_select - Select device 0/1 on ATA bus @@ -4905,6 +4933,7 @@ EXPORT_SYMBOL_GPL(ata_scsi_release); EXPORT_SYMBOL_GPL(ata_host_intr); EXPORT_SYMBOL_GPL(ata_dev_classify); EXPORT_SYMBOL_GPL(ata_dev_id_string); +EXPORT_SYMBOL_GPL(ata_dev_id_c_string); EXPORT_SYMBOL_GPL(ata_dev_config); EXPORT_SYMBOL_GPL(ata_scsi_simulate); EXPORT_SYMBOL_GPL(ata_eh_qc_complete); diff --git a/include/linux/libata.h b/include/linux/libata.h index 83a1f2ead861..0853032673b7 100644 --- a/include/linux/libata.h +++ b/include/linux/libata.h @@ -540,6 +540,8 @@ extern void ata_sg_init(struct ata_queued_cmd *qc, struct scatterlist *sg, extern unsigned int ata_dev_classify(const struct ata_taskfile *tf); extern void ata_dev_id_string(const u16 *id, unsigned char *s, unsigned int ofs, unsigned int len); +extern void ata_dev_id_c_string(const u16 *id, unsigned char *s, + unsigned int ofs, unsigned int len); extern void ata_dev_config(struct ata_port *ap, unsigned int i); extern void ata_bmdma_setup (struct ata_queued_cmd *qc); extern void ata_bmdma_start (struct ata_queued_cmd *qc); From 2e02671daa2cd69d93c828c40579bbe953f17210 Mon Sep 17 00:00:00 2001 From: Tejun Heo Date: Sun, 12 Feb 2006 22:47:04 +0900 Subject: [PATCH 34/48] [PATCH] libata: use ata_dev_id_c_string() Use ata_dev_id_c_string() Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik --- drivers/scsi/libata-core.c | 18 ++++-------------- drivers/scsi/libata-scsi.c | 11 ++++------- drivers/scsi/sata_sil.c | 19 +++++-------------- 3 files changed, 13 insertions(+), 35 deletions(-) diff --git a/drivers/scsi/libata-core.c b/drivers/scsi/libata-core.c index 7e410299d67a..1d65f703348e 100644 --- a/drivers/scsi/libata-core.c +++ b/drivers/scsi/libata-core.c @@ -2301,24 +2301,14 @@ static const char * const ata_dma_blacklist [] = { static int ata_dma_blacklisted(const struct ata_device *dev) { - unsigned char model_num[40]; - char *s; - unsigned int len; + unsigned char model_num[41]; int i; - ata_dev_id_string(dev->id, model_num, ATA_ID_PROD_OFS, - sizeof(model_num)); - s = &model_num[0]; - len = strnlen(s, sizeof(model_num)); - - /* ATAPI specifies that empty space is blank-filled; remove blanks */ - while ((len > 0) && (s[len - 1] == ' ')) { - len--; - s[len] = 0; - } + ata_dev_id_c_string(dev->id, model_num, ATA_ID_PROD_OFS, + sizeof(model_num)); for (i = 0; i < ARRAY_SIZE(ata_dma_blacklist); i++) - if (!strncmp(ata_dma_blacklist[i], s, len)) + if (!strcmp(ata_dma_blacklist[i], model_num)) return 1; return 0; diff --git a/drivers/scsi/libata-scsi.c b/drivers/scsi/libata-scsi.c index 26f07a2617f9..ebd7cf42550b 100644 --- a/drivers/scsi/libata-scsi.c +++ b/drivers/scsi/libata-scsi.c @@ -1806,15 +1806,12 @@ static int ata_dev_supports_fua(u16 *id) if (!ata_id_has_fua(id)) return 0; - model[40] = '\0'; - fw[8] = '\0'; + ata_dev_id_c_string(id, model, ATA_ID_PROD_OFS, sizeof(model)); + ata_dev_id_c_string(id, fw, ATA_ID_FW_REV_OFS, sizeof(fw)); - ata_dev_id_string(id, model, ATA_ID_PROD_OFS, sizeof(model) - 1); - ata_dev_id_string(id, fw, ATA_ID_FW_REV_OFS, sizeof(fw) - 1); - - if (strncmp(model, "Maxtor", 6)) + if (strcmp(model, "Maxtor")) return 1; - if (strncmp(fw, "BANC1G10", 8)) + if (strcmp(fw, "BANC1G10")) return 1; return 0; /* blacklisted */ diff --git a/drivers/scsi/sata_sil.c b/drivers/scsi/sata_sil.c index bd2887741d78..61c4ac7ff9db 100644 --- a/drivers/scsi/sata_sil.c +++ b/drivers/scsi/sata_sil.c @@ -337,22 +337,13 @@ static void sil_scr_write (struct ata_port *ap, unsigned int sc_reg, u32 val) static void sil_dev_config(struct ata_port *ap, struct ata_device *dev) { unsigned int n, quirks = 0; - unsigned char model_num[40]; - const char *s; - unsigned int len; + unsigned char model_num[41]; - ata_dev_id_string(dev->id, model_num, ATA_ID_PROD_OFS, - sizeof(model_num)); - s = &model_num[0]; - len = strnlen(s, sizeof(model_num)); - - /* ATAPI specifies that empty space is blank-filled; remove blanks */ - while ((len > 0) && (s[len - 1] == ' ')) - len--; + ata_dev_id_c_string(dev->id, model_num, ATA_ID_PROD_OFS, + sizeof(model_num)); for (n = 0; sil_blacklist[n].product; n++) - if (!memcmp(sil_blacklist[n].product, s, - strlen(sil_blacklist[n].product))) { + if (!strcmp(sil_blacklist[n].product, model_num)) { quirks = sil_blacklist[n].quirk; break; } @@ -372,7 +363,7 @@ static void sil_dev_config(struct ata_port *ap, struct ata_device *dev) /* limit to udma5 */ if (quirks & SIL_QUIRK_UDMA5MAX) { printk(KERN_INFO "ata%u(%u): applying Maxtor errata fix %s\n", - ap->id, dev->devno, s); + ap->id, dev->devno, model_num); ap->udma_mask &= ATA_UDMA5; return; } From 2940740bcaa5948967d261dfceec04f40b2d2fa1 Mon Sep 17 00:00:00 2001 From: Tejun Heo Date: Sun, 12 Feb 2006 22:47:04 +0900 Subject: [PATCH 35/48] [PATCH] libata: separate out ata_id_n_sectors() Separate out n_sectors calculation into ata_id_n_sectors() from ata_dev_identify(). This will be used by revalidation. Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik --- drivers/scsi/libata-core.c | 26 ++++++++++++++++++-------- 1 file changed, 18 insertions(+), 8 deletions(-) diff --git a/drivers/scsi/libata-core.c b/drivers/scsi/libata-core.c index 1d65f703348e..4df5024c3888 100644 --- a/drivers/scsi/libata-core.c +++ b/drivers/scsi/libata-core.c @@ -548,6 +548,21 @@ void ata_dev_id_c_string(const u16 *id, unsigned char *s, *p = '\0'; } +static u64 ata_id_n_sectors(const u16 *id) +{ + if (ata_id_has_lba(id)) { + if (ata_id_has_lba48(id)) + return ata_id_u64(id, 100); + else + return ata_id_u32(id, 60); + } else { + if (ata_id_current_chs_valid(id)) + return ata_id_u32(id, 57); + else + return id[1] * id[3] * id[6]; + } +} + /** * ata_noop_dev_select - Select device 0/1 on ATA bus * @ap: ATA channel to manipulate @@ -1009,6 +1024,8 @@ static void ata_dev_identify(struct ata_port *ap, unsigned int device) /* ATA-specific feature tests */ if (dev->class == ATA_DEV_ATA) { + dev->n_sectors = ata_id_n_sectors(dev->id); + if (!ata_id_is_ata(dev->id)) /* sanity check */ goto err_out_nosup; @@ -1038,12 +1055,8 @@ static void ata_dev_identify(struct ata_port *ap, unsigned int device) if (ata_id_has_lba(dev->id)) { dev->flags |= ATA_DFLAG_LBA; - if (ata_id_has_lba48(dev->id)) { + if (ata_id_has_lba48(dev->id)) dev->flags |= ATA_DFLAG_LBA48; - dev->n_sectors = ata_id_u64(dev->id, 100); - } else { - dev->n_sectors = ata_id_u32(dev->id, 60); - } /* print device info to dmesg */ printk(KERN_INFO "ata%u: dev %u ATA-%d, max %s, %Lu sectors:%s\n", @@ -1059,15 +1072,12 @@ static void ata_dev_identify(struct ata_port *ap, unsigned int device) dev->cylinders = dev->id[1]; dev->heads = dev->id[3]; dev->sectors = dev->id[6]; - dev->n_sectors = dev->cylinders * dev->heads * dev->sectors; if (ata_id_current_chs_valid(dev->id)) { /* Current CHS translation is valid. */ dev->cylinders = dev->id[54]; dev->heads = dev->id[55]; dev->sectors = dev->id[56]; - - dev->n_sectors = ata_id_u32(dev->id, 57); } /* print device info to dmesg */ From 3d2ca91095f8ab6dc0cb925374eec62fa5336764 Mon Sep 17 00:00:00 2001 From: Tejun Heo Date: Sun, 12 Feb 2006 22:47:04 +0900 Subject: [PATCH 36/48] [PATCH] libata: separate out ata_id_major_version() Separate out ATA major version calculation from ata_dev_identify() into ata_id_major_version(). It's preparation for splitting ata_dev_identify(). Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik --- drivers/scsi/libata-core.c | 6 +----- include/linux/ata.h | 10 ++++++++++ 2 files changed, 11 insertions(+), 5 deletions(-) diff --git a/drivers/scsi/libata-core.c b/drivers/scsi/libata-core.c index 4df5024c3888..d87854e199f6 100644 --- a/drivers/scsi/libata-core.c +++ b/drivers/scsi/libata-core.c @@ -927,7 +927,6 @@ static void ata_dev_identify(struct ata_port *ap, unsigned int device) { struct ata_device *dev = &ap->device[device]; unsigned int major_version; - u16 tmp; unsigned long xfer_modes; unsigned int using_edd; struct ata_taskfile tf; @@ -1030,10 +1029,7 @@ static void ata_dev_identify(struct ata_port *ap, unsigned int device) goto err_out_nosup; /* get major version */ - tmp = dev->id[ATA_ID_MAJOR_VER]; - for (major_version = 14; major_version >= 1; major_version--) - if (tmp & (1 << major_version)) - break; + major_version = ata_id_major_version(dev->id); /* * The exact sequence expected by certain pre-ATA4 drives is: diff --git a/include/linux/ata.h b/include/linux/ata.h index a8155ca4947f..b02a16c435e7 100644 --- a/include/linux/ata.h +++ b/include/linux/ata.h @@ -267,6 +267,16 @@ struct ata_taskfile { ((u64) (id)[(n) + 1] << 16) | \ ((u64) (id)[(n) + 0]) ) +static inline unsigned int ata_id_major_version(const u16 *id) +{ + unsigned int mver; + + for (mver = 14; mver >= 1; mver--) + if (id[ATA_ID_MAJOR_VER] & (1 << mver)) + break; + return mver; +} + static inline int ata_id_current_chs_valid(const u16 *id) { /* For ATA-1 devices, if the INITIALIZE DEVICE PARAMETERS command From 0bd3300ac9158b6ceef38fab6fb473765a40e77e Mon Sep 17 00:00:00 2001 From: Tejun Heo Date: Sun, 12 Feb 2006 22:47:05 +0900 Subject: [PATCH 37/48] [PATCH] libata: make ata_dump_id() take @id instead of @dev Make ata_dump_id() take @id instead of @dev. This is preparation for splitting ata_dev_identify(). Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik --- drivers/scsi/libata-core.c | 36 ++++++++++++++++++------------------ 1 file changed, 18 insertions(+), 18 deletions(-) diff --git a/drivers/scsi/libata-core.c b/drivers/scsi/libata-core.c index d87854e199f6..a0b6ca3d1a0c 100644 --- a/drivers/scsi/libata-core.c +++ b/drivers/scsi/libata-core.c @@ -651,41 +651,41 @@ void ata_dev_select(struct ata_port *ap, unsigned int device, /** * ata_dump_id - IDENTIFY DEVICE info debugging output - * @dev: Device whose IDENTIFY DEVICE page we will dump + * @id: IDENTIFY DEVICE page to dump * - * Dump selected 16-bit words from a detected device's - * IDENTIFY PAGE page. + * Dump selected 16-bit words from the given IDENTIFY DEVICE + * page. * * LOCKING: * caller. */ -static inline void ata_dump_id(const struct ata_device *dev) +static inline void ata_dump_id(const u16 *id) { DPRINTK("49==0x%04x " "53==0x%04x " "63==0x%04x " "64==0x%04x " "75==0x%04x \n", - dev->id[49], - dev->id[53], - dev->id[63], - dev->id[64], - dev->id[75]); + id[49], + id[53], + id[63], + id[64], + id[75]); DPRINTK("80==0x%04x " "81==0x%04x " "82==0x%04x " "83==0x%04x " "84==0x%04x \n", - dev->id[80], - dev->id[81], - dev->id[82], - dev->id[83], - dev->id[84]); + id[80], + id[81], + id[82], + id[83], + id[84]); DPRINTK("88==0x%04x " "93==0x%04x\n", - dev->id[88], - dev->id[93]); + id[88], + id[93]); } /* @@ -1019,7 +1019,7 @@ static void ata_dev_identify(struct ata_port *ap, unsigned int device) if (!xfer_modes) xfer_modes = ata_pio_modes(dev); - ata_dump_id(dev); + ata_dump_id(dev->id); /* ATA-specific feature tests */ if (dev->class == ATA_DEV_ATA) { @@ -2510,7 +2510,7 @@ static void ata_dev_reread_id(struct ata_port *ap, struct ata_device *dev) swap_buf_le16(dev->id, ATA_ID_WORDS); - ata_dump_id(dev); + ata_dump_id(dev->id); DPRINTK("EXIT\n"); From 61eb066affc02e16c548aef8b876c49c84113f40 Mon Sep 17 00:00:00 2001 From: Tejun Heo Date: Sun, 12 Feb 2006 23:22:37 +0900 Subject: [PATCH 38/48] [PATCH] libata: don't do EDD handling if ->probe_reset is used EDD is never used with ->probe_reset. Don't handle EDD special case in ata_dev_identify if ->probe_reset is in use. Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik --- drivers/scsi/libata-core.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/drivers/scsi/libata-core.c b/drivers/scsi/libata-core.c index a0b6ca3d1a0c..21ae752cd95c 100644 --- a/drivers/scsi/libata-core.c +++ b/drivers/scsi/libata-core.c @@ -939,7 +939,8 @@ static void ata_dev_identify(struct ata_port *ap, unsigned int device) return; } - if (ap->flags & (ATA_FLAG_SRST | ATA_FLAG_SATA_RESET)) + if (ap->ops->probe_reset || + ap->flags & (ATA_FLAG_SRST | ATA_FLAG_SATA_RESET)) using_edd = 0; else using_edd = 1; From 8eabd02c246b808e0e27c3ee9ea17d0349efb06d Mon Sep 17 00:00:00 2001 From: Tejun Heo Date: Sun, 12 Feb 2006 23:32:58 +0900 Subject: [PATCH 39/48] [PATCH] libata: make ata_dev_knobble() per-device ata_dev_knobble() unconditionally used the first device of the port to determine whether a device is bridged or not. This causes bridge limit to be incorrectly applied or unapplied for hosts with slave devices (e.g. ata_piix). Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik --- drivers/scsi/libata-core.c | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/drivers/scsi/libata-core.c b/drivers/scsi/libata-core.c index 21ae752cd95c..5e8a32052a1e 100644 --- a/drivers/scsi/libata-core.c +++ b/drivers/scsi/libata-core.c @@ -1121,9 +1121,10 @@ static void ata_dev_identify(struct ata_port *ap, unsigned int device) } -static inline u8 ata_dev_knobble(const struct ata_port *ap) +static inline u8 ata_dev_knobble(const struct ata_port *ap, + struct ata_device *dev) { - return ((ap->cbl == ATA_CBL_SATA) && (!ata_id_is_sata(ap->device->id))); + return ((ap->cbl == ATA_CBL_SATA) && (!ata_id_is_sata(dev->id))); } /** @@ -1137,9 +1138,9 @@ static inline u8 ata_dev_knobble(const struct ata_port *ap) void ata_dev_config(struct ata_port *ap, unsigned int i) { /* limit bridge transfers to udma5, 200 sectors */ - if (ata_dev_knobble(ap)) { + if (ata_dev_knobble(ap, &ap->device[i])) { printk(KERN_INFO "ata%u(%u): applying bridge limits\n", - ap->id, ap->device->devno); + ap->id, i); ap->udma_mask &= ATA_UDMA5; ap->host->max_sectors = ATA_MAX_SECTORS; ap->host->hostt->max_sectors = ATA_MAX_SECTORS; From 6e7846e9c548443c86cfbad9e4defb4bdcfc538b Mon Sep 17 00:00:00 2001 From: Tejun Heo Date: Sun, 12 Feb 2006 23:32:58 +0900 Subject: [PATCH 40/48] [PATCH] libata: move cdb_len for host to device cdb_len is per-device property. Sharing cdb_len on ap results in inaccurate configuration on revalidation and hotplugging. This patch makes cdb_len per-device. Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik --- drivers/scsi/ahci.c | 3 ++- drivers/scsi/libata-core.c | 19 ++++++++++++------- drivers/scsi/libata-scsi.c | 4 ++-- drivers/scsi/sata_sil24.c | 4 ++-- include/linux/libata.h | 2 +- 5 files changed, 19 insertions(+), 13 deletions(-) diff --git a/drivers/scsi/ahci.c b/drivers/scsi/ahci.c index 24a54a5a91b8..23caa0c4019b 100644 --- a/drivers/scsi/ahci.c +++ b/drivers/scsi/ahci.c @@ -617,7 +617,8 @@ static void ahci_qc_prep(struct ata_queued_cmd *qc) ata_tf_to_fis(&qc->tf, pp->cmd_tbl, 0); if (is_atapi) { memset(pp->cmd_tbl + AHCI_CMD_TBL_CDB, 0, 32); - memcpy(pp->cmd_tbl + AHCI_CMD_TBL_CDB, qc->cdb, ap->cdb_len); + memcpy(pp->cmd_tbl + AHCI_CMD_TBL_CDB, qc->cdb, + qc->dev->cdb_len); } n_elem = 0; diff --git a/drivers/scsi/libata-core.c b/drivers/scsi/libata-core.c index 5e8a32052a1e..1a373b4d0e22 100644 --- a/drivers/scsi/libata-core.c +++ b/drivers/scsi/libata-core.c @@ -931,7 +931,7 @@ static void ata_dev_identify(struct ata_port *ap, unsigned int device) unsigned int using_edd; struct ata_taskfile tf; unsigned int err_mask; - int rc; + int i, rc; if (!ata_dev_present(dev)) { DPRINTK("ENTER/EXIT (host %u, dev %u) -- nodev\n", @@ -1087,7 +1087,7 @@ static void ata_dev_identify(struct ata_port *ap, unsigned int device) } - ap->host->max_cmd_len = 16; + dev->cdb_len = 16; } /* ATAPI-specific feature tests */ @@ -1100,8 +1100,7 @@ static void ata_dev_identify(struct ata_port *ap, unsigned int device) printk(KERN_WARNING "ata%u: unsupported CDB len\n", ap->id); goto err_out_nosup; } - ap->cdb_len = (unsigned int) rc; - ap->host->max_cmd_len = (unsigned char) ap->cdb_len; + dev->cdb_len = (unsigned int) rc; /* print device info to dmesg */ printk(KERN_INFO "ata%u: dev %u ATAPI, max %s\n", @@ -1109,6 +1108,12 @@ static void ata_dev_identify(struct ata_port *ap, unsigned int device) ata_mode_string(xfer_modes)); } + ap->host->max_cmd_len = 0; + for (i = 0; i < ATA_MAX_DEVICES; i++) + ap->host->max_cmd_len = max_t(unsigned int, + ap->host->max_cmd_len, + ap->device[i].cdb_len); + DPRINTK("EXIT, drv_stat = 0x%x\n", ata_chk_status(ap)); return; @@ -4203,7 +4208,7 @@ static void atapi_packet_task(void *_data) /* send SCSI cdb */ DPRINTK("send cdb\n"); - WARN_ON(ap->cdb_len < 12); + WARN_ON(qc->dev->cdb_len < 12); if (qc->tf.protocol == ATA_PROT_ATAPI_DMA || qc->tf.protocol == ATA_PROT_ATAPI_NODATA) { @@ -4217,12 +4222,12 @@ static void atapi_packet_task(void *_data) */ spin_lock_irqsave(&ap->host_set->lock, flags); ap->flags &= ~ATA_FLAG_NOINTR; - ata_data_xfer(ap, qc->cdb, ap->cdb_len, 1); + ata_data_xfer(ap, qc->cdb, qc->dev->cdb_len, 1); if (qc->tf.protocol == ATA_PROT_ATAPI_DMA) ap->ops->bmdma_start(qc); /* initiate bmdma */ spin_unlock_irqrestore(&ap->host_set->lock, flags); } else { - ata_data_xfer(ap, qc->cdb, ap->cdb_len, 1); + ata_data_xfer(ap, qc->cdb, qc->dev->cdb_len, 1); /* PIO commands are handled by polling */ ap->hsm_task_state = HSM_ST; diff --git a/drivers/scsi/libata-scsi.c b/drivers/scsi/libata-scsi.c index ebd7cf42550b..3628fedc9865 100644 --- a/drivers/scsi/libata-scsi.c +++ b/drivers/scsi/libata-scsi.c @@ -2146,7 +2146,7 @@ static void atapi_request_sense(struct ata_queued_cmd *qc) ata_sg_init_one(qc, cmd->sense_buffer, sizeof(cmd->sense_buffer)); qc->dma_dir = DMA_FROM_DEVICE; - memset(&qc->cdb, 0, ap->cdb_len); + memset(&qc->cdb, 0, qc->dev->cdb_len); qc->cdb[0] = REQUEST_SENSE; qc->cdb[4] = SCSI_SENSE_BUFFERSIZE; @@ -2248,7 +2248,7 @@ static unsigned int atapi_xlat(struct ata_queued_cmd *qc, const u8 *scsicmd) if (ata_check_atapi_dma(qc)) using_pio = 1; - memcpy(&qc->cdb, scsicmd, qc->ap->cdb_len); + memcpy(&qc->cdb, scsicmd, dev->cdb_len); qc->complete_fn = atapi_qc_complete; diff --git a/drivers/scsi/sata_sil24.c b/drivers/scsi/sata_sil24.c index 228a7fabffff..24020c68903a 100644 --- a/drivers/scsi/sata_sil24.c +++ b/drivers/scsi/sata_sil24.c @@ -371,7 +371,7 @@ static void sil24_dev_config(struct ata_port *ap, struct ata_device *dev) { void __iomem *port = (void __iomem *)ap->ioaddr.cmd_addr; - if (ap->cdb_len == 16) + if (dev->cdb_len == 16) writel(PORT_CS_CDB16, port + PORT_CTRL_STAT); else writel(PORT_CS_CDB16, port + PORT_CTRL_CLR); @@ -543,7 +543,7 @@ static void sil24_qc_prep(struct ata_queued_cmd *qc) prb = &cb->atapi.prb; sge = cb->atapi.sge; memset(cb->atapi.cdb, 0, 32); - memcpy(cb->atapi.cdb, qc->cdb, ap->cdb_len); + memcpy(cb->atapi.cdb, qc->cdb, qc->dev->cdb_len); if (qc->tf.protocol != ATA_PROT_ATAPI_NODATA) { if (qc->tf.flags & ATA_TFLAG_WRITE) diff --git a/include/linux/libata.h b/include/linux/libata.h index 0853032673b7..853c98859a9f 100644 --- a/include/linux/libata.h +++ b/include/linux/libata.h @@ -348,6 +348,7 @@ struct ata_device { unsigned int multi_count; /* sectors count for READ/WRITE MULTIPLE */ + unsigned int cdb_len; /* for CHS addressing */ u16 cylinders; /* Number of cylinders */ @@ -377,7 +378,6 @@ struct ata_port { unsigned int mwdma_mask; unsigned int udma_mask; unsigned int cbl; /* cable type; ATA_CBL_xxx */ - unsigned int cdb_len; struct ata_device device[ATA_MAX_DEVICES]; From b00eec1d58ee71131375bfeb86e64bceec3f5618 Mon Sep 17 00:00:00 2001 From: Tejun Heo Date: Sun, 12 Feb 2006 23:32:59 +0900 Subject: [PATCH 41/48] [PATCH] libata: add per-device max_sectors If a low level driver wants to control max_sectors, it had to adjust ap->host->max_sectors and set ATA_DFLAG_LOCK_SECTORS to tell ata_scsi_slave_config not to override the limit. This is not only cumbersome but also incorrect for hosts which support more than one devices per port. This patch adds per-device ->max_sectors. If the field is unset (zero), libata core layer will adjust ->max_sectors according to default rules. If the field is set, libata honors the setting. Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik --- drivers/scsi/libata-core.c | 4 +--- drivers/scsi/libata-scsi.c | 18 +++++++++--------- drivers/scsi/sata_sil.c | 4 +--- include/linux/libata.h | 4 ++-- 4 files changed, 13 insertions(+), 17 deletions(-) diff --git a/drivers/scsi/libata-core.c b/drivers/scsi/libata-core.c index 1a373b4d0e22..61cba39a6834 100644 --- a/drivers/scsi/libata-core.c +++ b/drivers/scsi/libata-core.c @@ -1147,9 +1147,7 @@ void ata_dev_config(struct ata_port *ap, unsigned int i) printk(KERN_INFO "ata%u(%u): applying bridge limits\n", ap->id, i); ap->udma_mask &= ATA_UDMA5; - ap->host->max_sectors = ATA_MAX_SECTORS; - ap->host->hostt->max_sectors = ATA_MAX_SECTORS; - ap->device[i].flags |= ATA_DFLAG_LOCK_SECTORS; + ap->device[i].max_sectors = ATA_MAX_SECTORS; } if (ap->ops->dev_config) diff --git a/drivers/scsi/libata-scsi.c b/drivers/scsi/libata-scsi.c index 3628fedc9865..86da46502b3e 100644 --- a/drivers/scsi/libata-scsi.c +++ b/drivers/scsi/libata-scsi.c @@ -684,23 +684,23 @@ int ata_scsi_slave_config(struct scsi_device *sdev) if (sdev->id < ATA_MAX_DEVICES) { struct ata_port *ap; struct ata_device *dev; + unsigned int max_sectors; ap = (struct ata_port *) &sdev->host->hostdata[0]; dev = &ap->device[sdev->id]; - /* TODO: 1024 is an arbitrary number, not the + /* TODO: 2048 is an arbitrary number, not the * hardware maximum. This should be increased to * 65534 when Jens Axboe's patch for dynamically * determining max_sectors is merged. */ - if ((dev->flags & ATA_DFLAG_LBA48) && - ((dev->flags & ATA_DFLAG_LOCK_SECTORS) == 0)) { - /* - * do not overwrite sdev->host->max_sectors, since - * other drives on this host may not support LBA48 - */ - blk_queue_max_sectors(sdev->request_queue, 2048); - } + max_sectors = ATA_MAX_SECTORS; + if (dev->flags & ATA_DFLAG_LBA48) + max_sectors = 2048; + if (dev->max_sectors) + max_sectors = dev->max_sectors; + + blk_queue_max_sectors(sdev->request_queue, max_sectors); /* * SATA DMA transfers must be multiples of 4 byte, so diff --git a/drivers/scsi/sata_sil.c b/drivers/scsi/sata_sil.c index 61c4ac7ff9db..6c482c8be254 100644 --- a/drivers/scsi/sata_sil.c +++ b/drivers/scsi/sata_sil.c @@ -354,9 +354,7 @@ static void sil_dev_config(struct ata_port *ap, struct ata_device *dev) (quirks & SIL_QUIRK_MOD15WRITE))) { printk(KERN_INFO "ata%u(%u): applying Seagate errata fix (mod15write workaround)\n", ap->id, dev->devno); - ap->host->max_sectors = 15; - ap->host->hostt->max_sectors = 15; - dev->flags |= ATA_DFLAG_LOCK_SECTORS; + dev->max_sectors = 15; return; } diff --git a/include/linux/libata.h b/include/linux/libata.h index 853c98859a9f..afe46457124e 100644 --- a/include/linux/libata.h +++ b/include/linux/libata.h @@ -122,8 +122,7 @@ enum { /* struct ata_device stuff */ ATA_DFLAG_LBA48 = (1 << 0), /* device supports LBA48 */ ATA_DFLAG_PIO = (1 << 1), /* device currently in PIO mode */ - ATA_DFLAG_LOCK_SECTORS = (1 << 2), /* don't adjust max_sectors */ - ATA_DFLAG_LBA = (1 << 3), /* device supports LBA */ + ATA_DFLAG_LBA = (1 << 2), /* device supports LBA */ ATA_DEV_UNKNOWN = 0, /* unknown device */ ATA_DEV_ATA = 1, /* ATA device */ @@ -348,6 +347,7 @@ struct ata_device { unsigned int multi_count; /* sectors count for READ/WRITE MULTIPLE */ + unsigned int max_sectors; /* per-device max sectors */ unsigned int cdb_len; /* for CHS addressing */ From 49430f97dd952eda60848bf6bf161b4917ba103d Mon Sep 17 00:00:00 2001 From: Tejun Heo Date: Sun, 12 Feb 2006 23:32:59 +0900 Subject: [PATCH 42/48] [PATCH] libata: kill sht->max_sectors The previous dev->max_sectors patch made sht->max_sectors meaningless. Kill all initializations of sht->max_sectors. Signed-off-by: Tejun Heo Signed-off-by: Jeff Garzik --- drivers/scsi/ahci.c | 1 - drivers/scsi/ata_piix.c | 1 - drivers/scsi/pdc_adma.c | 1 - drivers/scsi/sata_mv.c | 1 - drivers/scsi/sata_nv.c | 1 - drivers/scsi/sata_promise.c | 1 - drivers/scsi/sata_qstor.c | 1 - drivers/scsi/sata_sil.c | 1 - drivers/scsi/sata_sil24.c | 1 - drivers/scsi/sata_sis.c | 1 - drivers/scsi/sata_svw.c | 1 - drivers/scsi/sata_sx4.c | 1 - drivers/scsi/sata_uli.c | 1 - drivers/scsi/sata_via.c | 1 - drivers/scsi/sata_vsc.c | 1 - 15 files changed, 15 deletions(-) diff --git a/drivers/scsi/ahci.c b/drivers/scsi/ahci.c index 23caa0c4019b..1c2ab3dede71 100644 --- a/drivers/scsi/ahci.c +++ b/drivers/scsi/ahci.c @@ -211,7 +211,6 @@ static struct scsi_host_template ahci_sht = { .can_queue = ATA_DEF_QUEUE, .this_id = ATA_SHT_THIS_ID, .sg_tablesize = AHCI_MAX_SG, - .max_sectors = ATA_MAX_SECTORS, .cmd_per_lun = ATA_SHT_CMD_PER_LUN, .emulated = ATA_SHT_EMULATED, .use_clustering = AHCI_USE_CLUSTERING, diff --git a/drivers/scsi/ata_piix.c b/drivers/scsi/ata_piix.c index 8e0529601730..4cc1108f721a 100644 --- a/drivers/scsi/ata_piix.c +++ b/drivers/scsi/ata_piix.c @@ -185,7 +185,6 @@ static struct scsi_host_template piix_sht = { .can_queue = ATA_DEF_QUEUE, .this_id = ATA_SHT_THIS_ID, .sg_tablesize = LIBATA_MAX_PRD, - .max_sectors = ATA_MAX_SECTORS, .cmd_per_lun = ATA_SHT_CMD_PER_LUN, .emulated = ATA_SHT_EMULATED, .use_clustering = ATA_SHT_USE_CLUSTERING, diff --git a/drivers/scsi/pdc_adma.c b/drivers/scsi/pdc_adma.c index d0ad3ebe9685..5f33cc932e70 100644 --- a/drivers/scsi/pdc_adma.c +++ b/drivers/scsi/pdc_adma.c @@ -148,7 +148,6 @@ static struct scsi_host_template adma_ata_sht = { .can_queue = ATA_DEF_QUEUE, .this_id = ATA_SHT_THIS_ID, .sg_tablesize = LIBATA_MAX_PRD, - .max_sectors = ATA_MAX_SECTORS, .cmd_per_lun = ATA_SHT_CMD_PER_LUN, .emulated = ATA_SHT_EMULATED, .use_clustering = ENABLE_CLUSTERING, diff --git a/drivers/scsi/sata_mv.c b/drivers/scsi/sata_mv.c index 732cb64a4d1b..c158de2e757d 100644 --- a/drivers/scsi/sata_mv.c +++ b/drivers/scsi/sata_mv.c @@ -383,7 +383,6 @@ static struct scsi_host_template mv_sht = { .can_queue = MV_USE_Q_DEPTH, .this_id = ATA_SHT_THIS_ID, .sg_tablesize = MV_MAX_SG_CT / 2, - .max_sectors = ATA_MAX_SECTORS, .cmd_per_lun = ATA_SHT_CMD_PER_LUN, .emulated = ATA_SHT_EMULATED, .use_clustering = ATA_SHT_USE_CLUSTERING, diff --git a/drivers/scsi/sata_nv.c b/drivers/scsi/sata_nv.c index cdfeb9aa600b..caffadc2e0ae 100644 --- a/drivers/scsi/sata_nv.c +++ b/drivers/scsi/sata_nv.c @@ -234,7 +234,6 @@ static struct scsi_host_template nv_sht = { .can_queue = ATA_DEF_QUEUE, .this_id = ATA_SHT_THIS_ID, .sg_tablesize = LIBATA_MAX_PRD, - .max_sectors = ATA_MAX_SECTORS, .cmd_per_lun = ATA_SHT_CMD_PER_LUN, .emulated = ATA_SHT_EMULATED, .use_clustering = ATA_SHT_USE_CLUSTERING, diff --git a/drivers/scsi/sata_promise.c b/drivers/scsi/sata_promise.c index c9dfd9370919..ba2b7a0983db 100644 --- a/drivers/scsi/sata_promise.c +++ b/drivers/scsi/sata_promise.c @@ -116,7 +116,6 @@ static struct scsi_host_template pdc_ata_sht = { .can_queue = ATA_DEF_QUEUE, .this_id = ATA_SHT_THIS_ID, .sg_tablesize = LIBATA_MAX_PRD, - .max_sectors = ATA_MAX_SECTORS, .cmd_per_lun = ATA_SHT_CMD_PER_LUN, .emulated = ATA_SHT_EMULATED, .use_clustering = ATA_SHT_USE_CLUSTERING, diff --git a/drivers/scsi/sata_qstor.c b/drivers/scsi/sata_qstor.c index 955131b43206..286482630be3 100644 --- a/drivers/scsi/sata_qstor.c +++ b/drivers/scsi/sata_qstor.c @@ -137,7 +137,6 @@ static struct scsi_host_template qs_ata_sht = { .can_queue = ATA_DEF_QUEUE, .this_id = ATA_SHT_THIS_ID, .sg_tablesize = QS_MAX_PRD, - .max_sectors = ATA_MAX_SECTORS, .cmd_per_lun = ATA_SHT_CMD_PER_LUN, .emulated = ATA_SHT_EMULATED, //FIXME .use_clustering = ATA_SHT_USE_CLUSTERING, diff --git a/drivers/scsi/sata_sil.c b/drivers/scsi/sata_sil.c index 6c482c8be254..15346888faf2 100644 --- a/drivers/scsi/sata_sil.c +++ b/drivers/scsi/sata_sil.c @@ -140,7 +140,6 @@ static struct scsi_host_template sil_sht = { .can_queue = ATA_DEF_QUEUE, .this_id = ATA_SHT_THIS_ID, .sg_tablesize = LIBATA_MAX_PRD, - .max_sectors = ATA_MAX_SECTORS, .cmd_per_lun = ATA_SHT_CMD_PER_LUN, .emulated = ATA_SHT_EMULATED, .use_clustering = ATA_SHT_USE_CLUSTERING, diff --git a/drivers/scsi/sata_sil24.c b/drivers/scsi/sata_sil24.c index 24020c68903a..a0e35a262156 100644 --- a/drivers/scsi/sata_sil24.c +++ b/drivers/scsi/sata_sil24.c @@ -285,7 +285,6 @@ static struct scsi_host_template sil24_sht = { .can_queue = ATA_DEF_QUEUE, .this_id = ATA_SHT_THIS_ID, .sg_tablesize = LIBATA_MAX_PRD, - .max_sectors = ATA_MAX_SECTORS, .cmd_per_lun = ATA_SHT_CMD_PER_LUN, .emulated = ATA_SHT_EMULATED, .use_clustering = ATA_SHT_USE_CLUSTERING, diff --git a/drivers/scsi/sata_sis.c b/drivers/scsi/sata_sis.c index 2f1815715705..7fd45f86de99 100644 --- a/drivers/scsi/sata_sis.c +++ b/drivers/scsi/sata_sis.c @@ -92,7 +92,6 @@ static struct scsi_host_template sis_sht = { .can_queue = ATA_DEF_QUEUE, .this_id = ATA_SHT_THIS_ID, .sg_tablesize = ATA_MAX_PRD, - .max_sectors = ATA_MAX_SECTORS, .cmd_per_lun = ATA_SHT_CMD_PER_LUN, .emulated = ATA_SHT_EMULATED, .use_clustering = ATA_SHT_USE_CLUSTERING, diff --git a/drivers/scsi/sata_svw.c b/drivers/scsi/sata_svw.c index f369c3003adf..4aaccd53e736 100644 --- a/drivers/scsi/sata_svw.c +++ b/drivers/scsi/sata_svw.c @@ -293,7 +293,6 @@ static struct scsi_host_template k2_sata_sht = { .can_queue = ATA_DEF_QUEUE, .this_id = ATA_SHT_THIS_ID, .sg_tablesize = LIBATA_MAX_PRD, - .max_sectors = ATA_MAX_SECTORS, .cmd_per_lun = ATA_SHT_CMD_PER_LUN, .emulated = ATA_SHT_EMULATED, .use_clustering = ATA_SHT_USE_CLUSTERING, diff --git a/drivers/scsi/sata_sx4.c b/drivers/scsi/sata_sx4.c index e158f7a34d62..9f8a76815402 100644 --- a/drivers/scsi/sata_sx4.c +++ b/drivers/scsi/sata_sx4.c @@ -187,7 +187,6 @@ static struct scsi_host_template pdc_sata_sht = { .can_queue = ATA_DEF_QUEUE, .this_id = ATA_SHT_THIS_ID, .sg_tablesize = LIBATA_MAX_PRD, - .max_sectors = ATA_MAX_SECTORS, .cmd_per_lun = ATA_SHT_CMD_PER_LUN, .emulated = ATA_SHT_EMULATED, .use_clustering = ATA_SHT_USE_CLUSTERING, diff --git a/drivers/scsi/sata_uli.c b/drivers/scsi/sata_uli.c index c500f2490902..37a487b7d655 100644 --- a/drivers/scsi/sata_uli.c +++ b/drivers/scsi/sata_uli.c @@ -80,7 +80,6 @@ static struct scsi_host_template uli_sht = { .can_queue = ATA_DEF_QUEUE, .this_id = ATA_SHT_THIS_ID, .sg_tablesize = LIBATA_MAX_PRD, - .max_sectors = ATA_MAX_SECTORS, .cmd_per_lun = ATA_SHT_CMD_PER_LUN, .emulated = ATA_SHT_EMULATED, .use_clustering = ATA_SHT_USE_CLUSTERING, diff --git a/drivers/scsi/sata_via.c b/drivers/scsi/sata_via.c index 2e20887dc88f..ff65a0b0457f 100644 --- a/drivers/scsi/sata_via.c +++ b/drivers/scsi/sata_via.c @@ -99,7 +99,6 @@ static struct scsi_host_template svia_sht = { .can_queue = ATA_DEF_QUEUE, .this_id = ATA_SHT_THIS_ID, .sg_tablesize = LIBATA_MAX_PRD, - .max_sectors = ATA_MAX_SECTORS, .cmd_per_lun = ATA_SHT_CMD_PER_LUN, .emulated = ATA_SHT_EMULATED, .use_clustering = ATA_SHT_USE_CLUSTERING, diff --git a/drivers/scsi/sata_vsc.c b/drivers/scsi/sata_vsc.c index cf1f8a61bda0..e124db8e8284 100644 --- a/drivers/scsi/sata_vsc.c +++ b/drivers/scsi/sata_vsc.c @@ -228,7 +228,6 @@ static struct scsi_host_template vsc_sata_sht = { .can_queue = ATA_DEF_QUEUE, .this_id = ATA_SHT_THIS_ID, .sg_tablesize = LIBATA_MAX_PRD, - .max_sectors = ATA_MAX_SECTORS, .cmd_per_lun = ATA_SHT_CMD_PER_LUN, .emulated = ATA_SHT_EMULATED, .use_clustering = ATA_SHT_USE_CLUSTERING, From 3c791925da0e6108cda15e3c2c7bfaebcd9ab9cf Mon Sep 17 00:00:00 2001 From: Jesper Juhl Date: Sun, 12 Feb 2006 14:34:53 -0800 Subject: [PATCH 43/48] [PATCH] netfilter: fix build error due to missing has_bridge_parent macro net/bridge/br_netfilter.c: In function `br_nf_post_routing': net/bridge/br_netfilter.c:808: warning: implicit declaration of function `has_bridge_parent' Signed-off-by: Jesper Juhl Cc: Harald Welte Cc: "David S. Miller" Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- net/bridge/br_netfilter.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/net/bridge/br_netfilter.c b/net/bridge/br_netfilter.c index b5018166b0e5..c06cb0983530 100644 --- a/net/bridge/br_netfilter.c +++ b/net/bridge/br_netfilter.c @@ -805,7 +805,7 @@ static unsigned int br_nf_post_routing(unsigned int hook, struct sk_buff **pskb, print_error: if (skb->dev != NULL) { printk("[%s]", skb->dev->name); - if (has_bridge_parent(skb->dev)) + if (bridge_parent(skb->dev)) printk("[%s]", bridge_parent(skb->dev)->name); } printk(" head:%p, raw:%p, data:%p\n", skb->head, skb->mac.raw, From 89edc3d2b429136a0e25f40275fd82dc58f147fd Mon Sep 17 00:00:00 2001 From: Jeff Mahoney Date: Sun, 12 Feb 2006 14:34:55 -0800 Subject: [PATCH 44/48] [PATCH] reiserfs: disable automatic enabling of reiserfs inode attributes Unfortunately, the reiserfs_attrs_cleared bit in the superblock flag can lie. File systems have been observed with the bit set, yet still contain garbage in the stat data field, causing unpredictable results. This patch backs out the enable-by-default behavior. It eliminates the changes from: d50a5cd860ce721dbeac6a4f3c6e42abcde68cd8, and ef5e5414e7a83eb9b4295bbaba5464410b11e030. Signed-off-by: Jeff Mahoney Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- fs/reiserfs/super.c | 2 -- 1 file changed, 2 deletions(-) diff --git a/fs/reiserfs/super.c b/fs/reiserfs/super.c index ef5e5414e7a8..d63da756eb49 100644 --- a/fs/reiserfs/super.c +++ b/fs/reiserfs/super.c @@ -1124,8 +1124,6 @@ static void handle_attrs(struct super_block *s) "reiserfs: cannot support attributes until flag is set in super-block"); REISERFS_SB(s)->s_mount_opt &= ~(1 << REISERFS_ATTRS); } - } else if (le32_to_cpu(rs->s_flags) & reiserfs_attrs_cleared) { - REISERFS_SB(s)->s_mount_opt |= (1 << REISERFS_ATTRS); } } From 8f6da52aeff1fd7272ff5082552a39c050565b57 Mon Sep 17 00:00:00 2001 From: Jesse Allen Date: Sun, 12 Feb 2006 14:34:56 -0800 Subject: [PATCH 45/48] [PATCH] orinoco: support smc2532w The orinoco wireless driver can support the SMC 2532W-B PC Card, so add the id for it. Signed-off-by: Jesse Allen Cc: Pavel Roskin Cc: David Gibson Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- drivers/net/wireless/orinoco_cs.c | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/net/wireless/orinoco_cs.c b/drivers/net/wireless/orinoco_cs.c index 3c128b692bce..ec6f2a48895b 100644 --- a/drivers/net/wireless/orinoco_cs.c +++ b/drivers/net/wireless/orinoco_cs.c @@ -590,6 +590,7 @@ static struct pcmcia_device_id orinoco_cs_ids[] = { PCMCIA_DEVICE_PROD_ID12("PROXIM", "LAN PC CARD HARMONY 80211B", 0xc6536a5e, 0x090c3cd9), PCMCIA_DEVICE_PROD_ID12("PROXIM", "LAN PCI CARD HARMONY 80211B", 0xc6536a5e, 0x9f494e26), PCMCIA_DEVICE_PROD_ID12("SAMSUNG", "11Mbps WLAN Card", 0x43d74cb4, 0x579bd91b), + PCMCIA_DEVICE_PROD_ID12("SMC", "SMC2532W-B EliteConnect Wireless Adapter", 0xc4f8b18b, 0x196bd757), PCMCIA_DEVICE_PROD_ID12("SMC", "SMC2632W", 0xc4f8b18b, 0x474a1f2a), PCMCIA_DEVICE_PROD_ID12("Symbol Technologies", "LA4111 Spectrum24 Wireless LAN PC Card", 0x3f02b4d6, 0x3663cb0e), PCMCIA_DEVICE_PROD_ID123("The Linksys Group, Inc.", "Instant Wireless Network PC Card", "ISL37300P", 0xa5f472c2, 0x590eb502, 0xc9049a39), From a65d17c9d27a85782cfe1bbc36c747ffa1f81814 Mon Sep 17 00:00:00 2001 From: John Blackwood Date: Sun, 12 Feb 2006 14:34:58 -0800 Subject: [PATCH 46/48] [PATCH] arch/x86_64/kernel/traps.c PTRACE_SINGLESTEP oops We found a problem with x86_64 kernels with preemption enabled, where having multiple tasks doing ptrace singlesteps around the same time will cause the system to 'oops'. The problem seems that a task can get preempted out of the do_debug() processing while it is running on the DEBUG_STACK stack. If another task on that same cpu then enters do_debug() and uses the same per-cpu DEBUG_STACK stack, the previous preempted tasks's stack contents can be corrupted, and the system will oops when the preempted task is context switched back in again. The typical oops looks like the following: Unable to handle kernel paging request at ffffffffffffffae RIP: {thread_return+34} PGD 103027 PUD 102429067 PMD 0 Oops: 0002 [1] PREEMPT SMP CPU 0 Modules linked in: Pid: 3786, comm: ssdd Not tainted 2.6.15.2 #1 RIP: 0010:[] {thread_return+34} RSP: 0018:ffffffff80824058 EFLAGS: 000136c2 RAX: ffff81017e12cea0 RBX: 0000000000000000 RCX: 00000000c0000100 RDX: 0000000000000000 RSI: ffff8100f7856e20 RDI: ffff81017e12cea0 RBP: 0000000000000046 R08: ffff8100f68a6000 R09: 0000000000000000 R10: 0000000000000000 R11: ffff81017e12cea0 R12: ffff81000c2d53e8 R13: ffff81017f5b3be8 R14: ffff81000c0036e0 R15: 000001056cbfc899 FS: 00002aaaaaad9b00(0000) GS:ffffffff80883800(0000) knlGS:0000000000000000 CS: 0010 DS: 0000 ES: 0000 CR0: 000000008005003b CR2: ffffffffffffffae CR3: 00000000f6fcf000 CR4: 00000000000006e0 Process ssdd (pid: 3786, threadinfo ffff8100f68a6000, task ffff8100f7856e20) Stack: ffffffff808240d8 ffffffff8012a84a ffff8100055f6c00 0000000000000020 0000000000000001 ffff81000c0036e0 ffffffff808240b8 0000000000000000 0000000000000000 0000000000000000 Call Trace: <#DB> {try_to_wake_up+985} {kick_process+87} {signal_wake_up+48} {specific_send_sig_info+179} {_spin_unlock_irqrestore+27} {force_sig_info+159} {do_debug+289} {sync_regs+103} {paranoid_userspace+35} Unable to handle kernel paging request at 00007fffffb7d000 RIP: {show_trace+465} PGD f6f25067 PUD f6fcc067 PMD f6957067 PTE 0 Oops: 0000 [2] PREEMPT SMP This patch disables preemptions for the task upon entry to do_debug(), before interrupts are reenabled, and then disables preemption before exiting do_debug(), after disabling interrupts. I've noticed that the task can be preempted either at the end of an interrupt, or on the call to force_sig_info() on the spin_unlock_irqrestore() processing. It might be better to attempt to code a fix in entry.S around the code that calls do_debug(). Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- arch/x86_64/kernel/traps.c | 18 +++++++++++++++++- 1 file changed, 17 insertions(+), 1 deletion(-) diff --git a/arch/x86_64/kernel/traps.c b/arch/x86_64/kernel/traps.c index ee1b2da9e5e7..28d50dc540e8 100644 --- a/arch/x86_64/kernel/traps.c +++ b/arch/x86_64/kernel/traps.c @@ -90,6 +90,20 @@ static inline void conditional_sti(struct pt_regs *regs) local_irq_enable(); } +static inline void preempt_conditional_sti(struct pt_regs *regs) +{ + preempt_disable(); + if (regs->eflags & X86_EFLAGS_IF) + local_irq_enable(); +} + +static inline void preempt_conditional_cli(struct pt_regs *regs) +{ + if (regs->eflags & X86_EFLAGS_IF) + local_irq_disable(); + preempt_enable_no_resched(); +} + static int kstack_depth_to_print = 10; #ifdef CONFIG_KALLSYMS @@ -693,7 +707,7 @@ asmlinkage void __kprobes do_debug(struct pt_regs * regs, SIGTRAP) == NOTIFY_STOP) return; - conditional_sti(regs); + preempt_conditional_sti(regs); /* Mask out spurious debug traps due to lazy DR7 setting */ if (condition & (DR_TRAP0|DR_TRAP1|DR_TRAP2|DR_TRAP3)) { @@ -738,11 +752,13 @@ asmlinkage void __kprobes do_debug(struct pt_regs * regs, clear_dr7: set_debugreg(0UL, 7); + preempt_conditional_cli(regs); return; clear_TF_reenable: set_tsk_thread_flag(tsk, TIF_SINGLESTEP); regs->eflags &= ~TF_MASK; + preempt_conditional_cli(regs); } static int kernel_math_error(struct pt_regs *regs, const char *str, int trapnr) From 0d541064e8f58858e11cd34d81b6e83617f6eb4a Mon Sep 17 00:00:00 2001 From: Andi Kleen Date: Sun, 12 Feb 2006 14:34:59 -0800 Subject: [PATCH 47/48] [PATCH] x86_64: GART DMA merging fix Don't touch the non DMA members in the sg list in dma_map_sg in the IOMMU Some drivers (in particular ST) ran into problems because they reused the sg lists after passing them to pci_map_sg(). The merging procedure in the K8 GART IOMMU corrupted the state. This patch changes it to only touch the dma* entries during merging, but not the other fields. Approach suggested by Dave Miller. Signed-off-by: Andi Kleen Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- arch/x86_64/kernel/pci-gart.c | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/arch/x86_64/kernel/pci-gart.c b/arch/x86_64/kernel/pci-gart.c index 2fe23a6c361b..dd0718dc178b 100644 --- a/arch/x86_64/kernel/pci-gart.c +++ b/arch/x86_64/kernel/pci-gart.c @@ -310,7 +310,7 @@ void gart_unmap_sg(struct device *dev, struct scatterlist *sg, int nents, int di for (i = 0; i < nents; i++) { struct scatterlist *s = &sg[i]; - if (!s->dma_length || !s->length) + if (!s->dma_length) break; dma_unmap_single(dev, s->dma_address, s->dma_length, dir); } @@ -364,7 +364,6 @@ static int __dma_map_cont(struct scatterlist *sg, int start, int stopat, BUG_ON(i > start && s->offset); if (i == start) { - *sout = *s; sout->dma_address = iommu_bus_base; sout->dma_address += iommu_page*PAGE_SIZE + s->offset; sout->dma_length = s->length; @@ -379,7 +378,7 @@ static int __dma_map_cont(struct scatterlist *sg, int start, int stopat, SET_LEAK(iommu_page); addr += PAGE_SIZE; iommu_page++; - } + } } BUG_ON(iommu_page - iommu_start != pages); return 0; @@ -391,7 +390,6 @@ static inline int dma_map_cont(struct scatterlist *sg, int start, int stopat, { if (!need) { BUG_ON(stopat - start != 1); - *sout = sg[start]; sout->dma_length = sg[start].length; return 0; } From e9bb4c9929a63b23dcc637fae312b36b038bdc61 Mon Sep 17 00:00:00 2001 From: Linus Torvalds Date: Sun, 12 Feb 2006 16:27:25 -0800 Subject: [PATCH 48/48] Linux v2.6.16-rc3 --- Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Makefile b/Makefile index a1158d1c051e..74d67b2c35d9 100644 --- a/Makefile +++ b/Makefile @@ -1,7 +1,7 @@ VERSION = 2 PATCHLEVEL = 6 SUBLEVEL = 16 -EXTRAVERSION =-rc2 +EXTRAVERSION =-rc3 NAME=Sliding Snow Leopard # *DOCUMENTATION*