From 9390bd479b99395ce69d41d817c7a261b9a8581a Mon Sep 17 00:00:00 2001 From: Linus Torvalds Date: Fri, 23 Nov 2007 15:17:42 -0500 Subject: [PATCH] Import 2.1.133pre3 --- CREDITS | 8 + Documentation/Configure.help | 956 +++++++++++++++++++++++-------- MAINTAINERS | 62 +- arch/alpha/defconfig | 1 + arch/alpha/kernel/irq.c | 2 +- arch/arm/kernel/ecard.c | 2 +- arch/arm/kernel/hw-ebsa285.c | 2 +- arch/arm/kernel/irq.c | 2 +- arch/i386/config.in | 18 +- arch/i386/defconfig | 57 +- arch/i386/kernel/mtrr.c | 3 +- arch/i386/kernel/time.c | 71 ++- arch/i386/kernel/traps.c | 13 +- arch/i386/lib/Makefile | 3 +- arch/i386/lib/checksum.S | 450 +++++++++++++++ arch/i386/lib/checksum.c | 459 --------------- arch/i386/lib/delay.c | 12 +- arch/i386/lib/old-checksum.c | 19 + arch/i386/lib/usercopy.c | 28 +- arch/i386/mm/init.c | 31 +- arch/mips/kernel/irq.c | 2 +- arch/ppc/8xx_io/uart.c | 2 +- arch/ppc/apus_defconfig | 1 + arch/ppc/chrp_defconfig | 1 + arch/ppc/common_defconfig | 1 + arch/ppc/config.in | 3 + arch/ppc/defconfig | 1 + arch/ppc/kernel/Makefile | 2 +- arch/ppc/lib/Makefile | 2 +- arch/ppc/mbx_defconfig | 1 + arch/ppc/pmac_defconfig | 1 + arch/ppc/prep_defconfig | 1 + arch/sparc/ap1000/util.c | 2 +- drivers/acorn/block/fd1772.c | 4 +- drivers/acorn/net/ether1.c | 10 +- drivers/acorn/scsi/acornscsi.c | 2 +- drivers/acorn/scsi/fas216.c | 2 +- drivers/ap1000/ddv_util.c | 2 +- drivers/block/genhd.c | 119 +++- drivers/block/ide-cd.c | 56 +- drivers/block/ide-cd.h | 5 +- drivers/block/ide-floppy.c | 3 + drivers/block/ide-probe.c | 2 +- drivers/block/ll_rw_blk.c | 80 --- drivers/block/paride/pg.c | 8 +- drivers/block/paride/pseudo.h | 2 +- drivers/cdrom/cdrom.c | 26 +- drivers/char/Config.in | 27 +- drivers/char/Makefile | 8 + drivers/char/isicom.c | 4 +- drivers/char/radio-gemtek.c | 310 ++++++++++ drivers/char/serial.c | 2 +- drivers/char/tpqic02.c | 4 +- drivers/char/videodev.c | 6 + drivers/isdn/avmb1/b1lli.c | 6 +- drivers/isdn/hisax/callc.c | 9 +- drivers/macintosh/macserial.c | 2 +- drivers/macintosh/via-pmu.c | 2 +- drivers/net/3c523.c | 2 +- drivers/net/Config.in | 4 + drivers/pci/oldproc.c | 2 +- drivers/sbus/char/bpp.c | 4 +- drivers/sbus/char/sab82532.c | 2 +- drivers/sbus/char/su.c | 2 +- drivers/scsi/README.tmscsim | 73 +-- drivers/scsi/advansys.c | 4 +- drivers/scsi/dc390.h | 4 +- drivers/scsi/g_NCR5380.c | 8 +- drivers/scsi/gdth.c | 2 +- drivers/scsi/i91uscsi.c | 2 +- drivers/scsi/scsi_error.c | 11 +- drivers/scsi/scsiiom.c | 570 ++++++++++-------- drivers/scsi/st.c | 9 +- drivers/scsi/tmscsim.c | 577 ++++++++++--------- drivers/scsi/tmscsim.h | 14 +- drivers/sound/Config.in | 8 +- drivers/sound/ad1848.c | 148 ++--- drivers/sound/cs4232.c | 6 +- drivers/sound/es1370.c | 29 +- drivers/sound/es1371.c | 46 +- drivers/sound/lowlevel/Config.in | 11 +- drivers/sound/opl3sa.c | 1 + drivers/sound/sb.h | 1 + drivers/sound/sb_common.c | 65 ++- drivers/sound/sb_mixer.c | 213 +++++-- drivers/sound/sb_mixer.h | 77 ++- drivers/sound/softoss_rs.c | 2 +- drivers/sound/sonicvibes.c | 45 +- drivers/sound/trix.c | 1 + fs/Config.in | 76 ++- fs/binfmt_misc.c | 10 +- fs/buffer.c | 3 +- fs/devices.c | 30 +- fs/fat/file.c | 6 + fs/file_table.c | 33 +- fs/hfs/ChangeLog | 21 + fs/hfs/bdelete.c | 9 +- fs/hfs/extent.c | 9 +- fs/hfs/hfs.h | 2 +- fs/hfs/inode.c | 1 + fs/hfs/mdb.c | 2 +- fs/hfs/sysdep.c | 19 +- fs/lockd/host.c | 8 +- fs/lockd/svc.c | 2 +- fs/locks.c | 4 +- fs/namei.c | 14 +- fs/ncpfs/inode.c | 7 +- fs/nfs/dir.c | 5 - fs/nfsd/nfsfh.c | 2 +- fs/open.c | 44 +- fs/read_write.c | 3 +- fs/smbfs/inode.c | 2 +- include/asm-alpha/machvec.h | 7 + include/asm-alpha/pgtable.h | 1 + include/asm-alpha/softirq.h | 6 +- include/asm-alpha/spinlock.h | 6 +- include/asm-i386/bitops.h | 6 +- include/asm-i386/checksum.h | 6 +- include/asm-i386/posix_types.h | 12 +- include/asm-i386/smplock.h | 2 +- include/asm-i386/system.h | 28 +- include/asm-i386/uaccess.h | 76 +-- include/asm-ppc/softirq.h | 6 +- include/linux/atalk.h | 2 +- include/linux/file.h | 48 +- include/linux/fs.h | 12 +- include/linux/genhd.h | 65 ++- include/linux/hfs_fs_i.h | 3 + include/linux/ipc.h | 5 + include/linux/ipx.h | 1 + include/linux/module.h | 24 +- include/linux/msdos_fs_sb.h | 8 +- include/linux/sem.h | 1 + include/linux/swap.h | 1 + include/linux/videodev.h | 2 + include/net/sock.h | 5 + include/video/fbcon.h | 13 +- ipc/sem.c | 316 +++++----- kernel/ksyms.c | 4 +- kernel/module.c | 15 +- kernel/sched.c | 46 +- mm/page_io.c | 213 ++++--- net/appletalk/aarp.c | 2 +- net/appletalk/ddp.c | 26 +- net/bridge/br.c | 2 +- net/ipv6/af_inet6.c | 2 +- net/ipx/af_ipx.c | 101 +++- net/sched/sch_api.c | 2 +- net/sunrpc/auth.c | 4 +- net/sunrpc/xprt.c | 4 +- scripts/Menuconfig | 126 ++-- 151 files changed, 4061 insertions(+), 2323 deletions(-) create mode 100644 arch/i386/lib/checksum.S delete mode 100644 arch/i386/lib/checksum.c create mode 100644 arch/i386/lib/old-checksum.c create mode 100644 drivers/char/radio-gemtek.c diff --git a/CREDITS b/CREDITS index b1fe938a9175..7a0675d46124 100644 --- a/CREDITS +++ b/CREDITS @@ -84,6 +84,14 @@ S: 20 Ames Street S: Cambridge, Massachusetts 02139 S: USA +N: Jens Axboe +E: axboe@image.dk +D: Linux CD-ROM maintainer +D: jiffies wrap fixes + schedule timeouts depending on HZ == 100 +S: Peter Bangs Vej 258, 2TH +S: 2500 Valby +S: Denmark + N: John Aycock E: aycock@cpsc.ucalgary.ca D: Adaptec 274x driver diff --git a/Documentation/Configure.help b/Documentation/Configure.help index 8567a867360f..9470b48650db 100644 --- a/Documentation/Configure.help +++ b/Documentation/Configure.help @@ -21,7 +21,7 @@ # # Information about what a kernel is, what it does, how to patch and # compile it and much more is contained in the Kernel-HOWTO, available -# via FTP (user: anonymous) from sunsite.unc.edu in the directory +# via FTP (user: anonymous) from metalab.unc.edu in the directory # /pub/Linux/docs/HOWTO. Before you start compiling, make sure that # you have the necessary versions of all programs and libraries # required to compile and run this kernel; they are listed in the file @@ -80,6 +80,29 @@ CONFIG_EXPERIMENTAL you say Y here, you will be offered the choice of using features or drivers that are currently considered to be in the alpha-test phase. +Symmetric Multi Processing +CONFIG_SMP + This enables support for systems with more than one CPU. If you have a + system with only one CPU, like most personal computers, say N. If you + have a system with more than one CPU, say Y. + + A non-SMP kernel will run on any machine, but will use only one CPU of + a multi-CPU machine. An SMP kernel will run on many, but not all, + single-CPU machines. On a single-CPU machine, a non-SMP kernel + will run faster than an SMP kernel. + + People using multiprocessor machines should also say Y to "Enhanced + Real Time Clock Support", below. The "Advanced Power Management" + code will be disabled in an SMP kernel. + + If you don't know what to do here, say N. + + See also: Documentation/SMP.txt, Documentation/smp.tex, + Documentation/smp.txt, and Documentation/IO-APIC.txt. Also see the + SMP-FAQ on the WWW at http://www.irisa.fr/prive/mentre/smp-faq/ (to + browse the WWW, you need to have access to a machine on the Internet + that has a program like lynx or netscape). + Kernel math emulation CONFIG_MATH_EMULATION Linux can emulate a math coprocessor (used for floating point @@ -97,7 +120,7 @@ CONFIG_MATH_EMULATION loader (lilo or loadlin) about how to pass options to the kernel at boot time. The lilo procedure is also explained in the SCSI-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO.) This means that it is a + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO.) This means that it is a good idea to say Y here if you intend to use this kernel on different machines. More information about the internals of Linux math coprocessor emulation can be found in @@ -238,11 +261,11 @@ CONFIG_BLK_DEV_IDE contained in Documentation/ide.txt. For detailed information about hard drives, consult the Disk-HOWTO and the Multi-Disk-HOWTO, available via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. To fine-tune IDE drive/interface parameters for improved performance, look for the hdparm package at - ftp://sunsite.unc.edu:/pub/Linux/kernel/patches/diskdrives/ + ftp://metalab.unc.edu:/pub/Linux/kernel/patches/diskdrives/ If you have one or more IDE drives, say Y here. If your system has no IDE drives, or if memory requirements are really tight, you could @@ -264,7 +287,7 @@ CONFIG_BLK_DEV_HD_ONLY If you are unsure, then just choose the Enhanced IDE/MFM/RLL driver instead of this one. For more detailed information, read the Disk-HOWTO, available via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. People with SCSI-only systems can say N here. @@ -307,7 +330,7 @@ CONFIG_BLK_DEV_IDECD a newer protocol used by IDE CDROM and TAPE drives, similar to the SCSI protocol. Most new CDROM drives use ATAPI, including the NEC-260, Mitsumi FX400, Sony 55E, and just about all non-SCSI - double(2X), quad(4X), and six(6X) speed drives. + double(2X) or better speed drives. If you say Y here, the CDROM drive will be identified at boot time along with other IDE devices, as "hdb" or "hdc", or something @@ -316,11 +339,11 @@ CONFIG_BLK_DEV_IDECD to say Y or M to "ISO 9660 CDROM filesystem support". Read the CDROM-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO and the file + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO and the file Documentation/cdrom/ide-cd. Note that older versions of lilo (the Linux boot loader) cannot properly deal with IDE/ATAPI CDROMs, so install lilo-16 or higher, available from - ftp://sunsite.unc.edu/pub/Linux/system/Linux-boot/lilo. + ftp://metalab.unc.edu/pub/Linux/system/Linux-boot/lilo. If you want to compile the driver as a module ( = code which can be inserted in and removed from the running kernel whenever you want), @@ -402,7 +425,7 @@ CONFIG_BLK_DEV_CMD640 bootparam" or see the documentation of your boot loader about how to pass options to the kernel. The lilo procedure is also explained in the SCSI-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO.) + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO.) The CMD640 chip is also used on add-in cards by Acculogic, and on the "CSA-6400E PCI to IDE controller" that some people have. For @@ -448,7 +471,7 @@ CONFIG_BLK_DEV_IDEDMA for these drives, but you can change that by saying Y to the following question "Use DMA by default when available". You can get the latest version of the hdparm utility via anonymous FTP from - ftp://sunsite.unc.edu/pub/Linux/system/hardware/. + ftp://metalab.unc.edu/pub/Linux/system/hardware/. Read the comments at the beginning of drivers/block/idedma.c and the file Documentation/ide.txt for more information. @@ -872,7 +895,7 @@ CONFIG_BLK_DEV_MD More information about Software RAID on Linux is contained in the Software-RAID mini-HOWTO, available via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO/mini. There you will also + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO/mini. There you will also learn where to get the supporting user space utilities raidtools. If unsure, say N. @@ -900,7 +923,7 @@ CONFIG_MD_STRIPED Information about Software RAID on Linux is contained in the Software-RAID mini-HOWTO, available via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO/mini. There you will also + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO/mini. There you will also learn where to get the supporting user space utilities raidtools. If you want to compile this as a module ( = code which can be @@ -922,7 +945,7 @@ CONFIG_MD_MIRRORING Information about Software RAID on Linux is contained in the Software-RAID mini-HOWTO, available via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO/mini. There you will also + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO/mini. There you will also learn where to get the supporting user space utilities raidtools. If you want to use such a RAID-1 set, say Y. This code is also @@ -945,7 +968,7 @@ CONFIG_MD_RAID5 Information about Software RAID on Linux is contained in the Software-RAID mini-HOWTO, available via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO/mini. There you will also + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO/mini. There you will also learn where to get the supporting user space utilities raidtools. If you want to use such a RAID-4/RAID-5 set, say Y. This code is @@ -1044,7 +1067,7 @@ CONFIG_NET_ALIAS address they listen on (e.g. "multihosting" or "virtual domains" or "virtual hosting services" on the web server apache and the ftp server wuftpd -- read the Virtual-Services-HOWTO, available via FTP - (user: anonymous) from ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO) + (user: anonymous) from ftp://metalab.unc.edu/pub/Linux/docs/HOWTO) or for connecting to different logical networks through the same physical interface (most commonly an Ethernet networking card). See Documentation/networking/alias.txt for more info. @@ -1150,7 +1173,7 @@ CONFIG_ALPHA_AVANTI http://www.azstarnet.com/~axplinux/ (to browse the WWW, you need to have access to a machine on the Internet that has a program like lynx or netscape) and also the Alpha-HOWTO, available via FTP (user: - anonymous) from ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. For this + anonymous) from ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. For this question, it suffices to give a unique prefix of the option you want to choose. The choices: ** Avanti: This is for Mustang (AS200), M3 (AS250), Avanti (AS400) @@ -1232,7 +1255,7 @@ CONFIG_SERIAL_MANY_PORTS standard COM 1/2/3/4 ports. This may happen if you have an AST FourPort, Accent Async, Boca (read the Boca mini-HOWTO, available via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO/mini), or other custom + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO/mini), or other custom serial port hardware which acts similar to standard serial port hardware. If you only use the standard COM 1/2/3/4 ports, you can say N here to save some memory. You can also say Y if you have an @@ -1285,7 +1308,7 @@ CONFIG_PCI your box. Other bus systems are ISA, EISA, Microchannel (MCA) or VESA. If you have PCI, say Y, otherwise N. The PCI-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO, contains valuable + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO, contains valuable information about which PCI hardware does work under Linux and which doesn't. @@ -1348,8 +1371,7 @@ CONFIG_MCA MicroChannel Architecture is found in some IBM PS/2 machines and laptops. It is a bus system similar to PCI or ISA. See Documentation/mca.txt (and especially the web page given there) - before attempting to build an MCA bus kernel. Note that this is - still experimental code. + before attempting to build an MCA bus kernel. System V IPC CONFIG_SYSVIPC @@ -1359,13 +1381,13 @@ CONFIG_SYSVIPC thing, and some programs won't run unless you say Y here. In particular, if you want to run the DOS emulator dosemu under Linux (read the DOSEMU-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO), you'll need to say Y + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO), you'll need to say Y here. You can find documentation about IPC with "info ipc" and also in section 6.4 of the Linux Programmer's Guide, available via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/docs/LDP/programmers-guide. + ftp://metalab.unc.edu/pub/Linux/docs/LDP/programmers-guide. Saying Y here enlarges your kernel by about 7 KB. Just say Y. @@ -1410,7 +1432,7 @@ CONFIG_BINFMT_ELF want to say Y here. Information about ELF is contained in the ELF HOWTO available via - FTP (user: anonymous) at ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + FTP (user: anonymous) at ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. If you find that after upgrading from Linux kernel 1.2 and saying Y here, you still can't run any ELF binaries (they just crash), then @@ -1455,7 +1477,7 @@ CONFIG_BINFMT_JAVA If you want to execute JAVA binaries, read the Java on Linux HOWTO, available via FTP (user: anonymous) at - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. You will then need to + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. You will then need to install the run time system contained in the Java Developers Kit (JDK) as described in the HOWTO. This is completely independent of the Linux kernel and you do NOT need to say Y here for this to work. @@ -1499,7 +1521,7 @@ CONFIG_BINFMT_MISC programs that need an interpreter to run like Java, Python or Emacs-Lisp. It's also useful if you often run DOS executables under the Linux DOS emulator DOSEMU (read the DOSEMU-HOWTO, available in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO). Once you have + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO). Once you have registered such a binary class with the kernel, you can start one of those programs simply by typing in its name at a shell prompt; Linux will automatically feed it to the correct interpreter. @@ -1553,24 +1575,6 @@ CONFIG_M386 In rare cases, it can make sense to specify "Pentium" even if running on a 486: the kernel will be smaller but slower. - If you have a single processor machine, make sure that the line - "SMP=1" at the top of the toplevel kernel Makefile is commented out; - if you have a multi processor machine and want Linux to use all the - processors in parallel (Symmetric Multi Processing), make sure that - the line "SMP=1" is not commented out and read Documentation/smp and - Documentation/IO-APIC.txt and the SMP-FAQ on the WWW at - http://www.irisa.fr/prive/mentre/smp-faq/ (to browse the WWW, you - need to have access to a machine on the Internet that has a program - like lynx or netscape). People using multiprocessor machines should - also say Y to "Enhanced Real Time Clock Support", below. - - If you want to compile a kernel that works on both single processor - and multi processor machines, it is possible to set SMP=1. The - "Advanced Power Management" code (see configuration option below) - will not work in that scenario, though. In addition, the kernel will - be slower on single processor machines, and other problems may - appear, so this is not recommended. - If you don't know what to do, choose "386". VGA text console @@ -1581,7 +1585,7 @@ CONFIG_VGA_CONSOLE The program SVGATextMode can be used to utilize SVGA video cards to their full potential in text mode. Download it via FTP (user: - anonymous) from ftp://sunsite.unc.edu/pub/Linux/utils/console. + anonymous) from ftp://metalab.unc.edu/pub/Linux/utils/console. Say Y. @@ -1596,7 +1600,7 @@ CONFIG_VIDEO_SELECT "man bootparam" or see the documentation of your boot loader about how to pass options to the kernel. The lilo procedure is also explained in the SCSI-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. Read + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Read Documentation/svga.txt for more information about the Video mode selection support. If unsure, say N. @@ -2232,10 +2236,10 @@ CONFIG_IP_FIREWALL If you want to configure your Linux box as a packet filter firewall for a local TCP/IP based network, say Y here. You may want to read the FIREWALL-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Also, you will need the ipchains tool (available on the WWW at - http://www.adelaide.net.au/~rustcorp/) to allow selective blocking + http://www.rustcorp.com/linux/ipchains/) to allow selective blocking of Internet traffic based on type, origin and destination. Note that the Linux firewall code has changed and the old program called ipfwadm won't work anymore. @@ -2336,9 +2340,7 @@ CONFIG_NET_IPIP Saying Y to this option will produce two modules ( = code which can be inserted in and removed from the running kernel whenever you - want), one encapsulator called tunnel.o and one decapsulator called - ipip.o. You can read details in drivers/net/README.tunnel. Most - people won't need this and can say N. + want). Most people won't need this and can say N. IP: GRE tunnels over IP CONFIG_NET_IPGRE @@ -2387,7 +2389,7 @@ CONFIG_IP_MASQUERADE Linux box to the Internet using SLiRP [SLiRP is a SLIP/PPP emulator that works if you have a regular dial up shell account on some UNIX computer; get it via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/system/network/serial/ ].) + ftp://metalab.unc.edu/pub/Linux/system/network/serial/ ].) The IP masquerading code will only work if IP forwarding is enabled in your kernel; you can do this by saying Y to "/proc @@ -2400,7 +2402,7 @@ CONFIG_IP_MASQUERADE Details on how to set things up are contained in the IP Masquerade mini-HOWTO, available via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO/mini; there's also some + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO/mini; there's also some information on the WWW at http://www.tor.shaw.wave.ca/~ambrose/kernel21.html. @@ -2427,7 +2429,7 @@ CONFIG_IP_MASQUERADE_ICMP IP: masquerading special modules support CONFIG_IP_MASQUERADE_MOD This provides support for special modules that can modify the - rewriting rules used when masquerading. Please not that this feature + rewriting rules used when masquerading. Please note that this feature adds a little overhead in the input packet processing chain. Examples of such modules are ipautofw (allowing the masquerading of @@ -2437,7 +2439,7 @@ CONFIG_IP_MASQUERADE_MOD You will need the user space program "ipmasqadm" to use these additional modules; you can download it from - http://juanjox.home.ml.org/ + http://juanjox.linuxhq.com/ All this additional code is still under development and so is currently marked EXPERIMENTAL. @@ -2452,7 +2454,7 @@ CONFIG_IP_MASQUERADE_IPAUTOFW ftp://ftp.netis.com/pub/members/rlynch/ You will also need the ipmasqadm tool available from - http://juanjox.home.ml.org . + http://juanjox.linuxhq.com/ . The ipautofw code is still under development and so is currently marked EXPERIMENTAL. If you want to try it, say Y. @@ -2483,7 +2485,7 @@ CONFIG_IP_MASQUERADE_IPPORTFW see ftp://ftp.compsoc.net/users/steve/ipportfw/linux21/ You will need the user space program "ipmasqadm" which can be - downloaded from http://juanjox.home.ml.org/ + downloaded from http://juanjox.linuxhq.com/ The portfw code is still under development and so is currently marked EXPERIMENTAL. If you want to try it, say Y. @@ -2494,12 +2496,12 @@ CONFIG_IP_MASQUERADE_IPPORTFW it as a module, say M here and read Documentation/modules.txt. IP: ipmarkfw masquerade support -CONFIG_IP_MASQUERADE_IPMARKFW - This provides functionality equivalent to port forwarding, the - difference is that Mark Forwarding uses "firewalling mark" to select - which packets must forward (see ipchains(8), "-m" argument). +CONFIG_IP_MASQUERADE_MFW + This provides functionality similar to port forwarding, the + difference is that Firewall Mark Forwarding uses "firewalling mark" + to select which packets must forward (see ipchains(8), "-m" argument). - The markfw code is still under development and so is currently + The ip_masq_mfw code is still under development and so is currently marked EXPERIMENTAL. If you want to try it, say Y. This code is also available as a module ( = code which can be @@ -2538,7 +2540,7 @@ CONFIG_IP_ALIAS need to have access to a machine on the Internet that has a program like lynx or netscape) and also in the Virtual-Hosting-HOWTO, available via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Another scenario would be that there are two logical networks living on your local Ethernet and you want to access them both with the @@ -2605,7 +2607,7 @@ CONFIG_INET_RARP If you actually want to use a diskless Sun 3 machine as an X terminal to Linux, say Y here and fetch Linux-Xkernel from - ftp://sunsite.unc.edu/pub/Linux/system/network/boot.net/. + ftp://metalab.unc.edu/pub/Linux/system/network/boot.net/. Superior solutions to the problem of booting and configuring machines over a net connection are given by the protocol BOOTP and @@ -2756,9 +2758,9 @@ CONFIG_IPX used for local networks of Windows machines. You need it if you want to access Novell NetWare file or print servers using the Linux Novell client ncpfs (available via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/system/filesystems/) or from within + ftp://metalab.unc.edu/pub/Linux/system/filesystems/) or from within the Linux DOS emulator DOSEMU (read the DOSEMU-HOWTO, available in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO). In order to do the + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO). In order to do the former, you'll also have to say Y to "NCP filesystem support", below. @@ -2768,9 +2770,9 @@ CONFIG_IPX To turn your Linux box into a fully featured NetWare file server and IPX router, say Y here and fetch either lwared from - ftp://sunsite.unc.edu/pub/Linux/system/network/daemons/ or mars_nwe + ftp://metalab.unc.edu/pub/Linux/system/network/daemons/ or mars_nwe from ftp://ftp.gwdg.de/pub/linux/misc/ncpfs. For more information, - read the IPX-HOWTO in ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + read the IPX-HOWTO in ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. General information about how to connect Linux, Windows machines and Macs is on the WWW at http://www.eats.com/linux_mac_win.html (to @@ -2793,7 +2795,7 @@ CONFIG_IPX_INTERN same address). The way this is done is to create a virtual internal "network" inside your box and to assign an IPX address to this network. Say Y here if you want to do this; read the IPX-HOWTO at - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO for details. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO for details. The full internal IPX network enables you to allocate sockets on different virtual nodes of the internal network. This is done by @@ -2823,7 +2825,7 @@ CONFIG_SPX space programs lwared or mars_nwe for the server side). Say Y here if you have use for SPX; read the IPX-HOWTO at - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO for details. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO for details. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -2844,7 +2846,7 @@ CONFIG_ATALK slower LocalTalk is AppleTalk over a proprietary apple network using serial links. EtherTalk and LocalTalk are fully supported by Linux. The NET-2-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO contains valuable + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO contains valuable information as well. General information about how to connect Linux, Windows machines and @@ -2928,7 +2930,7 @@ CONFIG_HAMRADIO (to browse the WWW, you need to have access to a machine on the Internet that has a program like lynx or netscape) and the HAM-HOWTO and the AX25-HOWTO, both available via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Note that the answer to this question won't directly affect the kernel: saying N will just cause this configure script to skip all @@ -2952,7 +2954,7 @@ CONFIG_AX25 Information about where to get supporting software for Linux amateur radio as well as information about how to configure an AX.25 port is contained in the AX25-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. You might also want to + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. You might also want to check out the file Documentation/networking/ax25.txt in the kernel source. More information about digital amateur radio in general is on the WWW at http://www.tapr.org/tapr/html/pkthome.html. (To browse @@ -2990,7 +2992,7 @@ CONFIG_NETROM A comprehensive listing of all the software for Linux amateur radio users as well as information about how to configure an AX.25 port is contained in the AX25-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. You also might want to + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. You also might want to check out the file Documentation/networking/ax25.txt. More information about digital amateur radio in general is on the WWW at http://www.tapr.org/tapr/html/pkthome.html (to browse the WWW, you @@ -3011,7 +3013,7 @@ CONFIG_ROSE A comprehensive listing of all the software for Linux amateur radio users as well as information about how to configure an AX.25 port is contained in the AX25-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. You also might want to + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. You also might want to check out the file Documentation/networking/ax25.txt. More information about digital amateur radio in general is on the WWW at http://www.tapr.org/tapr/html/pkthome.html (to browse the WWW, you @@ -3079,7 +3081,7 @@ CONFIG_DMASCC (http://www.paccomm.com/gracilis.html) boards. They are detected automatically. If you have one of these cards, say Y here and read the AX25-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO/. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO/. This driver can operate multiple boards simultaneously. If you compile it as a module (by saying M instead of Y), it will be called @@ -3105,7 +3107,7 @@ CONFIG_SCC in order to communicate with other computers. If you want to use this, read Documentation/networking/z8530drv.txt and the AX25-HOWTO, available via FTP (user: anonymous) at - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. Also make sure to say Y + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Also make sure to say Y to "Amateur Radio AX.25 Level 2" support. If you want to compile this as a module ( = code which can be @@ -3364,7 +3366,7 @@ CONFIG_BRIDGE probably contains several Ethernet devices, but the kernel is not able to recognize more than one at boot time without help; for details read the Ethernet-HOWTO, available via FTP (user: anonymous) - in ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. The Bridging code is + in ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. The Bridging code is still in test. If unsure, say N. Packet socket @@ -3419,7 +3421,7 @@ CONFIG_SCSI port version of the 100 MB IOMEGA ZIP drive. Please read the SCSI-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. The + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. The SCSI-Programming-HOWTO contains information about how to add or remove an SCSI device from a running Linux machine without rebooting. @@ -3437,7 +3439,7 @@ CONFIG_BLK_DEV_SD If you want to use a SCSI hard disk or the SCSI or parallel port version of the IOMEGA ZIP drive under Linux, say Y and read the SCSI-HOWTO, the Disk-HOWTO and the Multi-Disk-HOWTO, available via - FTP (user: anonymous) in ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + FTP (user: anonymous) in ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This is NOT for SCSI CDROMs. This driver is also available as a module ( = code which can be @@ -3453,7 +3455,7 @@ SCSI tape support CONFIG_CHR_DEV_ST If you want to use a SCSI tape drive under Linux, say Y and read the SCSI-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO and + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO and drivers/scsi/README.st in the kernel source. This is NOT for SCSI CDROMs. @@ -3467,7 +3469,7 @@ SCSI CDROM support CONFIG_BLK_DEV_SR If you want to use a SCSI CDROM under Linux, say Y and read the SCSI-HOWTO and the CDROM-HOWTO from - ftp://sunsite.unc.edu:/pub/Linux/docs/HOWTO. Also make sure to say Y + ftp://metalab.unc.edu:/pub/Linux/docs/HOWTO. Also make sure to say Y or M to "ISO 9660 CDROM filesystem support" later. This driver is also available as a module ( = code which can be @@ -3491,11 +3493,11 @@ CONFIG_CHR_DEV_SG directly, so you need some additional software which knows how to talk to these devices using the SCSI protocol. For CD-writers, you would need the program cdwrite, available via FTP (user: anonymous) - from ftp://sunsite.unc.edu/pub/Linux/utils/disk-management; for + from ftp://metalab.unc.edu/pub/Linux/utils/disk-management; for other devices, it's possible that you'll have to write the driver software yourself, so have a look at the SCSI-HOWTO and at the SCSI-Programming-HOWTO, both available via FTP (user: anonymous) in - ftp://sunsite.unc.edu:/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu:/pub/Linux/docs/HOWTO. If you want to compile this as a module ( = code which can be inserted in and removed from the running kernel whenever you want), @@ -3558,7 +3560,7 @@ CONFIG_SCSI_AHA152X This is support for the AHA-1510, AHA-1520, AHA-1522, and AHA-2825 SCSI host adapters. It is explained in section 3.3 of the SCSI-HOWTO, available via FTP (user: anonymous) at - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. You might also want to + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. You might also want to read the comments at the top of drivers/scsi/aha152x.c. This driver is also available as a module ( = code which can be @@ -3570,7 +3572,7 @@ Adaptec AHA1542 support CONFIG_SCSI_AHA1542 This is support for a SCSI host adapter. It is explained in section 3.4 of the SCSI-HOWTO, available via FTP (user: anonymous) at - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. Note that Trantor was + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Note that Trantor was recently purchased by Adaptec, and some former Trantor products are being sold under the Adaptec name. If it doesn't work out of the box, you may have to change some settings in drivers/scsi/aha1542.h. @@ -3584,7 +3586,7 @@ Adaptec AHA1740 support CONFIG_SCSI_AHA1740 This is support for a SCSI host adapter. It is explained in section 3.5 of the SCSI-HOWTO, available via FTP (user: anonymous) at - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. If it doesn't work out + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. If it doesn't work out of the box, you may have to change some settings in drivers/scsi/aha1740.h. @@ -3603,7 +3605,7 @@ CONFIG_SCSI_AIC7XXX found by checking the help file for each of the available configuration options. You also want to read drivers/scsi/README.aic7xxx and the SCSI-HOWTO, available via FTP - (user: anonymous) at ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + (user: anonymous) at ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Note that the AHA2920 SCSI host adapter is *not* supported by this driver; choose "Future Domain 16xx SCSI support" instead if you have one of those. @@ -3680,7 +3682,7 @@ BusLogic SCSI support CONFIG_SCSI_BUSLOGIC This is support for BusLogic MultiMaster and FlashPoint SCSI Host Adapters. Consult the SCSI-HOWTO, available via anonymous FTP from - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO, and the files + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO, and the files README.BusLogic and README.FlashPoint in drivers/scsi for more information. If this driver does not work correctly without modification, please contact the author, Leonard N. Zubkoff, by @@ -3703,7 +3705,7 @@ DTC3180/3280 SCSI support CONFIG_SCSI_DTC3280 This is support for DTC 3180/3280 SCSI Host Adapters. Please read the SCSI-HOWTO, available via FTP (user: anonymous) at - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO and the file + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO and the file drivers/scsi/README.dtc3x80. This driver is also available as a module ( = code which can be @@ -3711,15 +3713,18 @@ CONFIG_SCSI_DTC3280 The module will be called dtc.o. If you want to compile it as a module, say M here and read Documentation/modules.txt. -EATA-DMA (DPT, NEC, AT&T, SNI, AST, Olivetti, Alphatronix) support +EATA-DMA [Obsolete] (DPT, NEC, AT&T, SNI, AST, Olivetti, Alphatronix) support CONFIG_SCSI_EATA_DMA + This driver is obsolete. You should normally be using the generic EATA + driver for this hardware. + This is support for the EATA-DMA protocol compliant SCSI Host Adapters like the SmartCache III/IV, SmartRAID controller families and the DPT PM2011B and PM2012B controllers. Note that there is also another driver for the same hardware: "EATA ISA/EISA/PCI support". You should only say Y to one of them. Please read the SCSI-HOWTO, available via FTP (user: anonymous) at - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -3734,7 +3739,7 @@ CONFIG_SCSI_EATA_PIO doing so, since this driver only supports hard disks and lacks numerous features. You might want to have a look at the SCSI-HOWTO, available via FTP (user: anonymous) at - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. If you want to compile this as a module ( = code which can be inserted in and removed from the running kernel whenever you want), @@ -3748,7 +3753,7 @@ CONFIG_SCSI_U14_34F this hardware. If the driver doesn't work out of the box, you may have to change some settings in drivers/scsi/u14-34f.c. Read the SCSI-HOWTO, available via FTP (user: anonymous) at - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. Note that there is also + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Note that there is also another driver for the same hardware: "UltraStor SCSI support", below. You should say Y to both only if you want 24F support as well. @@ -3778,7 +3783,7 @@ CONFIG_SCSI_FUTURE_DOMAIN other adapters based on the Future Domain chipsets (Quantum ISA-200S, ISA-250MG; Adaptec AHA-2920; and at least one IBM board). It is explained in section 3.7 of the SCSI-HOWTO, available via FTP - (user: anonymous) at ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + (user: anonymous) at ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -3797,7 +3802,7 @@ CONFIG_SCSI_GENERIC_NCR5380 This is the generic NCR family of SCSI controllers, not to be confused with the NCR 53c7 or 8xx controllers. It is explained in section 3.8 of the SCSI-HOWTO, available via FTP (user: anonymous) - at ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. If it doesn't work + at ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. If it doesn't work out of the box, you may have to change some settings in drivers/scsi/g_NCR5380.h. @@ -3826,7 +3831,7 @@ CONFIG_SCSI_NCR53C7xx This is the 53c7 and 8xx NCR family of SCSI controllers, not to be confused with the NCR 5380 controllers. It is explained in section 3.8 of the SCSI-HOWTO, available via FTP (user: anonymous) at - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. If it doesn't work out + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. If it doesn't work out of the box, you may have to change some settings in drivers/scsi/53c7,8xx.h. @@ -4011,7 +4016,7 @@ CONFIG_SCSI_IBMMCA bootparam" or see the documentation of your boot loader about how to pass options to the kernel. The lilo procedure is also explained in the SCSI-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. If you want to compile this driver as a module ( = code which can be inserted in and removed from the running kernel whenever you want), @@ -4062,6 +4067,17 @@ CONFIG_IBMMCA_SCSI_DEV_RESET you know that one of your older devices needs it; N is the safe answer. +NCR 53C9x MCA support +CONFIG_SCSI_MCA_53C9X + Some Microchannel machines, notably the NCR 35xx line, use a SCSI + controller based on the NCR 53C94. This driver will allow use of + the controller on the 3550, and very possibly others. + + If you want to compile this as a module (= code which can be inserted + and removed from the running kernel whenever you want), + say M here and read Documentation/modules.txt. The module will be + called mca_53c9x.o. + Always IN2000 SCSI support CONFIG_SCSI_IN2000 This is support for an ISA bus SCSI host adapter. You'll find more @@ -4078,7 +4094,7 @@ PAS16 SCSI support CONFIG_SCSI_PAS16 This is support for a SCSI host adapter. It is explained in section 3.10 of the SCSI-HOWTO, available via FTP (user: anonymous) at - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. If it doesn't work out + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. If it doesn't work out of the box, you may have to change some settings in drivers/scsi/pas16.h. @@ -4091,7 +4107,7 @@ PCI2000 support CONFIG_SCSI_PCI2000 This is support for the PCI2000I EIDE interface card which acts as a SCSI host adapter. Please read the SCSI-HOWTO, available via FTP - (user: anonymous) at ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + (user: anonymous) at ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module called pci2000.o ( = code which can be inserted in and removed from the running kernel @@ -4102,7 +4118,7 @@ PCI2220i support CONFIG_SCSI_PCI2220I This is support for the PCI2220i EIDE interface card which acts as a SCSI host adapter. Please read the SCSI-HOWTO, available via FTP - (user: anonymous) at ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + (user: anonymous) at ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module called pci2220i.o ( = code which can be inserted in and removed from the running kernel @@ -4113,7 +4129,7 @@ PSI240i support CONFIG_SCSI_PSI240I This is support for the PSI240i EIDE interface card which acts as a SCSI host adapter. Please read the SCSI-HOWTO, available via FTP - (user: anonymous) at ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + (user: anonymous) at ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module called psi240i.o ( = code which can be inserted in and removed from the running kernel @@ -4129,7 +4145,7 @@ CONFIG_SCSI_QLOGIC_FAS the Qlogic ISP driver though. Information about this driver is contained in drivers/scsi/README.qlogicfas. You should also read the SCSI-HOWTO, available via FTP (user: anonymous) at - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -4146,7 +4162,7 @@ CONFIG_SCSI_QLOGIC_ISP Please read the file drivers/scsi/README.qlogicisp. You should also read the SCSI-HOWTO, available via FTP (user: anonymous) at - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -4158,7 +4174,7 @@ CONFIG_SCSI_SEAGATE These are 8-bit SCSI controllers; the ST-01 is also supported by this driver. It is explained in section 3.9 of the SCSI-HOWTO, available via FTP (user: anonymous) at - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. If it doesn't work out + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. If it doesn't work out of the box, you may have to change some settings in drivers/scsi/seagate.h. @@ -4171,7 +4187,7 @@ Trantor T128/T128F/T228 SCSI support CONFIG_SCSI_T128 This is support for a SCSI host adapter. It is explained in section 3.11 of the SCSI-HOWTO, available via FTP (user: anonymous) at - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. If it doesn't work out + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. If it doesn't work out of the box, you may have to change some settings in drivers/scsi/t128.h. Note that Trantor was purchased by Adaptec, and some former Trantor products are being sold under the Adaptec name. @@ -4186,7 +4202,7 @@ CONFIG_SCSI_ULTRASTOR This is support for the UltraStor 14F, 24F and 34F SCSI-2 host adapter family. This driver is explained in section 3.12 of the SCSI-HOWTO, available via FTP (user: anonymous) at - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. If it doesn't work out + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. If it doesn't work out of the box, you may have to change some settings in drivers/scsi/ultrastor.h. @@ -4216,7 +4232,7 @@ CONFIG_SCSI_EATA to "PCI BIOS support", the addresses of all the PCI SCSI controllers reported by BIOS32 are probed as well. You want to read the start of drivers/scsi/eata.c and the SCSI-HOWTO, available via FTP (user: - anonymous) at ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + anonymous) at ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Note that there is also another driver for the same hardware available: "EATA-DMA support". You should say Y to only one of them. @@ -4252,7 +4268,7 @@ CONFIG_SCSI_NCR53C406A This is support for the NCR53c406a SCSI host adapter. For user configurable parameters, check out drivers/scsi/NCR53c406.c in the kernel source. Also read the SCSI-HOWTO, available via FTP (user: - anonymous) at ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + anonymous) at ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. If you want to compile this driver as a module ( = code which can be inserted in and removed from the running kernel whenever you want), @@ -4296,7 +4312,7 @@ CONFIG_SCSI_AM53C974 This is support for the AM53/79C974 SCSI host adapters. Please read drivers/scsi/README.AM53C974 for details. Also, the SCSI-HOWTO, available via FTP (user: anonymous) at - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO, is for you. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO, is for you. Note that there is another driver for AM53C974 based adapters: "Tekram DC390(T) and Am53/79C974 (PCscsi) SCSI support", above. @@ -4324,7 +4340,7 @@ CONFIG_SCSI_PPA driver and how to use it you should read the file drivers/scsi/README.ppa. You should also read the SCSI-HOWTO, which is available via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. If you use this driver, + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. If you use this driver, you will still be able to use the parallel port for other tasks, such as a printer; it is safe to compile both drivers into the kernel. @@ -4441,7 +4457,7 @@ CONFIG_NETDEVICES line with a modem either via UUCP (UUCP is a protocol to forward mail and news between unix hosts over telephone lines; read the UUCP-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO) or dialing up a shell + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO) or dialing up a shell account or a BBS, even using term (term is a program which gives you almost full Internet connectivity if you have a regular dial up shell account on some Internet connected Unix computer. Read @@ -4453,7 +4469,7 @@ CONFIG_NETDEVICES you want to use under Linux (make sure you know its name because you will be asked for it and read the Ethernet-HOWTO (especially if you plan to use more than one network card under Linux), available from - ftp://sunsite.unc.edu:/pub/Linux/docs/HOWTO/mini) or if you want to + ftp://metalab.unc.edu:/pub/Linux/docs/HOWTO/mini) or if you want to use SLIP (Serial Line Internet Protocol is the protocol used to send Internet traffic over telephone lines or null modem cables) or CSLIP (compressed SLIP) or PPP (Point to Point Protocol, a better and @@ -4464,7 +4480,7 @@ CONFIG_NETDEVICES Make sure to read the NET-2-HOWTO. Eventually, you will have to read Olaf Kirch's excellent and free book "Network Administrator's - Guide", to be found in ftp://sunsite.unc.edu:/pub/Linux/docs/LDP. If + Guide", to be found in ftp://metalab.unc.edu:/pub/Linux/docs/LDP. If unsure, say Y. Dummy net driver support @@ -4475,7 +4491,7 @@ CONFIG_DUMMY inactive SLIP address seem like a real address for local programs. If you use SLIP or PPP, you might want to say Y here. Read about it in the Network Administrator's Guide, available via FTP (user: - anonymous) from ftp://sunsite.unc.edu/pub/Linux/docs/LDP. Since this + anonymous) from ftp://metalab.unc.edu/pub/Linux/docs/LDP. Since this thing often comes in handy, the default is Y. It won't enlarge your kernel either. What a deal. @@ -4500,11 +4516,11 @@ CONFIG_SLIP Normally, your access provider has to support SLIP in order for you to be able to use it, but there is now a SLIP emulator called SLiRP around (available via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/system/network/serial/ ) which + ftp://metalab.unc.edu/pub/Linux/system/network/serial/ ) which allows you to use SLIP over a regular dial up shell connection. If you plan to use SLiRP, make sure to say Y to CSLIP, below. The NET-2-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO, explains how to + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO, explains how to configure SLIP. Note that you don't need this option if you just want to run term (term is a program which gives you almost full Internet connectivity if you have a regular dial up shell account on @@ -4528,10 +4544,10 @@ CONFIG_SLIP_COMPRESSED answer Y, just in case. You will still be able to use plain SLIP. If you plan to use SLiRP, the SLIP emulator (available via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/system/network/serial/) which allows + ftp://metalab.unc.edu/pub/Linux/system/network/serial/) which allows you to use SLIP over a regular dial up shell connection, you definitely want to say Y here. The NET-2-HOWTO, available via FTP - (user: anonymous) in ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO, + (user: anonymous) in ftp://metalab.unc.edu/pub/Linux/docs/HOWTO, explains how to configure CSLIP. This won't enlarge your kernel. Keepalive and linefill @@ -4559,7 +4575,7 @@ CONFIG_PPP program SLiRP can emulate a PPP line if you just have a regular dial up shell account on some UNIX computer; get it via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/system/network/serial/). Note that + ftp://metalab.unc.edu/pub/Linux/system/network/serial/). Note that you don't need "PPP support" if you just want to run term (term is a program which gives you almost full Internet connectivity if you have a regular dial up shell account on some Internet connected UNIX @@ -4570,7 +4586,7 @@ CONFIG_PPP To use PPP, you need an additional program called pppd as described in Documentation/networking/ppp.txt and in the PPP-HOWTO, available - from ftp://sunsite.unc.edu:/pub/Linux/docs/HOWTO. If you upgrade + from ftp://metalab.unc.edu:/pub/Linux/docs/HOWTO. If you upgrade from an older kernel, you might need to upgrade pppd as well. The PPP option enlarges your kernel by about 16 KB. @@ -4637,7 +4653,7 @@ CONFIG_WAVELAN If you want to use an ISA WaveLAN card under Linux, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. Some more specific + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Some more specific information is contained in Documentation/networking/wavelan.txt and in the source code drivers/net/wavelan.p.h. @@ -4722,8 +4738,8 @@ CONFIG_PLIP If you want to use PLIP, say Y and read the PLIP mini-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO/mini as well as the - NET-2-HOWTO in ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. Note that + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO/mini as well as the + NET-2-HOWTO in ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Note that the PLIP protocol was changed and this PLIP driver won't work together with the PLIP support in Linux versions 1.0.x. This option enlarges your kernel by about 8 KB. @@ -5078,6 +5094,48 @@ CONFIG_HOSTESS_SV11 up to 256Kbits. It supports both PPP and Cisco HDLC At this point, the driver can only be compiled as a module. +COSA/SRP sync serial boards support +CONFIG_COSA + This is a driver for COSA and SRP synchronous serial boards. + These boards enable to connect synchronous serial devices (for + example base-band modems, or any other device with the X.21, V.24, + V.35 or V.36 interface) to your Linux box. The cards can work + as the character device, synchronous PPP network device, or the Cisco + HDLC network device. + + To actually use the COSA or SRP board, you will need user-space + utilities for downloading the firmware to the cards and to set + them up. Look at the http://www.fi.muni.cz/~kas/cosa/ for more + information about the cards (including the pointer to the user-space + utilities). You can also read the comment at the top of the + drivers/net/cosa.c for details about the cards and the driver itself. + + The driver will be compiled as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + The module will be called cosa.o. For general information about + modules read Documentation/modules.txt. + +COSA/SRP sync serial boards support +CONFIG_COSA + This is a driver for COSA and SRP synchronous serial boards. + These boards enable to connect synchronous serial devices (for + example base-band modems, or any other device with the X.21, V.24, + V.35 or V.36 interface) to your Linux box. The cards can work + as the character device, synchronous PPP network device, or the Cisco + HDLC network device. + + To actually use the COSA or SRP board, you will need user-space + utilities for downloading the firmware to the cards and to set + them up. Look at the http://www.fi.muni.cz/~kas/cosa/ for more + information about the cards (including the pointer to the user-space + utilities). You can also read the comment at the top of the + drivers/net/cosa.c for details about the cards and the driver itself. + + The driver will be compiled as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + The module will be called cosa.o. For general information about + modules read Documentation/modules.txt. + WAN Drivers CONFIG_WAN_DRIVERS Say Y to this option if your Linux box contains a WAN card and you @@ -5160,7 +5218,7 @@ CONFIG_NET_ETHERNET If your Linux machine will be connected to an Ethernet and you have an Ethernet network interface card (NIC) installed in your computer, say Y here and read the Ethernet-HOWTO, available via FTP (user: - anonymous) from ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. You will + anonymous) from ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. You will then also have to say Y to the driver for your particular NIC. Note that the answer to this question won't directly affect the @@ -5187,7 +5245,7 @@ Western Digital/SMC cards CONFIG_NET_VENDOR_SMC If you have a network (Ethernet) card belonging to this class, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Note that the answer to this question doesn't directly affect the kernel: saying N will just cause this configure script to skip all @@ -5198,7 +5256,7 @@ WD80*3 support CONFIG_WD80x3 If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5211,7 +5269,7 @@ CONFIG_ULTRAMCA If you have a network (Ethernet) card of this type and are running an MCA based system (PS/2), say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5223,7 +5281,7 @@ SMC Ultra support CONFIG_ULTRA If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Important: There have been many reports that, with some motherboards mixing an SMC Ultra and an Adaptec AHA154x SCSI card (or compatible, @@ -5242,7 +5300,7 @@ SMC Ultra32 EISA support CONFIG_ULTRA32 If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5258,7 +5316,7 @@ CONFIG_SMC9194 into the kernel, and read the file Documentation/networking/smc9.txt and the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you @@ -5272,7 +5330,7 @@ CONFIG_NE2K_PCI with ISA NE2000 cards (they have their own driver, "NE2000/NE1000 support" below). If you have a PCI NE2000 network (Ethernet) card, say Y and read the Ethernet-HOWTO, available via FTP (user: - anonymous) in ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + anonymous) in ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5285,7 +5343,7 @@ CONFIG_NET_VENDOR_RACAL If you have a network (Ethernet) card belonging to this class, such as the NI5010, NI5210 or NI6210, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Note that the answer to this question doesn't directly affect the kernel: saying N will just cause this configure script to skip all @@ -5296,7 +5354,7 @@ NI5010 support CONFIG_NI5010 If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. Note that this is still + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Note that this is still experimental code. This driver is also available as a module ( = code which can be @@ -5309,7 +5367,7 @@ NI5210 support CONFIG_NI52 If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5321,7 +5379,7 @@ NI6510 support CONFIG_NI65 If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5334,7 +5392,7 @@ CONFIG_RTL8139 This is a driver for the Fast Ethernet PCI network cards based on the RTL8129 and RTL8139 chips. If you have one of those, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. If you want to compile this driver as a module ( = code which can be inserted in and removed from the running kernel whenever you want), @@ -5373,14 +5431,14 @@ AMD LANCE and PCnet (AT1500 and NE2100) support CONFIG_LANCE If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. Some LinkSys cards are + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Some LinkSys cards are of this type. 3COM cards CONFIG_NET_VENDOR_3COM If you have a network (Ethernet) card belonging to this class, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Note that the answer to this question doesn't directly affect the kernel: saying N will just cause this configure script to skip all @@ -5391,7 +5449,7 @@ CONFIG_NET_VENDOR_3COM CONFIG_EL1 If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. Also, consider buying a + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Also, consider buying a new card, since the 3c501 is slow, broken, and obsolete: you will have problems. Some people suggest to ping ("man ping") a nearby machine every minute ("man cron") when using this card. @@ -5406,7 +5464,7 @@ CONFIG_EL1 CONFIG_EL2 If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5419,7 +5477,7 @@ CONFIG_ELPLUS Information about this network (Ethernet) card can be found in Documentation/networking/3c505.txt. If you have a card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: - anonymous) in ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + anonymous) in ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. If you want to compile this as a module ( = code which can be inserted in and removed from the running kernel whenever you want), @@ -5431,7 +5489,7 @@ CONFIG_ELPLUS CONFIG_EL16 If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5443,7 +5501,7 @@ CONFIG_EL16 CONFIG_ELMC If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5456,7 +5514,7 @@ CONFIG_EL3 If you have a network (Ethernet) card belonging to the 3Com EtherLinkIII series, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. If your card is not working you may need to use the DOS setup disk to disable Plug & Play mode, and to select the default @@ -5473,7 +5531,7 @@ CONFIG_VORTEX If you have a 3Com "Vortex" (Fast EtherLink 3c590/3c592/3c595/3c597) or "Boomerang" series (EtherLink XL 3c900 or 3c905) network (Ethernet) card, say Y and read the Ethernet-HOWTO, available via - FTP (user: anonymous) in ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + FTP (user: anonymous) in ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. More specific information is in Documentation/networking/vortex.txt and in the comments at the beginning of drivers/net/3c59x.c. @@ -5489,7 +5547,7 @@ CONFIG_NET_ISA of your computer) is ISA (as opposed to EISA, VLB or PCI), say Y. Make sure you know the name of your card. Read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. If unsure, say Y. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. If unsure, say Y. Note that the answer to this question doesn't directly affect the kernel: saying N will just cause this configure script to skip all @@ -5508,7 +5566,7 @@ CONFIG_ARCNET You might also want to have a look at the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO (even though ARCnet is + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO (even though ARCnet is not really Ethernet). This driver is also available as a module ( = code which can be @@ -5596,7 +5654,7 @@ Cabletron E21xx support CONFIG_E2100 If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5609,7 +5667,7 @@ CONFIG_CS89x0 Support for CS89x0 chipset based Ethernet cards. If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO as well as + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO as well as Documentation/networking/cs89x0.txt. If you want to compile this as a module ( = code which can be @@ -5622,7 +5680,7 @@ DEPCA support CONFIG_DEPCA If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO as well as + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO as well as drivers/net/depca.c. If you want to compile this as a module ( = code which can be @@ -5637,7 +5695,7 @@ CONFIG_EWRK3 cards. If this is for you, say Y and read Documentation/networking/ewrk3.txt in the kernel source as well as the Ethernet-HOWTO, available via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. If you want to compile this as a module ( = code which can be inserted in and removed from the running kernel whenever you want), @@ -5649,13 +5707,13 @@ SEEQ8005 support CONFIG_SEEQ8005 This is a driver for the SEEQ 8005 network (Ethernet) card. If this is for you, read the Ethernet-HOWTO, available via FTP (user: - anonymous) from ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + anonymous) from ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. AT1700/1720 support CONFIG_AT1700 If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5668,7 +5726,7 @@ FMV-181/182/183/184 support CONFIG_FMV18X If you have a Fujitsu FMV-181/182/183/184 network (Ethernet) card, say Y and read the Ethernet-HOWTO, available via FTP (user: - anonymous) in ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + anonymous) in ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. If you use an FMV-183 or FMV-184 and it is not working, you may need to disable Plug & Play mode of the card. @@ -5684,7 +5742,7 @@ CONFIG_EEXPRESS_PRO If you have a network (Ethernet) card of this type, say Y. Note however that the EtherExpress PRO/100 Ethernet card has its own separate driver. Please read the Ethernet-HOWTO, available via FTP - (user: anonymous) in ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + (user: anonymous) in ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5696,7 +5754,7 @@ EtherExpress support CONFIG_EEXPRESS If you have an EtherExpress16 network (Ethernet) card, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. Note that the Intel + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Note that the Intel EtherExpress16 card used to be regarded as a very poor choice because the driver was very unreliable. We now have a new driver that should do better. @@ -5711,7 +5769,7 @@ HP PCLAN+ (27247B and 27252A) support CONFIG_HPLAN_PLUS If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5723,7 +5781,7 @@ HP PCLAN (27245 and other 27xxx series) support CONFIG_HPLAN If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5735,7 +5793,7 @@ HP 10/100VG PCLAN (ISA, EISA, PCI) support CONFIG_HP100 If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. If you want to compile this as a module ( = code which can be inserted in and removed from the running kernel whenever you want), @@ -5747,7 +5805,7 @@ NE2000/NE1000 support CONFIG_NE2000 If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. Many Ethernet cards + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Many Ethernet cards without a specific driver are compatible with NE2000. If you have a PCI NE2000 card however, say N here and Y to "PCI @@ -5766,13 +5824,13 @@ SK_G16 support CONFIG_SK_G16 If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. NE/2 (ne2000 MCA version) support CONFIG_NE2_MCA If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5785,7 +5843,7 @@ CONFIG_NET_EISA This is another class of network cards which attach directly to the bus. If you have one of those, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Note that the answer to this question doesn't directly affect the kernel: saying N will just cause this configure script to skip all @@ -5797,7 +5855,7 @@ AMD PCnet32 (VLB and PCI) support CONFIG_PCNET32 If you have a PCnet32 or PCnetPCI based network (Ethernet) card, answer Y here and read the Ethernet-HOWTO, available via FTP (user: - anonymous) in ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + anonymous) in ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5809,7 +5867,7 @@ Ansel Communications EISA 3200 support CONFIG_AC3200 If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5821,7 +5879,7 @@ Mylex EISA LNE390A/LNE390B support CONFIG_LNE390 If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5833,7 +5891,7 @@ Novell/Eagle/Microdyne NE3210 EISA support CONFIG_NE3210 If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. Note that this driver + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Note that this driver will NOT WORK for NE3200 cards as they are completely different. This driver is also available as a module ( = code which can be @@ -5846,7 +5904,7 @@ Apricot Xen-II on board Ethernet CONFIG_APRICOT If you have a network (Ethernet) controller of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. If you want to compile this as a module ( = code which can be inserted in and removed from the running kernel whenever you want), @@ -5860,7 +5918,7 @@ CONFIG_DE4X5 These include the DE425, DE434, DE435, DE450 and DE500 models. If you have a network card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. More specific + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. More specific information is contained in Documentation/networking/de4x5.txt. This driver is also available as a module ( = code which can be @@ -5878,7 +5936,7 @@ CONFIG_DEC_ELCP (smc9332dst), you can also try the driver for "Generic DECchip" cards, above. However, most people with a network card of this type will say Y here.) Do read the Ethernet-HOWTO, available via FTP - (user: anonymous) in ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + (user: anonymous) in ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. More specific information is contained in Documentation/networking/tulip.txt. @@ -5894,7 +5952,7 @@ CONFIG_DGRS PCI/EISA Ethernet switch cards. These include the SE-4 and the SE-6 models. If you have a network card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. More specific + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. More specific information is contained in Documentation/networking/dgrs.txt. This driver is also available as a module ( = code which can be @@ -5907,7 +5965,7 @@ EtherExpress PRO/100 support CONFIG_EEXPRESS_PRO100 If you have an Intel EtherExpress PRO/100 PCI network (Ethernet) card, say Y and read the Ethernet-HOWTO, available via FTP (user: - anonymous) in ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + anonymous) in ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5919,7 +5977,7 @@ ICL EtherTeam 16i/32 support CONFIG_ETH16I If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5932,7 +5990,7 @@ CONFIG_TLAN If you have a PCI Ethernet network card based on the ThunderLAN chip which is supported by this driver, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Devices currently supported by this driver are Compaq Netelligent, Compaq NetFlex and Olicom cards. Please read the file @@ -5961,7 +6019,7 @@ Racal-Interlan EISA ES3210 support CONFIG_ES3210 If you have a network (Ethernet) card of this type, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5974,7 +6032,7 @@ CONFIG_EPIC100 If you have an SMC EtherPower II 9432 PCI Ethernet network card which is based on the SMC83c170, say Y and read the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5993,14 +6051,14 @@ CONFIG_ZNET (Ethernet) card, and this is the Linux driver for it. Note that the IBM Thinkpad 300 is compatible with the Z-Note and is also supported by this driver. Read the Ethernet-HOWTO, available via FTP (user: - anonymous) in ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + anonymous) in ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Pocket and portable adapters CONFIG_NET_POCKET Cute little network (Ethernet) devices which attach to the parallel port ("pocket adapters"), commonly used with laptops. If you have one of those, say Y and read the Ethernet-HOWTO, available via FTP - (user: anonymous) from ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + (user: anonymous) from ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. If you want to plug a network card into the PCMCIA slot of your laptop instead (PCMCIA is the standard for credit card size @@ -6023,7 +6081,7 @@ CONFIG_ATP This is a network (Ethernet) device which attaches to your parallel port. Read drivers/net/atp.c as well as the Ethernet-HOWTO, available via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO if you want to use this. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO if you want to use this. If you intend to use this driver, you should have said N to the Parallel Printer support, because the two drivers don't like each other. @@ -6033,7 +6091,7 @@ CONFIG_DE600 This is a network (Ethernet) device which attaches to your parallel port. Read Documentation/networking/DLINK.txt as well as the Ethernet-HOWTO, available via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO if you want to use this. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO if you want to use this. It is possible to have several devices share a single parallel port and it is safe to compile the corresponding drivers into the kernel. @@ -6047,7 +6105,7 @@ CONFIG_DE620 This is a network (Ethernet) device which attaches to your parallel port. Read Documentation/networking/DLINK.txt as well as the Ethernet-HOWTO, available via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO if you want to use this. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO if you want to use this. It is possible to have several devices share a single parallel port and it is safe to compile the corresponding drivers into the kernel. @@ -6065,7 +6123,7 @@ CONFIG_TR Ring card under Linux, say Y here and to the driver for your particular card below and read the Token-Ring mini-HOWTO, available via FTP (user:anonymous) from - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. Most people can say N + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Most people can say N here. IBM Tropic chipset based adapter support @@ -6073,7 +6131,7 @@ CONFIG_IBMTR This is support for all IBM Token Ring cards that don't use DMA. If you have such a beast, say Y and read the Token-Ring mini-HOWTO, available via FTP (user:anonymous) from - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Warning: this driver will almost definitely fail if more than one active Token Ring card is present. @@ -6091,7 +6149,7 @@ CONFIG_SKTR If you have such an adapter and would like to use it, say Y or M and read the Token-Ring mini-HOWTO, available via FTP (user: anonymous) - from ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + from ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Also read the file linux/Documentation/networking/sktr.txt or check the Linux-SNA WWW site for the latest information at @@ -6181,7 +6239,7 @@ CONFIG_ARM_ETHERH should say Y to this option if you wish to use it with Linux. EBSA-110 Ethernet interface -CONFIG_AM79C961A +CONFIG_ARM_AM79C961A If you wish to compile a kernel for the EBSA-110, then you should always answer Y to this. @@ -6189,7 +6247,7 @@ Support CDROM drives that are not SCSI or IDE/ATAPI CONFIG_CD_NO_IDESCSI If you have a CDROM drive that is neither SCSI nor IDE/ATAPI, say Y here, otherwise N. Read the CDROM-HOWTO, available via FTP (user: - anonymous) from ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + anonymous) from ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Note that the answer to this question doesn't directly affect the kernel: saying N will just cause this configure script to skip all @@ -6446,7 +6504,7 @@ CONFIG_QUOTA ext2 filesystem. You need additional software in order to use quota support; for details, read the Quota mini-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO/mini. Probably the quota + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO/mini. Probably the quota support is only useful for multi user systems. If unsure, say N. Minix fs support @@ -6487,7 +6545,7 @@ CONFIG_EXT2_FS by about 41 kB. The Ext2fs-Undeletion mini-HOWTO, available via FTP (user: - anonymous) from ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO/mini, + anonymous) from ftp://metalab.unc.edu/pub/Linux/docs/HOWTO/mini, gives information about how to retrieve deleted files on ext2fs filesystems. @@ -6497,9 +6555,9 @@ CONFIG_EXT2_FS Ext2fs partitions can be read from within DOS using the ext2tool command line tool package (available via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/system/filesystems/ext2) and from + ftp://metalab.unc.edu/pub/Linux/system/filesystems/ext2) and from within Windows NT using the ext2nt command line tool package from - ftp://sunsite.unc.edu/pub/Linux/utils/dos. Explore2fs is a graphical + ftp://metalab.unc.edu/pub/Linux/utils/dos. Explore2fs is a graphical explorer for ext2fs partitions which runs on Windows 95 and Windows NT and includes experimental write support; it is available from http://jnewbigin-pc.it.swin.edu.au/Linux/Explore2fs.htm. @@ -6522,7 +6580,7 @@ CONFIG_ISO9660_FS listen to audio CDs and watch its LEDs, say Y (and read Documentation/filesystems/isofs.txt and the CDROM-HOWTO, available via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO), thereby enlarging your + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO), thereby enlarging your kernel by about 27 kB; otherwise say N. If you want to compile this as a module ( = code which can be @@ -6583,8 +6641,8 @@ CONFIG_MSDOS_FS they are compressed; to access compressed MSDOS partitions under Linux, you can either use the DOS emulator DOSEMU, described in the DOSEMU-HOWTO, available via FTP (user: anonymous) at - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO, or try dmsdosfs in - ftp://sunsite.unc.edu/pub/Linux/system/filesystems/dosfs. If you + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO, or try dmsdosfs in + ftp://metalab.unc.edu/pub/Linux/system/filesystems/dosfs. If you intend to use dosemu with a non-compressed MSDOS partition, say Y here) and MSDOS floppies. This means that file access becomes transparent, i.e. the MSDOS files look and behave just like all @@ -6683,7 +6741,7 @@ CONFIG_NFS_FS programs nfsd and mountd (but does not need to have NFS filesystem support enabled in its kernel). NFS is explained in the Network Administrator's Guide, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/LDP, on its man page: "man + ftp://metalab.unc.edu/pub/Linux/docs/LDP, on its man page: "man nfs", and in the NFS-HOWTO. A superior but less widely used alternative to NFS is provided by @@ -6703,7 +6761,7 @@ CONFIG_NFS_FS cannot compile this driver as a module in this case. There are two packages designed for booting diskless machines over the net: netboot and etherboot, both available via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/system/boot/ethernet/ . + ftp://metalab.unc.edu/pub/Linux/system/boot/ethernet/ . If you don't know what all this is about, say N. @@ -6731,7 +6789,7 @@ CONFIG_NFSD You will need the support software from the linux-nfs package available at ftp://ftp.mathematik.th-darmstadt.de/pub/linux/okir/. Please read the NFS-HOWTO, available via FTP (user: anonymous) from - ftp://sunsite.unc.edu:/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu:/pub/Linux/docs/HOWTO. The NFS server is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -6994,6 +7052,24 @@ CONFIG_DEVPTS_FS whenever you want). If you want to compile it as a module, say M here and read Documentation/modules.txt. +Unixware slices support (EXPERIMENTAL) +CONFIG_UNIXWARE_DISKLABEL + Like some systems, Unixware uses, except DOS-like partition table, + its own slice table inside a partition (VTOC - Virtual Table of + Contents). Its format is incompatible with all other OSes. Saying Y + here allows you to read VTOC and further mount Unixware partitions + read-only from within Linux if you have also said Y to "UFS + filesystem support" or "System V and Coherent filesystem support", + above. + + This is mainly used to carry data from a Unixware box to your + Linux box via a removable medium like magneto-optical, ZIP or + removable IDE drives. Note, however, that a good portable way to + transport files and directories between unixes (and even other + operating systems) is given by the tar program ("man tar" or + preferably "info tar"). If you don't know what all this is about, + say N. + Macintosh partition map support CONFIG_MAC_PARTITION Say Y here if you want your Linux system to be able to read the @@ -7011,13 +7087,13 @@ CONFIG_SMB_FS transport protocol, and not NetBEUI. For details, read Documentation/filesystems/smbfs.txt and the SMB-HOWTO, available via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. Note: if you just want your box to act as an SMB *server* and make files and printing services available to Windows clients (which need to have a TCP/IP stack), you don't need to say Y here; you can use the program samba (available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/system/network/samba) for that. + ftp://metalab.unc.edu/pub/Linux/system/network/samba) for that. General information about how to connect Linux, Windows machines and Macs is on the WWW at http://www.eats.com/linux_mac_win.html (to @@ -7067,7 +7143,7 @@ CONFIG_NCP_FS mount NetWare file server volumes and to access them just like any other Unix directory. For details, please read the file Documentation/filesystems/ncpfs.txt in the kernel source and the - IPX-HOWTO on ftp://sunsite.unc.edu:/pub/Linux/docs/howto. + IPX-HOWTO on ftp://metalab.unc.edu:/pub/Linux/docs/howto. You do not have to say Y here if you want your Linux box to act as a file *server* for Novell NetWare clients. @@ -7489,7 +7565,7 @@ CONFIG_VT_CONSOLE loadlin) about how to pass options to the kernel at boot time. The lilo procedure is also explained in the SCSI-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO.) + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO.) If unsure, say Y. @@ -7553,7 +7629,7 @@ CONFIG_SERIAL_CONSOLE your boot loader (lilo or loadlin) about how to pass options to the kernel at boot time. The lilo procedure is also explained in the SCSI-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO.) + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO.) If you don't have a VGA card installed and you say Y here, the kernel will automatically use the first serial line, /dev/ttyS0, as @@ -7739,7 +7815,7 @@ CONFIG_PRINTER box (as opposed to using a serial printer; if the connector at the printer has 9 or 25 holes ["female"], then it's serial), say Y. Also read the Printing-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. It is possible to share one parallel port among several devices (e.g. printer and ZIP drive) and it is safe to compile the @@ -7754,7 +7830,7 @@ CONFIG_PRINTER of your boot loader (lilo or loadlin) about how to pass options to the kernel at boot time. The lilo procedure is also explained in the SCSI-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO.) The standard base + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO.) The standard base addresses as well as the syntax of the "lp" command line option can be found in drivers/char/lp.c. @@ -7774,7 +7850,7 @@ CONFIG_MOUSE Microsoft mouse (made by Logitech) that plugs into a COM port (rectangular with 9 or 25 pins). These people say N here. If you have something else, read the Busmouse-HOWTO, available via FTP - (user: anonymous) in ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO and + (user: anonymous) in ftp://metalab.unc.edu/pub/Linux/docs/HOWTO and say Y here. If you have a laptop, you either have to check the documentation or @@ -7792,7 +7868,7 @@ CONFIG_BUSMOUSE made by Logitech don't use the Logitech protocol anymore; for those, you don't need this option. You want to read the Busmouse-HOWTO, available via FTP (user: anonymous) in - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. If you want to compile this as a module ( = code which can be inserted in and removed from the running kernel whenever you want), @@ -7812,20 +7888,20 @@ CONFIG_PSMOUSE Although PS/2 mice are not technically bus mice, they are explained in detail in the Busmouse-HOWTO, available via FTP (user: anonymous) - in ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + in ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. When using a PS/2 mouse, you can get problems if you want to use the mouse both on the Linux console and under X. Using the "-R" option of the Linux mouse managing program gpm (available from - ftp://sunsite.unc.edu:/pub/Linux/system/Daemons) solves this - problem, or you can get the "mconv" utility also from sunsite. + ftp://metalab.unc.edu:/pub/Linux/system/Daemons) solves this + problem, or you can get the "mconv" utility also from metalab. C&T 82C710 mouse port support (as on TI Travelmate) CONFIG_82C710_MOUSE This is a certain kind of PS/2 mouse used on the TI Travelmate. If you are unsure, try first to say N here and come back if the mouse doesn't work. Read the Busmouse-HOWTO, available via FTP (user: - anonymous) in ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + anonymous) in ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. PC110 digitizer pad support CONFIG_PC110_PAD @@ -7845,7 +7921,7 @@ CONFIG_MS_BUSMOUSE These animals (also called Inport mice) are connected to an expansion board using a round connector with 9 pins. If this is what you have, say Y and read the Busmouse-HOWTO, available via FTP - (user: anonymous) in ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + (user: anonymous) in ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. If you are unsure, say N and read the HOWTO nevertheless: it will tell you what you have. Also be aware that several vendors talk @@ -7862,7 +7938,7 @@ CONFIG_ATIXL_BUSMOUSE This is a rare type of busmouse that is connected to the back of an ATI video card. Note that most ATI mice are actually Microsoft busmice. Read the Busmouse-HOWTO, available via FTP (user: - anonymous) in ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. + anonymous) in ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. If you want to compile this as a module ( = code which can be inserted in and removed from the running kernel whenever you want), @@ -8204,11 +8280,8 @@ CONFIG_MTRR set the MTRRs for the boot CPU and not the secondary CPUs. This can lead to all sorts of problems. - In general you should compile this into the kernel, rather than as a - loadable module, because the BIOS fix needs to be done early in the - boot sequence. If you compile this as a module, the BIOS fix will be - delayed until when you load the module. You do this at your own - risk. + You can safely say Y even if your machine doesn't have MTRRs, you'll + just add about 3k to your kernel. See Documentation/mtrr.txt for more information. @@ -8234,7 +8307,7 @@ CONFIG_APM Supporting software is available; for more information, read the Battery Powered Linux mini-HOWTO, available via FTP (user: - anonymous) from ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO/mini. + anonymous) from ftp://metalab.unc.edu/pub/Linux/docs/HOWTO/mini. This driver does not spin down disk drives (see the hdparm(8) manpage ("man 8 hdparm") for that), and it doesn't turn off @@ -8328,7 +8401,7 @@ CONFIG_APM_POWER_OFF is halted. You will need software (e.g., a suitable version of the halt(8) command ("man 8 halt")) to cause the computer to power down. Recent versions of the sysvinit package available from - ftp://sunsite.unc.edu/pub/Linux/system/daemons/init/ (user: + ftp://metalab.unc.edu/pub/Linux/system/daemons/init/ (user: anonymous) contain support for this ("halt -p" shuts down Linux and powers off the computer, if executed from runlevel 0). As with the other APM options, this option may not work reliably with some APM @@ -8461,13 +8534,8 @@ CONFIG_RTC 24 hour alarm. It reports status information via the file /proc/rtc and its behaviour is set by various ioctls on /dev/rtc. - People running SMP (multiprocessor) versions of Linux should say Y - here to read and set the RTC clock in a SMP compatible - fashion. (They should also read Documentation/smp and - Documentation/IO-APIC.txt and the SMP-FAQ on the WWW at - http://www.irisa.fr/prive/mentre/smp-faq/ (to browse the WWW, you - need to have access to a machine on the Internet that has a program - like lynx or netscape).) + If you enabled CONFIG_SMP, you should say Y here to read and set the + RTC clock in an SMP compatible fashion. If you think you have a use for such a device (such as periodic data sampling), then say Y here, and read Documentation/rtc.txt for @@ -8491,7 +8559,11 @@ CONFIG_NVRAM and "NVRAM" on Ataris. /dev/nvram may be used to view settings there, or to change them (with some utility). It could also be used to frequently save a few bits of very important data that may not be - lost over power-off and for which writing to disk is too insecure. + lost over power-off and for which writing to disk is too insecure. Note + however that most NVRAM space in a PC belongs to the BIOS and you should + NEVER idly tamper with it. See Ralf Browns interrupt list for a guide to + the use of CMOS bytes by your BIOS. + On Atari machines, /dev/nvram is always configured and does not need to be selected. @@ -8610,7 +8682,7 @@ CONFIG_SOUND about your sound card and its configuration down (I/O port, interrupt and DMA channel), because you will be asked for it. You want to read the Sound-HOWTO, available via FTP (user: anonymous) - from ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO. There is also some + from ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. There is also some information in various README files in drivers/sound, esp. in Readme.cards which you should read first to find out whether your card is supported by Linux, and, if yes, which driver to use. @@ -8645,6 +8717,14 @@ CONFIG_SOUND_SGALAXY cards from Aztech. It supports the Waverider Pro 32 - 3D and the Galaxy Washington 16. +Support for AD1816(A) based cards (EXPERIMENTAL) +CONFIG_SOUND_AD1816 + Say M here if you have a soundcard based on the Analog Devices + AD1816(A) chip. + + NOTE: This driver is still EXPERIMENTAL. + See Documentation/sound/AD1816 for further information. + Yamaha OPL3-SA1 audio controller CONFIG_SOUND_OPL3SA1 Say Y or M if you have a Yamaha OPL3-SA1 sound chip, which is @@ -8852,9 +8932,11 @@ CONFIG_SOUND_CS4232 See Documentation/sound/CS4232 for more information on configuring this card. -Support for Yamaha OPL3-SA[2,3,x] based (PnP) cards +Support for Yamaha OPL3-SA2, SA3, and SAx based PnP cards CONFIG_SOUND_OPL3SA2 - Say Y or M here if you have such a sound card. + Say Y or M if you have a card based on one of these Yamaha + sound chipsets. Read Documentation/sound/OPL3-SA2 for more + information on configuring these cards. Support for Turtle Beach Wave Front (Maui, Tropez) synthesizers CONFIG_SOUND_MAUI @@ -8975,16 +9057,16 @@ CONFIG_LOWLEVEL_SOUND affect the kernel; saying Y will simply cause this configure script to present you with more options. If unsure, say Y. -ACI mixer (miroPCM12) +ACI mixer (miroPCM12/PCM20) CONFIG_ACI_MIXER Audio Command Interface (ACI) driver. ACI is a protocol used to communicate with the microcontroller on some sound cards produced by miro, e.g. the miroSOUND PCM12 and PCM20. The main function of the ACI is to control the mixer and to get a product identification. This Voxware ACI driver currently only supports the ACI functions on - the miroSOUND PCM12 card. On the PCM20, ACI also controls the radio - tuner on this card, however this is not yet supported in this - software. + the miroSOUND PCM12 and PCM20 cards. On the PCM20, ACI also controls + the radio tuner. This is supported in the video4linux radio-miropcm20 + driver. SB32/AWE support CONFIG_AWE32_SYNTH @@ -8992,7 +9074,7 @@ CONFIG_AWE32_SYNTH similar sound card. See drivers/sound/lowlevel/README.awe, Documentation/sound/AWE32 and the Soundblaster-AWE mini-HOWTO, available via FTP (user: anonymous) from - ftp://sunsite.unc.edu/pub/Linux/docs/HOWTO/mini for more info. + ftp://metalab.unc.edu/pub/Linux/docs/HOWTO/mini for more info. Gallant's Audio Excel DSP 16 support (SC-6000 and SC-6600) CONFIG_AEDSP16 @@ -9013,17 +9095,11 @@ CONFIG_AEDSP16 Documentation/sound/AudioExcelDSP16 to get more information about this driver and its configuration. -SC-6600 based audio cards (new Audio Excel DSP 16) -CONFIG_SC6600 - The SC6600 is the new version of DSP mounted on the Audio Excel DSP - 16 cards. Find in the manual the FCC ID of your audio card and - answer Y if you have an SC6600 DSP. - -Audio Excel DSP 16 (MSS emulation) -CONFIG_AEDSP16_MSS - Answer Y if you want your audio card to emulate Microsoft Sound - System. You should then say Y to "Microsoft Sound System support" - and say N to "Audio Excel DSP 16 (SBPro emulation)". +I/O base for Audio Excel DSP 16 +CONFIG_AEDSP16_BASE + This is the base I/O address of the Audio Excel DSP 16 card. It must + be 220 or 240. If you compiled aedsp16.o as a module you can specify + this parameter as 'io=0xNNN'. Audio Excel DSP 16 (SBPro emulation) CONFIG_AEDSP16_SBPRO @@ -9032,6 +9108,68 @@ CONFIG_AEDSP16_SBPRO (SB16/32/64, ESS, Jazz16) support" and N to "Audio Excel DSP 16 (MSS emulation)". +Audio Excel DSP 16 IRQ +CONFIG_AEDSP16_SB_IRQ + This is the IRQ of the Audio Excel DSP 16 card. It must be 5, 7, 9, + 10 or 11. If you compiled aedsp16.o as a module you can specify + this parameter as 'irq=NN'. + +Audio Excel DSP 16 DMA +CONFIG_AEDSP16_SB_DMA + This is the IRQ of the Audio Excel DSP 16 card. It must be 0, 1 or 3. + If you compiled aedsp16.o as a module you can specify this parameter + as 'dma=NN'. + +Audio Excel DSP 16 (MSS emulation) +CONFIG_AEDSP16_MSS + Answer Y if you want your audio card to emulate Microsoft Sound + System. You should then say Y to "Microsoft Sound System support" + and say N to "Audio Excel DSP 16 (SBPro emulation)". + +Audio Excel DSP 16 IRQ +CONFIG_AEDSP16_MSS_IRQ + This is the IRQ of the Audio Excel DSP 16 card. It must be 5, 7, 9, + 10 or 11. If you compiled aedsp16.o as a module you can specify + this parameter as 'irq=NN'. + +Audio Excel DSP 16 DMA +CONFIG_AEDSP16_MSS_DMA + This is the IRQ of the Audio Excel DSP 16 card. It must be 0, 1 or 3. + If you compiled aedsp16.o as a module you can specify this parameter + as 'dma=NN'. + +SC-6600 based audio cards (new Audio Excel DSP 16) +CONFIG_SC6600 + The SC6600 is the new version of DSP mounted on the Audio Excel DSP + 16 cards. Find in the manual the FCC ID of your audio card and + answer Y if you have an SC6600 DSP. + +SC-6600 Joystick Interface +CONFIG_SC6600_JOY + This option activate the Joystick interface of Audio Excel DSP 16 card. + +SC-6600 CDROM Interface +CONFIG_SC6600_CDROM + This option activate the CDROM interface of Audio Excel DSP 16 card. + Required parameter can be: 0 for Sony, 1 for Panasonic, 2 for IDE, 4 for + no CDROM present. + +Audio Excel DSP 16 (MPU401 emulation) +CONFIG_AEDSP16_MPU401 + Answer Y if you want your audio card to emulate the MPU-401 midi + interface. You should then say Y to "MPU-401 support". + You have to hote that the I/O base for MPU-401 support of aedsp16 is + the same you have selected for "MPU-401 support". If you are using + this driver as a module you have to specify the MPU I/O base address + with the parameter 'mpu_base=0xNNN'. + +MPU401 IRQ for Audio Excel DSP 16 +CONFIG_AEDSP16_MPU_IRQ + This is the IRQ of the MPU-401 emulation of Audio Excel DSP 16 card. + It must be 5, 7, 9, 10 or 0 (to disable MPU-401 interface). If you + compiled aedsp16.o as a module you can specify this parameter as + 'mpu_irq=NN'. + Ensoniq ES1370 based PCI sound cards CONFIG_SOUND_ES1370 Say Y or M if you have a PCI sound card utilizing the Ensoniq @@ -9057,6 +9195,15 @@ CONFIG_SOUND_ES1371 models are either ES1370 or ES1371 based. This driver differs slightly from OSS/Free, so PLEASE READ Documentation/sound/es1371. +Gameport I/O-range selection +CONFIG_SOUND_ES1371_GAMEPORT + Select the I/O-range of the gameport on a ES1371 based soundcard. + The card uses 8 ioports and the gameport is available at all eight + ioports. Legal hexadecimal values are 200, 208, 210 and 218. + The joystick driver will by default use 0x201. + Leave the default 200 unless you have a joystick not attached + to your soundcard. + S3 SonicVibes based PCI sound cards CONFIG_SOUND_SONICVIBES Say Y or M if you have a PCI sound card utilizing the S3 @@ -9489,6 +9636,13 @@ CONFIG_MAC Say N unless you're willing to code the remaining necessary support. ;) +HP9000/300 support +CONFIG_HP300 + This option enables support for the HP9000/300 series of workstations. + Support for these machines is still very experimental. If you plan to + try to use the kernel on such a machine say Y here. Everybody else + says N. + # CONFIG_APOLLO, etc. coming soon (?) 68020 support @@ -9932,6 +10086,21 @@ CONFIG_DMASOUND want). If you want to compile it as a module, say M here and read Documentation/modules.txt. +HP DCA serial support +CONFIG_HPDCA + If you want to use the internal "DCA" serial ports on an HP300 + machine, say Y here. + +HP on-board LANCE support +CONFIG_HPLANCE + If you want to use the builtin "LANCE" Ethernet controller on an HP300 + machine, say Y here. + +DIO bus support +CONFIG_DIO + Say Y here to enable support for the "DIO" expansion bus used in HP300 + machines. If you are using such a system you almost certainly want this. + MSDOS partition support CONFIG_MSDOS_PARTITION This option enables support for using hard disks that were @@ -10139,8 +10308,9 @@ CONFIG_RADIO_ZOLTRIX_PORT Miro PCM20 Radio CONFIG_RADIO_MIROPCM20 - Choose Y here if you have one of these FM radio cards, and then fill - in the port address below. + Choose Y here if you have this FM radio card. You also need the + PCM12/PCM20 ACI mixer in additional low level sound drivers for this + to work. In order to control your radio card, you will need to use programs that are compatible with the Video for Linux API. Information on @@ -10154,6 +10324,28 @@ CONFIG_RADIO_MIROPCM20 say M here and read Documentation/modules.txt. The module will be called radio-miropcm20.o +GemTek Radio Card +CONFIG_RADIO_GEMTEK + Choose Y here if you have this FM radio card, and then fill in the + port address below. + + In order to control your radio card, you will need to use programs + that are compatible with the Video for Linux API. Information on + this API and pointers to "v4l" programs may be found on the WWW at + http://roadrunner.swansea.uk.linux.org/v4l.shtml; to browse the WWW, + you need to have access to a machine on the Internet that has a + program like lynx or netscape. + + If you want to compile this driver as a module ( = code which can be + inserted in and removed from the running kernel whenever you want), + say M here and read Documentation/modules.txt. The module will be + called radio-gemtek.o. + +GemTek i/o port +CONFIG_RADIO_GEMTEK_PORT + Enter either 0x20c, 0x30c, 0x24c or 0x34c here. The card default is + 0x34c, if you haven't changed the jumper setting on the card. + BT848 Video For Linux CONFIG_VIDEO_BT848 Support for BT848 based frame grabber/overlay boards. This includes @@ -10216,6 +10408,19 @@ CONFIG_ARCH_ARC to set this option to, please consult any information supplied with your system. +Include support for CATS boards +CONFIG_CATS + Say Y here if you wish to include support for the extra hardware found + in Chalice CATS machines. The resulting kernel will still run on an + EBSA-285 but will be slightly larger. If in doubt say N. + +Debug kernel errors +CONFIG_DEBUG_ERRORS + This option controls verbose debugging information which can be printed + when the kernel detects an internal error. Verbose debugging information + is useful when tracking down kernel problems, but it will be meaning less + for non-kernel hackers. It's safe for everyone to say Y. + Build Tools Selection CONFIG_BINUTILS_NEW Say Y here if and only if you're using GCC 2.8.1/EGCS with a @@ -10228,6 +10433,261 @@ CONFIG_FRAME_POINTER it will give useful debugging/error results. If you don't debug the kernel, you can say N. +Initial kernel command line +CONFIG_CMDLINE + On some architectures (EBSA285, EBSA110 and Corel Netwinder), there is + currently no way for the boot loader to pass arguments to the kernel. + For these architectures, you should supply some command-line options + at build time by entering them here. As a minimum, you should specify + the memory size and the root device (eg, mem=64M root=/dev/nfs) + +IrDA Protocols +CONFIG_IRDA + Say Y here if you want to build support for the IrDA (TM) + protocols. The Infrared Data Associations (tm) specifies standards + for wireless infrared communication and is supported by most laptops + and PDA's If you want to compile it as a module, say M here and read + Documentation/modules.txt. + + To use Linux support for the IrDA (tm) protocols, you will also need + some user-space utilities like the irmanager and probably irattach + as well. For more information, visit + http://www.cs.uit.no/~dagb/irda/ + +IrDA Cache last LSAP +CONFIG_IRDA_CACHE_LAST_LSAP + Say Y here if you want IrLMP to cache the last LSAP used. This makes + sense since most frames will be sent/received on the same connection. + Enabling this option will save a hash-lookup per frame. + + If unsure, say Y. + +IrDA Fast RR's +CONFIG_IRDA_FAST_RR + Say Y here is you want IrLAP to send fast RR (Receive Ready) frames + when acting as a primary station. This will make IrLAP send out a RR + frame immediately when receiving a frame if its own transmit queue is + currently empty. This will give a lot of speed improvement when + receiving much data since the secondary station will not have to + wait the max. turn around time before it is allowed to transmit the + next time. If the transmit queue of the secondary is also empty the + primary will back off waiting longer for sending out the RR frame + until the timeout reaches the normal value. Enabling this option + will make the IR-diode burn more power and thus reduce your battery + life. + + If unsure, say N. + +IrDA Recycle RR's +CONFIG_IRDA_RECYCLE_RR + In the normal life of the IrLAP protocol, it sends a lot of small RR + (Receive Ready) frames over the link (at least when it has nothing + else to do). Saying Y to this option will make IrLAP recycle these + frames thus avoiding many alloc_skb's and kfree_skb's. To do this it + will only buffer one of these frame which is enough for the normal + case. + + If unsure, say Y. + +IrLAP Compression support +CONFIG_IRDA_COMPRESSION + Compression is _not_ part of the IrDA(tm) protocol specification, + but its working great! Linux is the first to try out compresson + support at the IrLAP layer. This means that you will only benefit + from compression if you are running a Linux <-> Linux configuration + +IrLAP Deflate Compression Protocol +CONFIG_IRDA_DEFLATE + Say Y here if you want to build support for the Deflate compression + protocol. If you want to compile it as a module, say M here and read + Documentation/modules.txt. The deflate compression (GZIP) is exactly + the same as used by the PPP protocol. Enabling this option will + build a module called irda_deflate.o + +IrLAN Protocol +CONFIG_IRLAN + Say Y here if you want to build support for the IrLAN protocol. If + you want to compile it as a module, say M here and read + Documentation/modules.txt. IrLAN emulates an Ethernet and makes it + possible to put up an wireless LAN using infrared beams. + +IrLAN Client Protocol +CONFIG_IRLAN_CLIENT + Say Y here if you want to build support for the IrLAN client + protocol. If you want to compile it as a module, say M here and read + Documentation/modules.txt. The IrLAN client protocol can be used to + talk with infrared access points like the HP NetbeamIR, or the ESI + JetEye NET. You can also connect to another Linux machine running + the IrLAN server protocol for ac-hoc networking! + +IrLAN Server Protocol +CONFIG_IRLAN_SERVER + Say Y here if you want to build support for infrared LAN access. If + you want to compile it as a module, say M here and read + Documentation/modules.txt. The IrLAN server protocol makes it + possible to set up a wireless LAN with a machine running the IrLAN + client protocol. Notice that the IrLAN server protocol currently + only emulates an access point and does not implement the ad-hoc + specification of IrLAN, but this will not be noticeable for the + user. + +IrOBEX Protocol +CONFIG_IROBEX + Say Y here if you want to build support for the IrOBEX protocol. If + you want to compile it as a module, say M here and read + Documentation/modules.txt. The module does not actually implement + the IrOBEX protocol since that protocol lives in userspace, but it + contains the necessary functions to interface the user-space stuff + with the kernel. So you will need to have the user-space library and + programs that can use this library installed as well to be able to + use the IrOBEX protocol. This module will hopefully be replaced by + IrDA sockets in the future. + +IrCOMM Protocol +CONFIG_IRCOMM + Say Y here if you want to build support for the IrCOMM protocol. If + you want to compile it as a module, say M here and read + Documentation/modules.txt. IrCOMM implements serial port emulation, + and makes it possible to use all existing applications that + understands TTY's with an infrared link. Thus you should be able to + use application like PPP, minicom and others. Enabling this option + will create two modules called ircomm and ircomm_tty. For more + information go to http://www.pluto.dti.ne.jp/~thiguchi/irda/ + +IrTTY IrDA Device Driver +CONFIG_IRTTY_SIR + Say Y here if you want to build support for the IrTTY line + discipline. If you want to compile it as a module, say M here and + read Documentation/modules.txt. IrTTY makes it possible to use + Linux's own serial driver for all IrDA ports that are 16550 + compatible. Most IrDA chips are 16550 compatible so you should + probably say Y to this option. Using IrTTY will however limit the + speed of the connection to 115200 bps (IrDA SIR mode) + + If unsure, say Y. + +Winbond W83977AF IrDA Device Driver +CONFIG_WINBOND_FIR + Say Y here if you want to build IrDA support for the Winbond W83977AF + super-io chipset. If you want to compile it as a module, say M here + and read Documentation/modules.txt. This driver should be used for + the IrDA chipset in the Corel NetWinder. The driver supports SIR, + MIR and FIR (4Mbps) speeds. + +NSC PC87108 IrDA Device Driver +CONFIG_NSC_FIR + Say Y here if you want to build support for the NSC PC87108 IrDA + chipset. If you want to compile it as a module, say M here and + read Documentation/modules.txt. This drivers currently only supports + the ACTiSYS IR2000B ISA card and supports SIR, MIR and FIR (4Mbps) + speeds. + +ESI JetEye PC Dongle +CONFIG_ESI_DONGLE + Say Y here if you want to build support for the Extended Systems + JetEye PC dongle. If you want to compile it as a module, say M here + and read Documentation/modules.txt. The ESI dongle attaches to the + normal 9-pin serial port connector, and can currently only be used + by IrTTY. To activate support for ESI dongles you will have to + insert "irattach -d esi" in the /etc/irda/drivers script. + +ACTiSYS IR-220L and IR220L+ dongle +CONFIG_ACTISYS_DONGLE + Say Y here if you want to build support for the ACTiSYS + IR-220L and IR220L+ dongles. If you want to compile it as a module, + say M here and read Documentation/modules.txt. The ACTiSYS dongles + attaches to the normal 9-pin serial port connector, and can + currently only be used by IrTTY. To activate support for ACTiSYS + dongles you will have to insert "irattach -d actisys" or + "irattach -d actisys_plus" in the/etc/irda/drivers script. + +Tekram IrMate 210B dongle +CONFIG_TEKRAM_DONGLE + Say Y here if you want to build support for the Tekram IrMate 210B + dongle. If you want to compile it as a module, say M here + and read Documentation/modules.txt. The Tekram dongle attaches to + the normal 9-pin serial port connector, and can currently only be + used by IrTTY. To activate support for Tekram dongles you will have + to insert "irattach -d tekram" in the /etc/irda/drivers script. + +VME (Motorola and BVM) support +CONFIG_VME + Say Y here if you want to build a kernel for a 680x0 based VME + board. Boards currently supported include Motorola boards MVME162, + MVME166, MVME167, MVME172, and MVME177. BVME4000 and BVME6000 + boards from BVM Ltd are also supported. + +MVME162, 166 and 167 support +CONFIG_MVME16x + Say Y to include support for Motorola VME boards. This will build a + kernel which can run on MVME162, MVME166, MVME167, MVME172, and + MVME177 boards. If you select this option you will have to select + the appropriate drivers for SCSI, Ethernet and serial ports later + on. + +BVME4000 and BVME6000 support +CONFIG_BVME6000 + Say Y to include support for VME boards from BVM Ltd. This will + build a kernel which can run on BVME4000 and BVME6000 boards. If + you select this option you will have to select the appropriate + drivers for SCSI, Ethernet and serial ports later on. + +Use write-through caching for 68060 supervisor accesses +CONFIG_060_WRITETHROUGH + The 68060 generally uses copyback caching of recently accessed data. + Copyback caching means that memory writes will be held in an on-chip + cache and only written back to memory some time later. Saying Y + here will force supervisor (kernel) accesses to use writethrough + caching. Writethrough caching means that data is written to memory + straight away, so that cache and memory data always agree. + Writethrough caching is less efficient, but is needed for some + drivers on 68060 based systems where the 68060 bus snooping signal + is hardwired on. The 53c710 SCSI driver is known to suffer from + this problem. + +NCR53C710 SCSI driver for MVME16x +CONFIG_MVME16x_SCSI + The Motorola MVME162, 166, 167, 172 and 177 boards use the NCR53C710 + SCSI controller chip. Almost everyone using one of these boards + will want to say Y to this question. + +NCR53C710 SCSI driver for BVME6000 +CONFIG_BVME6000_SCSI + The BVME4000 and BVME6000 boards from BVM Ltd use the NCR53C710 + SCSI controller chip. Almost everyone using one of these boards + will want to say Y to this question. + +MVME16x Ethernet support +CONFIG_MVME16x_NET + This is the driver for the Ethernet interface on the Motorola + MVME162, 166, 167, 172 and 177 boards. Say Y here to include the + driver for this chip in your kernel. If you want to compile it as + a module, say M here and read Documentation/modules.txt. + +BVME6000 Ethernet support +CONFIG_BVME6000_NET + This is the driver for the Ethernet interface on BVME4000 and + BVME6000 VME boards. Say Y here to include the driver for this chip + in your kernel. If you want to compile it as a module, say M here + and read Documentation/modules.txt. + +CD2401 support for MVME166/7 serial ports +CONFIG_SERIAL167 + This is the driver for the serial ports on the Motorola MVME166, + 167, and 172 boards. Everyone using one of these boards should say + Y here. + +SCC support for MVME162 serial ports +CONFIG_MVME162_SCC + This is the driver for the serial ports on the Motorola MVME162 and + 172 boards. Everyone using one of these boards should say Y here. + +SCC support for BVME6000 serial ports +CONFIG_BVME6000_SCC + This is the driver for the serial ports on the BVME4000 and BVME6000 + boards from BVM Ltd. Everyone using one of these boards should say + Y here. + # # A couple of things I keep forgetting: # capitalize: AppleTalk, Ethernet, DMA, FTP, Internet, Intel, IRQ, @@ -10237,7 +10697,7 @@ CONFIG_FRAME_POINTER # # This is used by Emacs' spell checker ispell.el: # -# LocalWords: CONFIG coprocessor DX Pentium SX lilo loadlin HOWTO ftp sunsite +# LocalWords: CONFIG coprocessor DX Pentium SX lilo loadlin HOWTO ftp metalab # LocalWords: unc edu docs emu README kB BLK DEV FD Thinkpad fd MFM RLL IDE gz # LocalWords: cdrom diskless netboot nfs xzvf ATAPI MB ide pavia rubini pl pd # LocalWords: HD CDROMs IDECD NEC MITSUMI filesystem XT XD PCI BIOS cezar ATEN diff --git a/MAINTAINERS b/MAINTAINERS index bafcd31654ae..4f0c66b264a8 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -94,9 +94,12 @@ L: linux-net@vger.rutgers.edu S: Maintained W: http://rsphy1.anu.edu.au/~gpg109/ne2000.html -AEDSP16 DRIVER -P: Riccardo Facchetti -M: fizban@tin.it +AD1816 SOUND DRIVER +P: Thorsten Knabe +M: Thorsten Knabe +M: Thorsten Knabe +W: http://www.student.informatik.tu-darmstadt.de/~tek/projects/linux.html +W: http://www.tu-darmstadt.de/~tek01/projects/linux.html S: Maintained ADVANSYS SCSI DRIVER @@ -105,6 +108,11 @@ M: Bob Frey W: http://www.advansys.com/linux S: Maintained +AEDSP16 DRIVER +P: Riccardo Facchetti +M: fizban@tin.it +S: Maintained + AHA152X SCSI DRIVER P: Juergen E. Fischer M: Juergen Fischer @@ -167,14 +175,26 @@ P: Axel Boldt M: boldt@math.ucsb.edu S: Maintained +COSA/SRP SYNC SERIAL DRIVER +P: Jan "Yenya" Kasprzak +M: kas@fi.muni.cz +W: http://www.fi.muni.cz/~kas/cosa/ +S: Maintained + +COSA/SRP SYNC SERIAL DRIVER +P: Jan "Yenya" Kasprzak +M: kas@fi.muni.cz +W: http://www.fi.muni.cz/~kas/cosa/ +S: Maintained + CREDITS FILE P: John A. Martin M: jam@acm.org S: Maintained CYCLADES ASYNC MUX DRIVER -P: Marcio Saito -M: Marcio Saito +P: Ivan Passos +M: Ivan Passos W: http://www.cyclades.com/ S: Supported @@ -188,13 +208,15 @@ S: Maintained DC390/AM53C974 SCSI driver P: Kurt Garloff -M: K.Garloff@ping.de -W: ftp://student.physik.uni-dortmund.de/pub/linux/kernel/dc390/ +M: kurt@garloff.de +W: http://www.garloff.de/kurt/linux/dc390/ S: Maintained DECnet NETWORK LAYER P: Steven Whitehouse M: SteveW@ACM.org +W: http://www.sucs.swan.ac.uk/~rohan/ +W: http://www-sigproc.eng.cam.ac.uk/~sjw44/ L: netdev@roxanne.nuclecu.unam.mx S: Maintained @@ -350,7 +372,7 @@ S: Maintained IP FIREWALL P: Paul Russell M: Paul.Russell@rustcorp.com.au -W: http://www.adelaide.net.au/~rustcorp/ipfwchains/ipfwchains.html +W: http://www.rustcorp.com/linux/ipchains S: Supported IPX/SPX NETWORK LAYER @@ -359,6 +381,13 @@ M: Jay Schulist L: linux-net@vger.rutgers.edu S: Maintained +IRDA SUBSYSTEM +P: Dag Brattli +M: Dag Brattli +L: linux-irda@list.uit.no +W: http://www.cs.uit.no/~dagb/irda/ +S: Maintained + ISDN SUBSYSTEM P: Fritz Elfert M: fritz@wuemaus.franken.de @@ -448,6 +477,13 @@ M: rubini@ipvvis.unipv.it L: linux-kernel@vger.rutgers.edu S: Maintained +MTRR AND SIMILAR SUPPORT [i386] +P: Richard Gooch +M: rgooch@atnf.csiro.au +L: linux-kernel@vger.rutgers.edu +W: http://www.atnf.csiro.au/~rgooch/linux/kernel-patches.html +S: Maintained + MULTISOUND SOUND DRIVER P: Andrew Veliath M: andrewtv@usa.net @@ -457,7 +493,7 @@ NCP FILESYSTEM P: Petr Vandrovec M: vandrove@vc.cvut.cz P: Volker Lendecke -M: lendecke@Math.Uni-Goettingen.de +M: vl@kki.org L: linware@sh.cvut.cz S: Maintained @@ -502,6 +538,12 @@ M: emoenke@gwdg.de L: linux-kernel@vger.rutgers.edu S: Maintained +OPL3-SA2, SA3, and SAx DRIVER +P: Scott Murray +M: scottm@interlog.com +L: linux-sound@vger.rutgers.edu +S: Maintained + PARALLEL PORT SUPPORT P: Phil Blundell M: Philip.Blundell@pobox.com @@ -596,7 +638,7 @@ S: Maintained SMB FILESYSTEM P: Volker Lendecke -M: lendecke@Math.Uni-Goettingen.de +M: vl@kki.org L: samba@listproc.anu.edu.au S: Maintained diff --git a/arch/alpha/defconfig b/arch/alpha/defconfig index 96666ced7751..cfd366eb5917 100644 --- a/arch/alpha/defconfig +++ b/arch/alpha/defconfig @@ -42,6 +42,7 @@ CONFIG_ALPHA_GENERIC=y # CONFIG_ALPHA_SX164 is not set # CONFIG_ALPHA_SABLE is not set # CONFIG_ALPHA_TAKARA is not set +# CONFIG_SMP is not set CONFIG_PCI=y CONFIG_ALPHA_NEED_ROUNDING_EMULATION=y # CONFIG_PCI_QUIRKS is not set diff --git a/arch/alpha/kernel/irq.c b/arch/alpha/kernel/irq.c index 4323b569596b..467a861d1478 100644 --- a/arch/alpha/kernel/irq.c +++ b/arch/alpha/kernel/irq.c @@ -824,7 +824,7 @@ probe_irq_on(void) * Wait about 100ms for spurious interrupts to mask themselves * out again... */ - for (delay = jiffies + HZ/10; delay > jiffies; ) + for (delay = jiffies + HZ/10; time_before(jiffies, delay); ) barrier(); /* Now filter out any obviously spurious interrupts. */ diff --git a/arch/arm/kernel/ecard.c b/arch/arm/kernel/ecard.c index a2c702501a6c..fc092a495eff 100644 --- a/arch/arm/kernel/ecard.c +++ b/arch/arm/kernel/ecard.c @@ -215,7 +215,7 @@ static void ecard_irq_noexpmask(int intr_no, void *dev_id, struct pt_regs *regs) } else lockup = 0; - if (!last || last + 500 < jiffies) { + if (!last || time_after(jiffies, last + 500)) { last = jiffies; printk(KERN_ERR "\nUnrecognised interrupt from backplane\n"); } diff --git a/arch/arm/kernel/hw-ebsa285.c b/arch/arm/kernel/hw-ebsa285.c index d88ca6ce99a3..e3385696b076 100644 --- a/arch/arm/kernel/hw-ebsa285.c +++ b/arch/arm/kernel/hw-ebsa285.c @@ -123,7 +123,7 @@ static void irq_pci_err(int irq, void *dev_id, struct pt_regs *regs) err = "system"; break; } - if (next_warn[idx] <= jiffies) { + if (time_after_eq(jiffies, next_warn[idx])) { next_warn[idx] = jiffies + 3 * HZ / 100; printk(KERN_ERR "PCI %s error detected\n", err); } diff --git a/arch/arm/kernel/irq.c b/arch/arm/kernel/irq.c index 4c2063ae5e62..332e8940d707 100644 --- a/arch/arm/kernel/irq.c +++ b/arch/arm/kernel/irq.c @@ -356,7 +356,7 @@ unsigned long probe_irq_on(void) /* * wait for spurious interrupts to mask themselves out again */ - for (delay = jiffies + HZ/10; delay > jiffies; ) + for (delay = jiffies + HZ/10; time_before(jiffies, delay); ) /* min 100ms delay */; /* diff --git a/arch/i386/config.in b/arch/i386/config.in index 9a7bd3f5bd17..f64a0da2fc24 100644 --- a/arch/i386/config.in +++ b/arch/i386/config.in @@ -17,9 +17,7 @@ choice 'Processor family' \ Pentium/K5/5x86/6x86 CONFIG_M586 \ PPro/K6/6x86MX CONFIG_M686" Pentium bool 'Math emulation' CONFIG_MATH_EMULATION -if [ "$CONFIG_EXPERIMENTAL" = "y" ]; then - bool 'MTRR (Memory Type Range Register) support' CONFIG_MTRR -fi +bool 'MTRR (Memory Type Range Register) support' CONFIG_MTRR bool 'Symmetric multi-processing support' CONFIG_SMP endmenu @@ -38,10 +36,16 @@ comment 'General setup' bool 'Networking support' CONFIG_NET bool 'PCI support' CONFIG_PCI if [ "$CONFIG_PCI" = "y" ]; then - bool ' PCI BIOS support' CONFIG_PCI_BIOS - bool ' PCI direct access support' CONFIG_PCI_DIRECT - if [ "$CONFIG_PCI_BIOS" = "n" -a "$CONFIG_PCI_DIRECT" = "n" ]; then - define_bool CONFIG_PCI_BIOS "y" + unset CONFIG_PCI_BIOS CONFIG_PCI_DIRECT + choice 'PCI access mode' \ + "BIOS CONFIG_PCI_GOBIOS \ + Direct CONFIG_PCI_GODIRECT \ + Any CONFIG_PCI_GOANY" Any + if [ -n "$CONFIG_PCI_GOBIOS" -o -n "$CONFIG_PCI_GOANY" ]; then + define_bool CONFIG_PCI_BIOS y + fi + if [ -n "$CONFIG_PCI_GODIRECT" -o -n "$CONFIG_PCI_GOANY" ]; then + define_bool CONFIG_PCI_DIRECT y fi bool ' PCI quirks' CONFIG_PCI_QUIRKS if [ "$CONFIG_PCI_QUIRKS" = "y" -a "$CONFIG_EXPERIMENTAL" = "y" ]; then diff --git a/arch/i386/defconfig b/arch/i386/defconfig index 3f6ebecd1550..4187224cda50 100644 --- a/arch/i386/defconfig +++ b/arch/i386/defconfig @@ -15,6 +15,7 @@ CONFIG_M586=y # CONFIG_M686 is not set # CONFIG_MATH_EMULATION is not set +# CONFIG_MTRR is not set CONFIG_SMP=y # @@ -29,6 +30,9 @@ CONFIG_MODULES=y # CONFIG_NET=y CONFIG_PCI=y +# CONFIG_PCI_GOBIOS is not set +# CONFIG_PCI_GODIRECT is not set +CONFIG_PCI_GOANY=y CONFIG_PCI_BIOS=y CONFIG_PCI_DIRECT=y CONFIG_PCI_QUIRKS=y @@ -211,6 +215,7 @@ CONFIG_EEXPRESS_PRO100=y # CONFIG_NET_RADIO is not set # CONFIG_TR is not set # CONFIG_HOSTESS_SV11 is not set +# CONFIG_COSA is not set # CONFIG_WAN_DRIVERS is not set # CONFIG_LAPBETHER is not set # CONFIG_X25_ASY is not set @@ -242,6 +247,10 @@ CONFIG_SERIAL=y CONFIG_UNIX98_PTYS=y CONFIG_UNIX98_PTY_COUNT=256 CONFIG_MOUSE=y + +# +# Mice +# # CONFIG_ATIXL_BUSMOUSE is not set # CONFIG_BUSMOUSE is not set # CONFIG_MS_BUSMOUSE is not set @@ -250,9 +259,17 @@ CONFIG_82C710_MOUSE=y # CONFIG_PC110_PAD is not set # CONFIG_QIC02_TAPE is not set # CONFIG_WATCHDOG is not set +# CONFIG_NVRAM is not set # CONFIG_RTC is not set + +# +# Video For Linux +# # CONFIG_VIDEO_DEV is not set -# CONFIG_NVRAM is not set + +# +# Joystick support +# # CONFIG_JOYSTICK is not set # @@ -264,36 +281,44 @@ CONFIG_82C710_MOUSE=y # Filesystems # # CONFIG_QUOTA is not set -# CONFIG_MINIX_FS is not set -CONFIG_EXT2_FS=y -CONFIG_ISO9660_FS=y -# CONFIG_JOLIET is not set +CONFIG_AUTOFS_FS=y +# CONFIG_AFFS_FS is not set +# CONFIG_HFS_FS is not set # CONFIG_FAT_FS is not set # CONFIG_MSDOS_FS is not set # CONFIG_UMSDOS_FS is not set # CONFIG_VFAT_FS is not set +CONFIG_ISO9660_FS=y +# CONFIG_JOLIET is not set +# CONFIG_MINIX_FS is not set +# CONFIG_NTFS_FS is not set +# CONFIG_HPFS_FS is not set CONFIG_PROC_FS=y +CONFIG_DEVPTS_FS=y +# CONFIG_ROMFS_FS is not set +CONFIG_EXT2_FS=y +# CONFIG_SYSV_FS is not set +# CONFIG_UFS_FS is not set + +# +# Network File Systems +# +# CONFIG_CODA_FS is not set CONFIG_NFS_FS=y CONFIG_NFSD=y # CONFIG_NFSD_SUN is not set CONFIG_SUNRPC=y CONFIG_LOCKD=y -# CONFIG_CODA_FS is not set # CONFIG_SMB_FS is not set # CONFIG_NCP_FS is not set -# CONFIG_HPFS_FS is not set -# CONFIG_NTFS_FS is not set -# CONFIG_SYSV_FS is not set -# CONFIG_AFFS_FS is not set -# CONFIG_HFS_FS is not set -# CONFIG_ROMFS_FS is not set -CONFIG_AUTOFS_FS=y -# CONFIG_UFS_FS is not set + +# +# Partition Types +# # CONFIG_BSD_DISKLABEL is not set +# CONFIG_MAC_PARTITION is not set # CONFIG_SMD_DISKLABEL is not set # CONFIG_SOLARIS_X86_PARTITION is not set -CONFIG_DEVPTS_FS=y -# CONFIG_MAC_PARTITION is not set # CONFIG_NLS is not set # diff --git a/arch/i386/kernel/mtrr.c b/arch/i386/kernel/mtrr.c index 324e8cec7d5b..fd330ac294ba 100644 --- a/arch/i386/kernel/mtrr.c +++ b/arch/i386/kernel/mtrr.c @@ -615,7 +615,8 @@ static void do_all_cpus (void (*handler) (struct set_mtrr_context *ctxt, smp_message_pass (MSG_ALL_BUT_SELF, MSG_MTRR_CHANGE, 0, 0); /* Wait for it to be done */ timeout = jiffies + JIFFIE_TIMEOUT; - while ( (atomic_read (&undone_count) > 0) && (jiffies < timeout) ) + while ( (atomic_read (&undone_count) > 0) && + time_before(jiffies, timeout) ) barrier (); if (atomic_read (&undone_count) > 0) { diff --git a/arch/i386/kernel/time.c b/arch/i386/kernel/time.c index 1cafe87c6a19..30f0dac3f4f5 100644 --- a/arch/i386/kernel/time.c +++ b/arch/i386/kernel/time.c @@ -22,8 +22,10 @@ * ported from 2.0.35 Jumbo-9 by Michael Krause ). * 1998-12-16 Andrea Arcangeli * Fixed Jumbo-9 code in 2.1.131: do_gettimeofday was missing 1 jiffy - * because was not accounting lost_ticks. I also removed some ugly - * not needed global cli() and where needed I used a disable_irq(0). + * because was not accounting lost_ticks. + * 1998-12-24 Copyright (C) 1998 Andrea Arcangeli + * Fixed a xtime SMP race (we need the xtime_lock rw spinlock to + * serialize accesses to xtime/lost_ticks). */ /* What about the "updated NTP code" stuff in 2.0 time.c? It's not in @@ -82,6 +84,8 @@ static unsigned long last_tsc_low; /* lsb 32 bits of Time Stamp Counter */ */ static unsigned long fast_gettimeoffset_quotient=0; +extern rwlock_t xtime_lock; + static unsigned long do_fast_gettimeoffset(void) { register unsigned long eax asm("ax"); @@ -237,12 +241,12 @@ void do_gettimeofday(struct timeval *tv) extern volatile unsigned long lost_ticks; unsigned long flags; - save_flags(flags); cli(); + read_lock_irqsave(&xtime_lock, flags); *tv = xtime; tv->tv_usec += do_gettimeoffset(); if (lost_ticks) tv->tv_usec += lost_ticks * (1000000/HZ); - restore_flags(flags); + read_unlock_irqrestore(&xtime_lock, flags); while (tv->tv_usec >= 1000000) { tv->tv_usec -= 1000000; tv->tv_sec++; @@ -251,7 +255,7 @@ void do_gettimeofday(struct timeval *tv) void do_settimeofday(struct timeval *tv) { - cli(); + write_lock_irq(&xtime_lock); /* This is revolting. We need to set the xtime.tv_usec * correctly. However, the value in this location is * is value at the last tick. @@ -269,7 +273,7 @@ void do_settimeofday(struct timeval *tv) time_state = TIME_BAD; time_maxerror = MAXPHASE; time_esterror = MAXPHASE; - sti(); + write_unlock_irq(&xtime_lock); } /* @@ -344,7 +348,7 @@ static long last_rtc_update = 0; * timer_interrupt() needs to keep up the real-time clock, * as well as call the "do_timer()" routine every clocktick */ -static inline void timer_interrupt(int irq, void *dev_id, struct pt_regs *regs) +static inline void do_timer_interrupt(int irq, void *dev_id, struct pt_regs *regs) { do_timer(regs); /* @@ -398,37 +402,56 @@ static inline void timer_interrupt(int irq, void *dev_id, struct pt_regs *regs) #endif } +static int use_tsc = 0; + /* * This is the same as the above, except we _also_ save the current * Time Stamp Counter value at the time of the timer interrupt, so that * we later on can estimate the time of day more exactly. */ -static void pentium_timer_interrupt(int irq, void *dev_id, struct pt_regs *regs) +static void timer_interrupt(int irq, void *dev_id, struct pt_regs *regs) { int count; - /* It is important that these two operations happen almost at the - * same time. We do the RDTSC stuff first, since it's faster. To - * avoid any inconsistencies, we need interrupts disabled locally. - */ - /* - * Interrupts are just disabled locally since the timer irq has the - * SA_INTERRUPT flag set. -arca + * Here we are in the timer irq handler. We just have irqs locally + * disabled but we don't know if the timer_bh is running on the other + * CPU. We need to avoid to SMP race with it. NOTE: we don' t need + * the irq version of write_lock because as just said we have irq + * locally disabled. -arca */ + write_lock(&xtime_lock); + + if (use_tsc) + { + /* + * It is important that these two operations happen almost at + * the same time. We do the RDTSC stuff first, since it's + * faster. To avoid any inconsistencies, we need interrupts + * disabled locally. + */ + + /* + * Interrupts are just disabled locally since the timer irq + * has the SA_INTERRUPT flag set. -arca + */ - /* read Pentium cycle counter */ - __asm__("rdtsc" : "=a" (last_tsc_low) : : "edx"); + /* read Pentium cycle counter */ + __asm__("rdtsc" : "=a" (last_tsc_low) : : "edx"); - outb_p(0x00, 0x43); /* latch the count ASAP */ + outb_p(0x00, 0x43); /* latch the count ASAP */ - count = inb_p(0x40); /* read the latched count */ - count |= inb(0x40) << 8; + count = inb_p(0x40); /* read the latched count */ + count |= inb(0x40) << 8; - count = ((LATCH-1) - count) * TICK_SIZE; - delay_at_last_interrupt = (count + LATCH/2) / LATCH; + count = ((LATCH-1) - count) * TICK_SIZE; + delay_at_last_interrupt = (count + LATCH/2) / LATCH; + } - timer_interrupt(irq, NULL, regs); + do_timer_interrupt(irq, NULL, regs); + + write_unlock(&xtime_lock); + } /* Converts Gregorian date to seconds since 1970-01-01 00:00:00. @@ -601,7 +624,7 @@ __initfunc(void time_init(void)) if (boot_cpu_data.x86_capability & X86_FEATURE_TSC) { do_gettimeoffset = do_fast_gettimeoffset; do_get_fast_time = do_gettimeofday; - irq0.handler = pentium_timer_interrupt; + use_tsc = 1; fast_gettimeoffset_quotient = calibrate_tsc(); /* report CPU clock rate in Hz. diff --git a/arch/i386/kernel/traps.c b/arch/i386/kernel/traps.c index 6e9a95423008..71b47d788584 100644 --- a/arch/i386/kernel/traps.c +++ b/arch/i386/kernel/traps.c @@ -499,15 +499,18 @@ __initfunc(void trap_init_f00f_bug(void)) } #define _set_gate(gate_addr,type,dpl,addr) \ -__asm__ __volatile__ ("movw %%dx,%%ax\n\t" \ - "movw %2,%%dx\n\t" \ +do { \ + int __d0, __d1; \ + __asm__ __volatile__ ("movw %%dx,%%ax\n\t" \ + "movw %4,%%dx\n\t" \ "movl %%eax,%0\n\t" \ "movl %%edx,%1" \ :"=m" (*((long *) (gate_addr))), \ - "=m" (*(1+(long *) (gate_addr))) \ + "=m" (*(1+(long *) (gate_addr))), "=&a" (__d0), "=&d" (__d1) \ :"i" ((short) (0x8000+(dpl<<13)+(type<<8))), \ - "d" ((char *) (addr)),"a" (__KERNEL_CS << 16) \ - :"ax","dx") + "3" ((char *) (addr)),"2" (__KERNEL_CS << 16)); \ +} while (0) + /* * This needs to use 'idt_table' rather than 'idt', and diff --git a/arch/i386/lib/Makefile b/arch/i386/lib/Makefile index 6490984b16fc..c2cb3e5a6b9d 100644 --- a/arch/i386/lib/Makefile +++ b/arch/i386/lib/Makefile @@ -6,6 +6,7 @@ $(CC) -D__ASSEMBLY__ $(AFLAGS) -traditional -c $< -o $*.o L_TARGET = lib.a -L_OBJS = checksum.o semaphore.o delay.o usercopy.o getuser.o putuser.o +L_OBJS = checksum.o old-checksum.o semaphore.o delay.o \ + usercopy.o getuser.o putuser.o include $(TOPDIR)/Rules.make diff --git a/arch/i386/lib/checksum.S b/arch/i386/lib/checksum.S new file mode 100644 index 000000000000..f721cb89207e --- /dev/null +++ b/arch/i386/lib/checksum.S @@ -0,0 +1,450 @@ +/* + * INET An implementation of the TCP/IP protocol suite for the LINUX + * operating system. INET is implemented using the BSD Socket + * interface as the means of communication with the user level. + * + * IP/TCP/UDP checksumming routines + * + * Authors: Jorge Cwik, + * Arnt Gulbrandsen, + * Tom May, + * Pentium Pro/II routines: + * Alexander Kjeldaas + * Finn Arne Gangstad + * Lots of code moved from tcp.c and ip.c; see those files + * for more names. + * + * Changes: Ingo Molnar, converted csum_partial_copy() to 2.1 exception + * handling. + * Andi Kleen, add zeroing on error + * converted to pure assembler + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version + * 2 of the License, or (at your option) any later version. + */ + +#include + +/* + * computes a partial checksum, e.g. for TCP/UDP fragments + */ + +/* +unsigned int csum_partial(const unsigned char * buff, int len, unsigned int sum) + */ + +.text +.align 4 +.globl csum_partial + +#if CPU!=686 + + /* + * Experiments with Ethernet and SLIP connections show that buff + * is aligned on either a 2-byte or 4-byte boundary. We get at + * least a twofold speedup on 486 and Pentium if it is 4-byte aligned. + * Fortunately, it is easy to convert 2-byte alignment to 4-byte + * alignment for the unrolled loop. + */ +csum_partial: + pushl %esi + pushl %ebx + movl 20(%esp),%eax # Function arg: unsigned int sum + movl 16(%esp),%ecx # Function arg: int len + movl 12(%esp),%esi # Function arg: unsigned char *buff + testl $2, %esi # Check alignment. + jz 2f # Jump if alignment is ok. + subl $2, %ecx # Alignment uses up two bytes. + jae 1f # Jump if we had at least two bytes. + addl $2, %ecx # ecx was < 2. Deal with it. + jmp 4f +1: movw (%esi), %bx + addl $2, %esi + addw %bx, %ax + adcl $0, %eax +2: + movl %ecx, %edx + shrl $5, %ecx + jz 2f + testl %esi, %esi +1: movl (%esi), %ebx + adcl %ebx, %eax + movl 4(%esi), %ebx + adcl %ebx, %eax + movl 8(%esi), %ebx + adcl %ebx, %eax + movl 12(%esi), %ebx + adcl %ebx, %eax + movl 16(%esi), %ebx + adcl %ebx, %eax + movl 20(%esi), %ebx + adcl %ebx, %eax + movl 24(%esi), %ebx + adcl %ebx, %eax + movl 28(%esi), %ebx + adcl %ebx, %eax + lea 32(%esi), %esi + dec %ecx + jne 1b + adcl $0, %eax +2: movl %edx, %ecx + andl $0x1c, %edx + je 4f + shrl $2, %edx # This clears CF +3: adcl (%esi), %eax + lea 4(%esi), %esi + dec %edx + jne 3b + adcl $0, %eax +4: andl $3, %ecx + jz 7f + cmpl $2, %ecx + jb 5f + movw (%esi),%cx + leal 2(%esi),%esi + je 6f + shll $16,%ecx +5: movb (%esi),%cl +6: addl %ecx,%eax + adcl $0, %eax +7: + popl %ebx + popl %esi + ret + +#else /* CPU==686 */ + +csum_partial: + movl 12(%esp),%eax # Function arg: unsigned int sum + movl 8(%esp),%ecx # Function arg: int len + movl 4(%esp),%esi # Function arg: const unsigned char *buf + + testl $2, %esi + jnz 30f +10: + movl %ecx, %edx + movl %ecx, %ebx + andl $0x7c, %ebx + shrl $7, %ecx + addl %ebx,%esi + shrl $2, %ebx + negl %ebx + lea 45f(%ebx,%ebx,2), %ebx + testl %esi, %esi + jmp *%ebx + + # Handle 2-byte-aligned regions +20: addw (%esi), %ax + lea 2(%esi), %esi + adcl $0, %eax + jmp 10b + +30: subl $2, %ecx + ja 20b + je 32f + movzbl (%esi),%ebx # csumming 1 byte, 2-aligned + addl %ebx, %eax + adcl $0, %eax + jmp 80f +32: + addw (%esi), %ax # csumming 2 bytes, 2-aligned + adcl $0, %eax + jmp 80f + +40: + addl -128(%esi), %eax + adcl -124(%esi), %eax + adcl -120(%esi), %eax + adcl -116(%esi), %eax + adcl -112(%esi), %eax + adcl -108(%esi), %eax + adcl -104(%esi), %eax + adcl -100(%esi), %eax + adcl -96(%esi), %eax + adcl -92(%esi), %eax + adcl -88(%esi), %eax + adcl -84(%esi), %eax + adcl -80(%esi), %eax + adcl -76(%esi), %eax + adcl -72(%esi), %eax + adcl -68(%esi), %eax + adcl -64(%esi), %eax + adcl -60(%esi), %eax + adcl -56(%esi), %eax + adcl -52(%esi), %eax + adcl -48(%esi), %eax + adcl -44(%esi), %eax + adcl -40(%esi), %eax + adcl -36(%esi), %eax + adcl -32(%esi), %eax + adcl -28(%esi), %eax + adcl -24(%esi), %eax + adcl -20(%esi), %eax + adcl -16(%esi), %eax + adcl -12(%esi), %eax + adcl -8(%esi), %eax + adcl -4(%esi), %eax +45: + lea 128(%esi), %esi + adcl $0, %eax + dec %ecx + jge 40b + movl %edx, %ecx +50: andl $3, %ecx + jz 80f + + # Handle the last 1-3 bytes without jumping + notl %ecx # 1->2, 2->1, 3->0, higher bits are masked + movl $0xffffff,%ebx # by the shll and shrl instructions + shll $3,%ecx + shrl %cl,%ebx + andl -128(%esi),%ebx # esi is 4-aligned so should be ok + addl %ebx,%eax + adcl $0,%eax +80: + ret + +#endif /* CPU==686 */ + +/* +unsigned int csum_partial_copy_generic (const char *src, char *dst, + int len, int sum, int *src_err_ptr, int *dst_err_ptr) + */ + +/* + * Copy from ds while checksumming, otherwise like csum_partial + * + * The macros SRC and DST specify the type of access for the instruction. + * thus we can call a custom exception handler for all access types. + * + * FIXME: could someone double-check whether I haven't mixed up some SRC and + * DST definitions? It's damn hard to trigger all cases. I hope I got + * them all but there's no guarantee. + */ + +#define SRC(y...) \ + 9999: y; \ + .section __ex_table, "a"; \ + .long 9999b, 6001f ; \ + .previous + +#define DST(y...) \ + 9999: y; \ + .section __ex_table, "a"; \ + .long 9999b, 6002f ; \ + .previous + +.align 4 +.globl csum_partial_copy_generic + +#if CPU!=686 + +#define ARGBASE 16 +#define FP 12 + +csum_partial_copy_generic: + subl $4,%esp + pushl %edi + pushl %esi + pushl %ebx + movl ARGBASE+16(%esp),%eax # sum + movl ARGBASE+12(%esp),%ecx # len + movl ARGBASE+4(%esp),%esi # src + movl ARGBASE+8(%esp),%edi # dst + + testl $2, %edi # Check alignment. + jz 2f # Jump if alignment is ok. + subl $2, %ecx # Alignment uses up two bytes. + jae 1f # Jump if we had at least two bytes. + addl $2, %ecx # ecx was < 2. Deal with it. + jmp 4f +SRC(1: movw (%esi), %bx ) + addl $2, %esi +DST( movw %bx, (%edi) ) + addl $2, %edi + addw %bx, %ax + adcl $0, %eax +2: + movl %ecx, FP(%esp) + shrl $5, %ecx + jz 2f + testl %esi, %esi +SRC(1: movl (%esi), %ebx ) +SRC( movl 4(%esi), %edx ) + adcl %ebx, %eax +DST( movl %ebx, (%edi) ) + adcl %edx, %eax +DST( movl %edx, 4(%edi) ) + +SRC( movl 8(%esi), %ebx ) +SRC( movl 12(%esi), %edx ) + adcl %ebx, %eax +DST( movl %ebx, 8(%edi) ) + adcl %edx, %eax +DST( movl %edx, 12(%edi) ) + +SRC( movl 16(%esi), %ebx ) +SRC( movl 20(%esi), %edx ) + adcl %ebx, %eax +DST( movl %ebx, 16(%edi) ) + adcl %edx, %eax +DST( movl %edx, 20(%edi) ) + +SRC( movl 24(%esi), %ebx ) +SRC( movl 28(%esi), %edx ) + adcl %ebx, %eax +DST( movl %ebx, 24(%edi) ) + adcl %edx, %eax +DST( movl %edx, 28(%edi) ) + +SRC( lea 32(%esi), %esi ) +DST( lea 32(%edi), %edi ) + dec %ecx + jne 1b + adcl $0, %eax +2: movl FP(%esp), %edx + movl %edx, %ecx + andl $0x1c, %edx + je 4f + shrl $2, %edx # This clears CF +SRC(3: movl (%esi), %ebx ) + adcl %ebx, %eax +DST( movl %ebx, (%edi) ) +SRC( lea 4(%esi), %esi ) +DST( lea 4(%edi), %edi ) + dec %edx + jne 3b + adcl $0, %eax +4: andl $3, %ecx + jz 7f + cmpl $2, %ecx + jb 5f +SRC( movw (%esi), %cx ) +SRC( leal 2(%esi), %esi ) +DST( movw %cx, (%edi) ) +DST( leal 2(%edi), %edi ) + je 6f + shll $16,%ecx +SRC(5: movb (%esi), %cl ) +DST( movb %cl, (%edi) ) +6: addl %ecx, %eax + adcl $0, %eax +7: +5000: + +# Exception handler: +.section .fixup, "ax" + +6000: + + movl $-EFAULT, (%ebx) + + # zero the complete destination - computing the rest + # is too much work + movl ARGBASE+8(%esp), %edi # dst + movl ARGBASE+12(%esp), %ecx # len + xorl %eax,%eax + rep ; stosb + + jmp 5000b + +6001: + movl ARGBASE+20(%esp), %ebx # src_err_ptr + jmp 6000b + +6002: + movl ARGBASE+24(%esp), %ebx # dst_err_ptr + jmp 6000b + +.previous + + popl %ebx + popl %esi + popl %edi + popl %ecx # equivalent to addl $4,%esp + ret + +#else + +/* Version for PentiumII/PPro */ + +#define ROUND1(x) \ + SRC(movl x(%esi), %ebx ) ; \ + addl %ebx, %eax\n ; \ + DST(movl %ebx, x(%edi) ) ; + +#define ROUND(x) \ + SRC(movl x(%esi), %ebx ) ; \ + adcl %ebx, %eax ; \ + DST(movl %ebx, x(%edi) ) ; + +#define ARGBASE 12 + +csum_partial_copy_generic: + pushl %ebx + pushl %edi + pushl %esi + movl ARGBASE+4(%esp),%esi #src + movl ARGBASE+8(%esp),%edi #dst + movl ARGBASE+12(%esp),%ecx #len + movl ARGBASE+16(%esp),%eax #sum + movl %ecx, %edx + movl %ecx, %ebx + shrl $6, %ecx + andl $0x3c, %ebx + negl %ebx + subl %ebx, %esi + subl %ebx, %edi + lea 3f(%ebx,%ebx), %ebx + testl %esi, %esi + jmp *%ebx +1: addl $64,%esi + addl $64,%edi + ROUND1(-64) ROUND(-60) ROUND(-56) ROUND(-52) + ROUND (-48) ROUND(-44) ROUND(-40) ROUND(-36) + ROUND (-32) ROUND(-28) ROUND(-24) ROUND(-20) + ROUND (-16) ROUND(-12) ROUND(-8) ROUND(-4) +3: adcl $0,%eax + dec %ecx + jge 1b +4: andl $3, %edx + jz 7f + cmpl $2, %edx + jb 5f +SRC( movw (%esi), %dx ) + leal 2(%esi), %esi +DST( movw %dx, (%edi) ) + leal 2(%edi), %edi + je 6f + shll $16,%edx +5: +SRC( movb (%esi), %dl ) +DST( movb %dl, (%edi) ) +6: addl %edx, %eax + adcl $0, %eax +7: +.section .fixup, "ax" +6000: movl $-EFAULT, (%ebx) + # zero the complete destination (computing the rest is too much work) + movl ARGBASE+8(%esp),%edi # dst + movl ARGBASE+12(%esp),%ecx # len + xorl %eax,%eax + rep; stosb + jmp 7b +6001: movl ARGBASE+20(%esp), %ebx # src_err_ptr + jmp 6000b +6002: movl ARGBASE+24(%esp), %ebx # dst_err_ptr + jmp 6000b +.previous + + popl %esi + popl %edi + popl %ebx + ret + +#undef ROUND +#undef ROUND1 + +#endif /* CPU==i686 */ diff --git a/arch/i386/lib/checksum.c b/arch/i386/lib/checksum.c deleted file mode 100644 index 51a9219db757..000000000000 --- a/arch/i386/lib/checksum.c +++ /dev/null @@ -1,459 +0,0 @@ -/* - * INET An implementation of the TCP/IP protocol suite for the LINUX - * operating system. INET is implemented using the BSD Socket - * interface as the means of communication with the user level. - * - * IP/TCP/UDP checksumming routines - * - * Authors: Jorge Cwik, - * Arnt Gulbrandsen, - * Tom May, - * Pentium Pro/II routines: - * Alexander Kjeldaas - * Finn Arne Gangstad - * Lots of code moved from tcp.c and ip.c; see those files - * for more names. - * - * Changes: Ingo Molnar, converted csum_partial_copy() to 2.1 exception - * handling. - * Andi Kleen, add zeroing on error, fix constraints. - * - * To fix: - * Convert to pure asm, because this file is too hard - * for gcc's register allocator and it is not clear if the - * contraints are correct. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU General Public License - * as published by the Free Software Foundation; either version - * 2 of the License, or (at your option) any later version. - */ - -#include - -/* - * computes a partial checksum, e.g. for TCP/UDP fragments - */ - -#if CPU!=686 - -unsigned int csum_partial(const unsigned char * buff, int len, unsigned int sum) { - /* - * Experiments with Ethernet and SLIP connections show that buff - * is aligned on either a 2-byte or 4-byte boundary. We get at - * least a twofold speedup on 486 and Pentium if it is 4-byte aligned. - * Fortunately, it is easy to convert 2-byte alignment to 4-byte - * alignment for the unrolled loop. - */ - __asm__(" - testl $2, %%esi # Check alignment. - jz 2f # Jump if alignment is ok. - subl $2, %%ecx # Alignment uses up two bytes. - jae 1f # Jump if we had at least two bytes. - addl $2, %%ecx # ecx was < 2. Deal with it. - jmp 4f -1: movw (%%esi), %%bx - addl $2, %%esi - addw %%bx, %%ax - adcl $0, %%eax -2: - movl %%ecx, %%edx - shrl $5, %%ecx - jz 2f - testl %%esi, %%esi -1: movl (%%esi), %%ebx - adcl %%ebx, %%eax - movl 4(%%esi), %%ebx - adcl %%ebx, %%eax - movl 8(%%esi), %%ebx - adcl %%ebx, %%eax - movl 12(%%esi), %%ebx - adcl %%ebx, %%eax - movl 16(%%esi), %%ebx - adcl %%ebx, %%eax - movl 20(%%esi), %%ebx - adcl %%ebx, %%eax - movl 24(%%esi), %%ebx - adcl %%ebx, %%eax - movl 28(%%esi), %%ebx - adcl %%ebx, %%eax - lea 32(%%esi), %%esi - dec %%ecx - jne 1b - adcl $0, %%eax -2: movl %%edx, %%ecx - andl $0x1c, %%edx - je 4f - shrl $2, %%edx # This clears CF -3: adcl (%%esi), %%eax - lea 4(%%esi), %%esi - dec %%edx - jne 3b - adcl $0, %%eax -4: andl $3, %%ecx - jz 7f - cmpl $2, %%ecx - jb 5f - movw (%%esi),%%cx - leal 2(%%esi),%%esi - je 6f - shll $16,%%ecx -5: movb (%%esi),%%cl -6: addl %%ecx,%%eax - adcl $0, %%eax -7: " - : "=a"(sum) - : "0"(sum), "c"(len), "S"(buff) - : "bx", "dx", "si", "cx", "memory"); - return(sum); -} - -#else /* 686 */ - -unsigned int csum_partial(const unsigned char * buf, int len, unsigned int sum) { - __asm__ (" - testl $2, %%esi - jnz 30f -10: - movl %%ecx, %%edx - movl %%ecx, %%ebx - andl $0x7c, %%ebx - shrl $7, %%ecx - addl %%ebx,%%esi - shrl $2, %%ebx - negl %%ebx - lea 45f(%%ebx,%%ebx,2), %%ebx - testl %%esi, %%esi - jmp *%%ebx - - # Handle 2-byte-aligned regions -20: addw (%%esi), %%ax - lea 2(%%esi), %%esi - adcl $0, %%eax - jmp 10b - -30: subl $2, %%ecx - ja 20b - je 32f - movzbl (%%esi),%%ebx # csumming 1 byte, 2-aligned - addl %%ebx, %%eax - adcl $0, %%eax - jmp 80f -32: - addw (%%esi), %%ax # csumming 2 bytes, 2-aligned - adcl $0, %%eax - jmp 80f - -40: - addl -128(%%esi), %%eax - adcl -124(%%esi), %%eax - adcl -120(%%esi), %%eax - adcl -116(%%esi), %%eax - adcl -112(%%esi), %%eax - adcl -108(%%esi), %%eax - adcl -104(%%esi), %%eax - adcl -100(%%esi), %%eax - adcl -96(%%esi), %%eax - adcl -92(%%esi), %%eax - adcl -88(%%esi), %%eax - adcl -84(%%esi), %%eax - adcl -80(%%esi), %%eax - adcl -76(%%esi), %%eax - adcl -72(%%esi), %%eax - adcl -68(%%esi), %%eax - adcl -64(%%esi), %%eax - adcl -60(%%esi), %%eax - adcl -56(%%esi), %%eax - adcl -52(%%esi), %%eax - adcl -48(%%esi), %%eax - adcl -44(%%esi), %%eax - adcl -40(%%esi), %%eax - adcl -36(%%esi), %%eax - adcl -32(%%esi), %%eax - adcl -28(%%esi), %%eax - adcl -24(%%esi), %%eax - adcl -20(%%esi), %%eax - adcl -16(%%esi), %%eax - adcl -12(%%esi), %%eax - adcl -8(%%esi), %%eax - adcl -4(%%esi), %%eax -45: - lea 128(%%esi), %%esi - adcl $0, %%eax - dec %%ecx - jge 40b - movl %%edx, %%ecx -50: andl $3, %%ecx - jz 80f - - # Handle the last 1-3 bytes without jumping - notl %%ecx # 1->2, 2->1, 3->0, higher bits are masked - movl $0xffffff,%%ebx # by the shll and shrl instructions - shll $3,%%ecx - shrl %%cl,%%ebx - andl -128(%%esi),%%ebx # esi is 4-aligned so should be ok - addl %%ebx,%%eax - adcl $0,%%eax -80: " - : "=a"(sum) - : "0"(sum), "c"(len), "S"(buf) - : "bx", "dx", "cx", "si", "memory"); - return(sum); -} - -#endif - -/* - * Copy from ds while checksumming, otherwise like csum_partial - * - * The macros SRC and DST specify the type of access for the instruction. - * thus we can call a custom exception handler for all access types. - * - * FIXME: could someone double-check whether I haven't mixed up some SRC and - * DST definitions? It's damn hard to trigger all cases. I hope I got - * them all but there's no guarantee. - */ - -#define SRC(y...) \ -" 9999: "#y"; \n \ - .section __ex_table, \"a\"; \n \ - .long 9999b, 6001f \n \ - .previous\n" - -#define DST(y...) \ -" 9999: "#y"; \n \ - .section __ex_table, \"a\"; \n \ - .long 9999b, 6002f \n \ - .previous\n" - -#if CPU!=686 - -unsigned int csum_partial_copy_generic (const char *src, char *dst, - int len, int sum, int *src_err_ptr, int *dst_err_ptr) -{ - __u32 tmp_var; - - __asm__ __volatile__ ( " - movl %6,%%edi - testl $2, %%edi # Check alignment. - jz 2f # Jump if alignment is ok. - subl $2, %%ecx # Alignment uses up two bytes. - jae 1f # Jump if we had at least two bytes. - addl $2, %%ecx # ecx was < 2. Deal with it. - jmp 4f -"SRC( 1: movw (%%esi), %%bx )" - addl $2, %%esi -"DST( movw %%bx, (%%edi) )" - addl $2, %%edi - addw %%bx, %%ax - adcl $0, %%eax - 2: - movl %%ecx, %8 - shrl $5, %%ecx - jz 2f - testl %%esi, %%esi -"SRC( 1: movl (%%esi), %%ebx )" -"SRC( movl 4(%%esi), %%edx )" - adcl %%ebx, %%eax -"DST( movl %%ebx, (%%edi) )" - adcl %%edx, %%eax -"DST( movl %%edx, 4(%%edi) )" - -"SRC( movl 8(%%esi), %%ebx )" -"SRC( movl 12(%%esi), %%edx )" - adcl %%ebx, %%eax -"DST( movl %%ebx, 8(%%edi) )" - adcl %%edx, %%eax -"DST( movl %%edx, 12(%%edi) )" - -"SRC( movl 16(%%esi), %%ebx )" -"SRC( movl 20(%%esi), %%edx )" - adcl %%ebx, %%eax -"DST( movl %%ebx, 16(%%edi) )" - adcl %%edx, %%eax -"DST( movl %%edx, 20(%%edi) )" - -"SRC( movl 24(%%esi), %%ebx )" -"SRC( movl 28(%%esi), %%edx )" - adcl %%ebx, %%eax -"DST( movl %%ebx, 24(%%edi) )" - adcl %%edx, %%eax -"DST( movl %%edx, 28(%%edi) )" - -"SRC( lea 32(%%esi), %%esi )" -"DST( lea 32(%%edi), %%edi )" - dec %%ecx - jne 1b - adcl $0, %%eax - 2: movl %8, %%edx - movl %%edx, %%ecx - andl $0x1c, %%edx - je 4f - shrl $2, %%edx # This clears CF -"SRC( 3: movl (%%esi), %%ebx )" - adcl %%ebx, %%eax -"DST( movl %%ebx, (%%edi) )" -"SRC( lea 4(%%esi), %%esi )" -"DST( lea 4(%%edi), %%edi )" - dec %%edx - jne 3b - adcl $0, %%eax - 4: andl $3, %%ecx - jz 7f - cmpl $2, %%ecx - jb 5f -"SRC( movw (%%esi), %%cx )" -"SRC( leal 2(%%esi), %%esi )" -"DST( movw %%cx, (%%edi) )" -"DST( leal 2(%%edi), %%edi )" - je 6f - shll $16,%%ecx -"SRC( 5: movb (%%esi), %%cl )" -"DST( movb %%cl, (%%edi) )" - 6: addl %%ecx, %%eax - adcl $0, %%eax - 7: - -5000: - -# Exception handler: -################################################ - # -.section .fixup, \"ax\" # - # -6000: # - # - movl %7, (%%ebx) # - # -# zero the complete destination - computing the rest -# is too much work - movl %6, %%edi - movl %9, %%ecx - xorl %%eax,%%eax - rep ; stosb - # - jmp 5000b # - # -6001: # - movl %1, %%ebx # - jmp 6000b # - # -6002: # - movl %2, %%ebx # - jmp 6000b # - # -.previous # - # -################################################ - -" - : "=a" (sum) - : "m" (src_err_ptr), "m" (dst_err_ptr), - "0" (sum), "c" (len), "S" (src), "m" (dst), - "i" (-EFAULT), "m"(tmp_var), - "m" (len) - : "bx", "dx", "si", "di", "cx", "memory" ); - - return(sum); -} - -#else /* CPU == 686 */ - -#define ROUND1(x) \ - SRC(movl x(%%esi), %%ebx ) \ - "addl %%ebx, %%eax\n" \ - DST(movl %%ebx, x(%%edi) ) - -#define ROUND(x) \ - SRC(movl x(%%esi), %%ebx ) \ - "adcl %%ebx, %%eax\n" \ - DST(movl %%ebx, x(%%edi) ) - -unsigned int csum_partial_copy_generic (const char *src, char *dst, - int len, int sum, int *src_err_ptr, int *dst_err_ptr) -{ - __asm__ __volatile__ (" - movl %4,%%ecx - movl %%ecx, %%edx - movl %%ecx, %%ebx - shrl $6, %%ecx - andl $0x3c, %%ebx - negl %%ebx - subl %%ebx, %%esi - subl %%ebx, %%edi - lea 3f(%%ebx,%%ebx), %%ebx - testl %%esi, %%esi - jmp *%%ebx -1: addl $64,%%esi - addl $64,%%edi\n" -ROUND1(-64) ROUND(-60) ROUND(-56) ROUND(-52) -ROUND (-48) ROUND(-44) ROUND(-40) ROUND(-36) -ROUND (-32) ROUND(-28) ROUND(-24) ROUND(-20) -ROUND (-16) ROUND(-12) ROUND(-8) ROUND(-4) -"3: adcl $0,%%eax - dec %%ecx - jge 1b -4: andl $3, %%edx - jz 7f - cmpl $2, %%edx - jb 5f - " SRC(movw (%%esi), %%dx )" - leal 2(%%esi), %%esi - " DST(movw %%dx, (%%edi) )" - leal 2(%%edi), %%edi - je 6f - shll $16,%%edx -5:" SRC(movb (%%esi), %%dl )" - " DST(movb %%dl, (%%edi) )" -6: addl %%edx, %%eax - adcl $0, %%eax -7: -.section .fixup, \"ax\" -6000: movl %7, (%%ebx) -# zero the complete destination (computing the rest is too much work) - movl %8,%%edi - movl %4,%%ecx - xorl %%eax,%%eax - rep ; stosb - jmp 7b -6001: movl %1, %%ebx - jmp 6000b -6002: movl %2, %%ebx - jmp 6000b -.previous - " - : "=a"(sum) - : "m"(src_err_ptr), "m"(dst_err_ptr), - "0"(sum), "m"(len), "S"(src), "D" (dst), - "i" (-EFAULT), - "m" (dst) - : "bx", "cx", "si", "di", "dx", "memory" ); - return(sum); -} - -#undef ROUND -#undef ROUND1 - -#endif - - -#undef SRC -#undef DST - -/* - * FIXME: old compatibility stuff, will be removed soon. - */ - -unsigned int csum_partial_copy( const char *src, char *dst, int len, int sum) -{ - int src_err=0, dst_err=0; - - sum = csum_partial_copy_generic ( src, dst, len, sum, &src_err, &dst_err); - - if (src_err || dst_err) - printk("old csum_partial_copy_fromuser(), tell mingo to convert me.\n"); - - return sum; -} - - diff --git a/arch/i386/lib/delay.c b/arch/i386/lib/delay.c index ae8aec6360f9..6918451a6b02 100644 --- a/arch/i386/lib/delay.c +++ b/arch/i386/lib/delay.c @@ -19,23 +19,23 @@ void __delay(unsigned long loops) { + int d0; __asm__ __volatile__( "\tjmp 1f\n" ".align 16\n" "1:\tjmp 2f\n" ".align 16\n" "2:\tdecl %0\n\tjns 2b" - :/* no outputs */ - :"a" (loops) - :"ax"); + :"=&a" (d0) + :"0" (loops)); } inline void __const_udelay(unsigned long xloops) { + int d0; __asm__("mull %0" - :"=d" (xloops) - :"a" (xloops),"0" (current_cpu_data.loops_per_sec) - :"ax"); + :"=d" (xloops), "=&a" (d0) + :"1" (xloops),"0" (current_cpu_data.loops_per_sec)); __delay(xloops); } diff --git a/arch/i386/lib/old-checksum.c b/arch/i386/lib/old-checksum.c new file mode 100644 index 000000000000..ae3a38043a7f --- /dev/null +++ b/arch/i386/lib/old-checksum.c @@ -0,0 +1,19 @@ +/* + * FIXME: old compatibility stuff, will be removed soon. + */ + +#include + +unsigned int csum_partial_copy( const char *src, char *dst, int len, int sum) +{ + int src_err=0, dst_err=0; + + sum = csum_partial_copy_generic ( src, dst, len, sum, &src_err, &dst_err); + + if (src_err || dst_err) + printk("old csum_partial_copy_fromuser(), tell mingo to convert me.\n"); + + return sum; +} + + diff --git a/arch/i386/lib/usercopy.c b/arch/i386/lib/usercopy.c index d5b052c20f3c..f43be511f34a 100644 --- a/arch/i386/lib/usercopy.c +++ b/arch/i386/lib/usercopy.c @@ -29,6 +29,8 @@ __generic_copy_from_user(void *to, const void *from, unsigned long n) */ #define __do_strncpy_from_user(dst,src,count,res) \ +do { \ + int __d0, __d1, __d2; \ __asm__ __volatile__( \ " testl %1,%1\n" \ " jz 2f\n" \ @@ -41,16 +43,18 @@ __generic_copy_from_user(void *to, const void *from, unsigned long n) "1: subl %1,%0\n" \ "2:\n" \ ".section .fixup,\"ax\"\n" \ - "3: movl %2,%0\n" \ + "3: movl %5,%0\n" \ " jmp 2b\n" \ ".previous\n" \ ".section __ex_table,\"a\"\n" \ " .align 4\n" \ " .long 0b,3b\n" \ ".previous" \ - : "=d"(res), "=c"(count) \ - : "i"(-EFAULT), "0"(count), "1"(count), "S"(src), "D"(dst) \ - : "si", "di", "ax", "memory") + : "=d"(res), "=c"(count), "=&a" (__d0), "=&S" (__d1), \ + "=&D" (__d2) \ + : "i"(-EFAULT), "0"(count), "1"(count), "3"(src), "4"(dst) \ + : "memory"); \ +} while (0) long __strncpy_from_user(char *dst, const char *src, long count) @@ -74,14 +78,16 @@ strncpy_from_user(char *dst, const char *src, long count) * Zero Userspace */ -#define __do_clear_user(addr,size) \ - __asm__ __volatile__( \ +#define __do_clear_user(addr,size) \ +do { \ + int __d0; \ + __asm__ __volatile__( \ "0: rep; stosl\n" \ - " movl %1,%0\n" \ + " movl %2,%0\n" \ "1: rep; stosb\n" \ "2:\n" \ ".section .fixup,\"ax\"\n" \ - "3: lea 0(%1,%0,4),%0\n" \ + "3: lea 0(%2,%0,4),%0\n" \ " jmp 2b\n" \ ".previous\n" \ ".section __ex_table,\"a\"\n" \ @@ -89,9 +95,9 @@ strncpy_from_user(char *dst, const char *src, long count) " .long 0b,3b\n" \ " .long 1b,2b\n" \ ".previous" \ - : "=&c"(size) \ - : "r"(size & 3), "0"(size / 4), "D"(addr), "a"(0) \ - : "di") + : "=&c"(size), "=&D" (__d0) \ + : "r"(size & 3), "0"(size / 4), "1"(addr), "a"(0)); \ +} while (0) unsigned long clear_user(void *to, unsigned long n) diff --git a/arch/i386/mm/init.c b/arch/i386/mm/init.c index 693072b1a5d5..6697a991117b 100644 --- a/arch/i386/mm/init.c +++ b/arch/i386/mm/init.c @@ -119,24 +119,28 @@ int do_check_pgt_cache(int low, int high) pte_t * __bad_pagetable(void) { extern char empty_bad_page_table[PAGE_SIZE]; - - __asm__ __volatile__("cld ; rep ; stosl": - :"a" (pte_val(BAD_PAGE)), - "D" ((long) empty_bad_page_table), - "c" (PAGE_SIZE/4) - :"di","cx"); + int d0, d1; + + __asm__ __volatile__("cld ; rep ; stosl" + : "=&D" (d0), "=&c" (d1) + : "a" (pte_val(BAD_PAGE)), + "0" ((long) empty_bad_page_table), + "1" (PAGE_SIZE/4) + : "memory"); return (pte_t *) empty_bad_page_table; } pte_t __bad_page(void) { extern char empty_bad_page[PAGE_SIZE]; - - __asm__ __volatile__("cld ; rep ; stosl": - :"a" (0), - "D" ((long) empty_bad_page), - "c" (PAGE_SIZE/4) - :"di","cx"); + int d0, d1; + + __asm__ __volatile__("cld ; rep ; stosl" + : "=&D" (d0), "=&c" (d1) + : "a" (0), + "0" ((long) empty_bad_page), + "1" (PAGE_SIZE/4) + : "memory"); return pte_mkdirty(mk_pte((unsigned long) empty_bad_page, PAGE_SHARED)); } @@ -298,7 +302,8 @@ __initfunc(unsigned long paging_init(unsigned long start_mem, unsigned long end_ * NOTE! There are Linux loaders that will corrupt the EBDA * area, and as such this kind of SMP config may be less * trustworthy, simply because the SMP table may have been - * stomped on during early boot. + * stomped on during early boot. These loaders are buggy and + * should be fixed. */ address = *(unsigned short *)phys_to_virt(0x40E); address<<=4; diff --git a/arch/mips/kernel/irq.c b/arch/mips/kernel/irq.c index b91d7f81efda..b20e92d2f2a6 100644 --- a/arch/mips/kernel/irq.c +++ b/arch/mips/kernel/irq.c @@ -287,7 +287,7 @@ unsigned long probe_irq_on (void) } /* wait for spurious interrupts to mask themselves out again */ - for (delay = jiffies + HZ/10; delay > jiffies; ) + for (delay = jiffies + HZ/10; time_before(jiffies, delay); ) /* about 100ms delay */; /* now filter out any obviously spurious interrupts */ diff --git a/arch/ppc/8xx_io/uart.c b/arch/ppc/8xx_io/uart.c index fdbd0c79693f..94901245fcfe 100644 --- a/arch/ppc/8xx_io/uart.c +++ b/arch/ppc/8xx_io/uart.c @@ -1692,7 +1692,7 @@ static void rs_8xx_wait_until_sent(struct tty_struct *tty, int timeout) schedule_timeout(char_time); if (signal_pending(current)) break; - if (timeout && ((orig_jiffies + timeout) < jiffies)) + if (timeout && time_after(jiffies, orig_jiffies + timeout)) break; bdp = info->tx_cur; } while (bdp->cbd_sc & BD_SC_READY); diff --git a/arch/ppc/apus_defconfig b/arch/ppc/apus_defconfig index 1e9499a9c4c3..c9f900cfed0d 100644 --- a/arch/ppc/apus_defconfig +++ b/arch/ppc/apus_defconfig @@ -14,6 +14,7 @@ CONFIG_PMAC=y # CONFIG_ALL_PPC is not set # CONFIG_APUS is not set # CONFIG_MBX is not set +# CONFIG_SMP is not set CONFIG_MACH_SPECIFIC=y # diff --git a/arch/ppc/chrp_defconfig b/arch/ppc/chrp_defconfig index dcaf4b2d54ac..9141b2d908f5 100644 --- a/arch/ppc/chrp_defconfig +++ b/arch/ppc/chrp_defconfig @@ -14,6 +14,7 @@ CONFIG_CHRP=y # CONFIG_ALL_PPC is not set # CONFIG_APUS is not set # CONFIG_MBX is not set +# CONFIG_SMP is not set CONFIG_MACH_SPECIFIC=y # diff --git a/arch/ppc/common_defconfig b/arch/ppc/common_defconfig index 4a5ea33d918c..6cc14e80b762 100644 --- a/arch/ppc/common_defconfig +++ b/arch/ppc/common_defconfig @@ -14,6 +14,7 @@ CONFIG_6xx=y CONFIG_ALL_PPC=y # CONFIG_APUS is not set # CONFIG_MBX is not set +# CONFIG_SMP is not set # # General setup diff --git a/arch/ppc/config.in b/arch/ppc/config.in index 59223a45c462..0378a8e4b97c 100644 --- a/arch/ppc/config.in +++ b/arch/ppc/config.in @@ -22,6 +22,9 @@ choice 'Machine Type' \ if [ "$CONFIG_ALL_PPC" != "y" ];then define_bool CONFIG_MACH_SPECIFIC y fi + +bool 'Symmetric multi-processing support' CONFIG_SMP + endmenu if [ "$CONFIG_MBX" = "y" ];then diff --git a/arch/ppc/defconfig b/arch/ppc/defconfig index ae1303bb4813..b0c9ad966f43 100644 --- a/arch/ppc/defconfig +++ b/arch/ppc/defconfig @@ -14,6 +14,7 @@ CONFIG_PMAC=y # CONFIG_ALL_PPC is not set # CONFIG_APUS is not set # CONFIG_MBX is not set +# CONFIG_SMP is not set CONFIG_MACH_SPECIFIC=y # diff --git a/arch/ppc/kernel/Makefile b/arch/ppc/kernel/Makefile index 0914879f5607..d047c2086d63 100644 --- a/arch/ppc/kernel/Makefile +++ b/arch/ppc/kernel/Makefile @@ -42,7 +42,7 @@ endif endif endif -ifdef SMP +ifdef CONFIG_SMP O_OBJS += smp.o endif diff --git a/arch/ppc/lib/Makefile b/arch/ppc/lib/Makefile index 4cc49de17f37..8ca9a3cd5466 100644 --- a/arch/ppc/lib/Makefile +++ b/arch/ppc/lib/Makefile @@ -8,7 +8,7 @@ O_TARGET = lib.o O_OBJS = checksum.o string.o strcase.o -ifdef SMP +ifdef CONFIG_SMP O_OBJS += locks.o endif diff --git a/arch/ppc/mbx_defconfig b/arch/ppc/mbx_defconfig index 4882740c5d98..54035b866044 100644 --- a/arch/ppc/mbx_defconfig +++ b/arch/ppc/mbx_defconfig @@ -14,6 +14,7 @@ CONFIG_8xx=y # CONFIG_ALL_PPC is not set # CONFIG_APUS is not set CONFIG_MBX=y +CONFIG_SMP=n CONFIG_MACH_SPECIFIC=y CONFIG_SERIAL_CONSOLE=y diff --git a/arch/ppc/pmac_defconfig b/arch/ppc/pmac_defconfig index ae1303bb4813..b0c9ad966f43 100644 --- a/arch/ppc/pmac_defconfig +++ b/arch/ppc/pmac_defconfig @@ -14,6 +14,7 @@ CONFIG_PMAC=y # CONFIG_ALL_PPC is not set # CONFIG_APUS is not set # CONFIG_MBX is not set +# CONFIG_SMP is not set CONFIG_MACH_SPECIFIC=y # diff --git a/arch/ppc/prep_defconfig b/arch/ppc/prep_defconfig index 41db35a4a4a9..14b4ea4a0ffc 100644 --- a/arch/ppc/prep_defconfig +++ b/arch/ppc/prep_defconfig @@ -14,6 +14,7 @@ CONFIG_PREP=y # CONFIG_ALL_PPC is not set # CONFIG_APUS is not set # CONFIG_MBX is not set +# CONFIG_SMP is not set CONFIG_MACH_SPECIFIC=y # diff --git a/arch/sparc/ap1000/util.c b/arch/sparc/ap1000/util.c index abb51426e402..079c9f4c0db6 100644 --- a/arch/sparc/ap1000/util.c +++ b/arch/sparc/ap1000/util.c @@ -393,7 +393,7 @@ void ap_nfs_hook(unsigned long server) unsigned end = jiffies + 20*HZ; /* we are booting from another cell */ printk("waiting for the master cell\n"); - while (jiffies < end) ; + while (time_before(jiffies, end)) ; printk("continuing\n"); } } diff --git a/drivers/acorn/block/fd1772.c b/drivers/acorn/block/fd1772.c index a92320305539..9597bd51aeb1 100644 --- a/drivers/acorn/block/fd1772.c +++ b/drivers/acorn/block/fd1772.c @@ -1090,7 +1090,7 @@ static void finish_fdc_done(int dummy) NeedSeek = 0; if ((timer_active & (1 << FLOPPY_TIMER)) && - timer_table[FLOPPY_TIMER].expires < jiffies + 5) + time_after(jiffies + 5, timer_table[FLOPPY_TIMER].expires)) /* If the check for a disk change is done too early after this * last seek command, the WP bit still reads wrong :-(( */ @@ -1424,7 +1424,7 @@ static int fd_test_drive_present(int drive) FDC1772_WRITE(FDC1772REG_CMD, FDC1772CMD_RESTORE | FDC1772CMDADD_H | FDC1772STEP_6); /*printk("fd_test_drive_present: Going into timeout loop\n"); */ - for (ok = 0, timeout = jiffies + 2 * HZ + HZ / 2; jiffies < timeout;) { + for (ok = 0, timeout = jiffies + 2 * HZ + HZ / 2; time_before(jiffies, timeout);) { /* What does this piece of atariism do? - query for an interrupt? */ /* if (!(mfp.par_dt_reg & 0x20)) break; */ diff --git a/drivers/acorn/net/ether1.c b/drivers/acorn/net/ether1.c index f57cb7ffef6a..1d2283f3d9b1 100644 --- a/drivers/acorn/net/ether1.c +++ b/drivers/acorn/net/ether1.c @@ -519,7 +519,7 @@ ether1_init_for_open (struct device *dev) /* 586 should now unset iscp.busy */ i = jiffies + HZ/2; while (ether1_inw (dev, ISCP_ADDR, iscp_t, iscp_busy, DISABLEIRQS) == 1) { - if (jiffies > i) { + if (time_after(jiffies, i)) { printk (KERN_WARNING "%s: can't initialise 82586: iscp is busy\n", dev->name); return 1; } @@ -529,7 +529,7 @@ ether1_init_for_open (struct device *dev) i += HZ/10; while (((status = ether1_inw (dev, CFG_ADDR, cfg_t, cfg_status, DISABLEIRQS)) & STAT_COMPLETE) == 0) { - if (jiffies > i) + if (time_after(jiffies, i)) break; } @@ -546,7 +546,7 @@ ether1_init_for_open (struct device *dev) i += HZ/10; while (((status = ether1_inw (dev, SA_ADDR, sa_t, sa_status, DISABLEIRQS)) & STAT_COMPLETE) == 0) { - if (jiffies > i) + if (time_after(jiffies, i)) break; } @@ -563,7 +563,7 @@ ether1_init_for_open (struct device *dev) i += HZ/10; while (((status = ether1_inw (dev, MC_ADDR, mc_t, mc_status, DISABLEIRQS)) & STAT_COMPLETE) == 0) { - if (jiffies > i) + if (time_after(jiffies, i)) break; } @@ -580,7 +580,7 @@ ether1_init_for_open (struct device *dev) i += HZ; while (((status = ether1_inw (dev, TDR_ADDR, tdr_t, tdr_status, DISABLEIRQS)) & STAT_COMPLETE) == 0) { - if (jiffies > i) + if (time_after(jiffies, i)) break; } diff --git a/drivers/acorn/scsi/acornscsi.c b/drivers/acorn/scsi/acornscsi.c index 56aafd46784c..50ec36436b7a 100644 --- a/drivers/acorn/scsi/acornscsi.c +++ b/drivers/acorn/scsi/acornscsi.c @@ -323,7 +323,7 @@ acornscsi_csdelay (unsigned int cs) save_flags (flags); sti (); - while (jiffies < target_jiffies) barrier(); + while (time_before(jiffies, target_jiffies)) barrier(); restore_flags (flags); } diff --git a/drivers/acorn/scsi/fas216.c b/drivers/acorn/scsi/fas216.c index b6ffe08d9ea0..6cd638242847 100644 --- a/drivers/acorn/scsi/fas216.c +++ b/drivers/acorn/scsi/fas216.c @@ -2049,7 +2049,7 @@ int fas216_init(struct Scsi_Host *instance) save_flags(flags); sti(); - while (jiffies < target_jiffies) barrier(); + while (time_before(jiffies, target_jiffies)) barrier(); restore_flags(flags); diff --git a/drivers/ap1000/ddv_util.c b/drivers/ap1000/ddv_util.c index b853a3216b93..d6cf122160d6 100644 --- a/drivers/ap1000/ddv_util.c +++ b/drivers/ap1000/ddv_util.c @@ -92,7 +92,7 @@ int ddv_restart_cpu(void) return(-1); } for (timeout=jiffies + 10; - (jiffies < timeout) || (OPT_IO(PBUF0) == 0); + time_before(jiffies, timeout) || (OPT_IO(PBUF0) == 0); ) /* wait */ ; if (OPT_IO(PBUF0) == 0) { printk("WARNING: option kernel didn't startup\n"); diff --git a/drivers/block/genhd.c b/drivers/block/genhd.c index 7fb8430ee77a..6eb8cfa16335 100644 --- a/drivers/block/genhd.c +++ b/drivers/block/genhd.c @@ -317,11 +317,50 @@ solaris_x86_partition(struct gendisk *hd, kdev_t dev, long offset) { #endif #ifdef CONFIG_BSD_DISKLABEL +static void check_and_add_bsd_partition(struct gendisk *hd, struct bsd_partition *bsd_p) +{ + struct hd_struct *lin_p; + /* check relative position of partitions. */ + for (lin_p = hd->part + 1; lin_p - hd->part < current_minor; lin_p++) { + /* no relationship -> try again */ + if (lin_p->start_sect + lin_p->nr_sects <= bsd_p->p_offset + || lin_p->start_sect >= bsd_p->p_offset + bsd_p->p_size) + continue; + /* equal -> no need to add */ + if (lin_p->start_sect == bsd_p->p_offset && + lin_p->nr_sects == bsd_p->p_size) + return; + /* bsd living within dos partition */ + if (lin_p->start_sect <= bsd_p->p_offset && lin_p->start_sect + + lin_p->nr_sects >= bsd_p->p_offset + bsd_p->p_size) { +#ifdef DEBUG_BSD_DISKLABEL + printk("w: %d %ld+%ld,%d+%d", + lin_p - hd->part, + lin_p->start_sect, lin_p->nr_sects, + bsd_p->p_offset, bsd_p->p_size); +#endif + break; + } + /* ouch: bsd and linux overlap. Don't even try for that partition */ +#ifdef DEBUG_BSD_DISKLABEL + printk("???: %d %ld+%ld,%d+%d", + lin_p - hd->part, lin_p->start_sect, lin_p->nr_sects, + bsd_p->p_offset, bsd_p->p_size); +#endif + printk("???"); + return; + } /* if the bsd partition is not currently known to linux, we end + * up here + */ + add_partition(hd, current_minor, bsd_p->p_offset, bsd_p->p_size); + current_minor++; +} /* * Create devices for BSD partitions listed in a disklabel, under a * dos-like partition. See extended_partition() for more information. */ -static void bsd_disklabel_partition(struct gendisk *hd, kdev_t dev) +static void bsd_disklabel_partition(struct gendisk *hd, kdev_t dev, + int max_partitions) { struct buffer_head *bh; struct bsd_disklabel *l; @@ -337,19 +376,56 @@ static void bsd_disklabel_partition(struct gendisk *hd, kdev_t dev) return; } - p = &l->d_partitions[0]; - while (p - &l->d_partitions[0] <= BSD_MAXPARTITIONS) { + if (l->d_npartitions < max_partitions) + max_partitions = l->d_npartitions; + for (p = l->d_partitions; p - l->d_partitions < max_partitions; p++) { if ((current_minor & mask) >= (4 + hd->max_p)) break; - if (p->p_fstype != BSD_FS_UNUSED) { - add_partition(hd, current_minor, p->p_offset, p->p_size); + if (p->p_fstype != BSD_FS_UNUSED) + check_and_add_bsd_partition(hd, p); + } + brelse(bh); + +} +#endif + +#ifdef CONFIG_UNIXWARE_DISKLABEL +/* + * Create devices for Unixware partitions listed in a disklabel, under a + * dos-like partition. See extended_partition() for more information. + */ +static void unixware_partition(struct gendisk *hd, kdev_t dev) +{ + struct buffer_head *bh; + struct unixware_disklabel *l; + struct unixware_slice *p; + int mask = (1 << hd->minor_shift) - 1; + + if (!(bh = bread(dev, 14, get_ptable_blocksize(dev)))) + return; + bh->b_state = 0; + l = (struct unixware_disklabel *) (bh->b_data+512); + if (le32_to_cpu(l->d_magic) != UNIXWARE_DISKMAGIC || + le32_to_cpu(l->vtoc.v_magic) != UNIXWARE_DISKMAGIC2) { + brelse(bh); + return; + } + printk(" vtoc.v_slice[1]; + /* I omit the 0th slice as it is the same as whole disk. */ + while (p - &l->vtoc.v_slice[0] < UNIXWARE_NUMSLICE) { + if ((current_minor & mask) == 0) + break; + + if (p->s_label != UNIXWARE_FS_UNUSED) { + add_partition(hd, current_minor, START_SECT(p), NR_SECTS(p)); current_minor++; } p++; } brelse(bh); - + printk(" >"); } #endif @@ -360,6 +436,11 @@ static int msdos_partition(struct gendisk *hd, kdev_t dev, unsigned long first_s struct partition *p; unsigned char *data; int mask = (1 << hd->minor_shift) - 1; +#ifdef CONFIG_BSD_DISKLABEL + /* no bsd disklabel as a default */ + kdev_t bsd_kdev = 0; + int bsd_maxpart; +#endif #ifdef CONFIG_BLK_DEV_IDE int tested_for_xlate = 0; @@ -476,12 +557,25 @@ check_table: hd->part[minor].nr_sects = 2; } #ifdef CONFIG_BSD_DISKLABEL + /* tag first disklabel for late recognition */ if (SYS_IND(p) == BSD_PARTITION) { - printk(" <"); - bsd_disklabel_partition(hd, MKDEV(hd->major, minor)); - printk(" >"); + printk("!"); + if (!bsd_kdev) { + bsd_kdev = MKDEV(hd->major, minor); + bsd_maxpart = BSD_MAXPARTITIONS; + } + } else if (SYS_IND(p) == OPENBSD_PARTITION) { + printk("!"); + if (!bsd_kdev) { + bsd_kdev = MKDEV(hd->major, minor); + bsd_maxpart = OPENBSD_MAXPARTITIONS; + } } #endif +#ifdef CONFIG_UNIXWARE_DISKLABEL + if (SYS_IND(p) == UNIXWARE_PARTITION) + unixware_partition(hd, MKDEV(hd->major, minor)); +#endif #ifdef CONFIG_SOLARIS_X86_PARTITION /* james@bpgc.com: Solaris has a nasty indicator: 0x82 @@ -495,6 +589,13 @@ check_table: } #endif } +#ifdef CONFIG_BSD_DISKLABEL + if (bsd_kdev) { + printk(" <"); + bsd_disklabel_partition(hd, bsd_kdev, bsd_maxpart); + printk(" >"); + } +#endif /* * Check for old-style Disk Manager partition table */ diff --git a/drivers/block/ide-cd.c b/drivers/block/ide-cd.c index 2231f56937b1..ebd77992f025 100644 --- a/drivers/block/ide-cd.c +++ b/drivers/block/ide-cd.c @@ -1,4 +1,3 @@ -#define VERBOSE_IDE_CD_ERRORS 1 /* * linux/drivers/block/ide-cd.c * Copyright (C) 1994, 1995, 1996 scott snyder @@ -28,7 +27,6 @@ * This will allow us to get automagically notified when the media changes * on ATAPI drives (something the stock ATAPI spec is lacking). Looks * very cool. I discovered its existance the other day at work... - * -Fix ide_cdrom_reset so that it works (it does nothing right now) * -Query the drive to find what features are available before trying to * use them (like trying to close the tray in drives that can't). * -Make it so that Pioneer CD DR-A24X and friends don't get screwed up on @@ -36,9 +34,6 @@ * -Handle older drives that can't report their speed. (i.e. check if they * support a version of ATAPI where they can report their speed before * checking their speed and believing what they return). - * -It seems we do not always honor it when Uniform gets a request to change - * the cdi->options. We should _always_ check the options before doing stuff. - * This must be fixed. * * * ---------------------------------- @@ -226,9 +221,16 @@ * Jens Axboe * Chris Zwilling * + * 4.51 Dec 23, 1998 -- Jens Axboe + * - ide_cdrom_reset enabled since the ide subsystem + * handles resets fine now. + * - Transfer size fix for Samsung CD-ROMs, thanks to + * "Ville Hallik" . + * - other minor stuff. + * *************************************************************************/ -#define IDECD_VERSION "4.50" +#define IDECD_VERSION "4.51" #include #include @@ -456,7 +458,7 @@ static void cdrom_queue_request_sense (ide_drive_t *drive, len *= 4; pc->c[0] = REQUEST_SENSE; - pc->c[4] = len; + pc->c[4] = (unsigned char) len; pc->buffer = (char *)reqbuf; pc->buflen = len; pc->sense_data = (struct atapi_request_sense *)failed_command; @@ -856,7 +858,12 @@ static void cdrom_read_intr (ide_drive_t *drive) if ((len % SECTOR_SIZE) != 0) { printk ("%s: cdrom_read_intr: Bad transfer size %d\n", drive->name, len); - printk (" This drive is not supported by this version of the driver\n"); + if (CDROM_CONFIG_FLAGS (drive)->limit_nframes) + printk (" This drive is not supported by this version of the driver\n"); + else { + printk (" Trying to limit transfer sizes\n"); + CDROM_CONFIG_FLAGS (drive)->limit_nframes = 1; + } cdrom_end_request (0, drive); return; } @@ -992,7 +999,6 @@ static void cdrom_start_read_continuation (ide_drive_t *drive) { struct packet_command pc; struct request *rq = HWGROUP(drive)->rq; - int nsect, sector, nframes, frame, nskip; /* Number of sectors to transfer. */ @@ -1029,8 +1035,10 @@ static void cdrom_start_read_continuation (ide_drive_t *drive) nframes = (nsect + SECTORS_PER_FRAME-1) / SECTORS_PER_FRAME; frame = sector / SECTORS_PER_FRAME; - /* Largest number of frames was can transfer at once is 64k-1. */ - nframes = MIN (nframes, 65535); + /* Largest number of frames was can transfer at once is 64k-1. For + some drives we need to limit this even more. */ + nframes = MIN (nframes, (CDROM_CONFIG_FLAGS (drive)->limit_nframes) ? + (65534 / CD_FRAMESIZE) : 65535); /* Set up the command */ memset (&pc.c, 0, sizeof (pc.c)); @@ -1328,7 +1336,7 @@ int cdrom_queue_packet_command (ide_drive_t *drive, struct packet_command *pc) struct atapi_request_sense *reqbuf = pc->sense_data; if (reqbuf->sense_key == UNIT_ATTENTION) - ; + cdrom_saw_media_change (drive); else if (reqbuf->sense_key == NOT_READY && reqbuf->asc == 4) { /* The drive is in the process of loading @@ -2477,19 +2485,12 @@ static int ide_cdrom_reset (struct cdrom_device_info *cdi) { -/* This doesn't work reliably yet, and so it is currently just a stub. */ - -#if 0 ide_drive_t *drive = (ide_drive_t*) cdi->handle; struct request req; + ide_init_drive_cmd (&req); req.cmd = RESET_DRIVE_COMMAND; return ide_do_drive_cmd (drive, &req, ide_wait); -#endif - -/* For now, just return 0, as if things had worked... */ - return 0; - } @@ -2916,10 +2917,10 @@ static void ide_cdrom_add_settings(ide_drive_t *drive) int major = HWIF(drive)->major; int minor = drive->select.b.unit << PARTN_BITS; - ide_add_setting(drive, "breada_readahead", SETTING_RW, BLKRAGET, BLKRASET, TYPE_INT, 0, 255, 1, 2, &read_ahead[major], NULL); - ide_add_setting(drive, "file_readahead", SETTING_RW, BLKFRAGET, BLKFRASET, TYPE_INTA, 0, INT_MAX, 1, 1024, &max_readahead[major][minor], NULL); - ide_add_setting(drive, "max_kb_per_request", SETTING_RW, BLKSECTGET, BLKSECTSET, TYPE_INTA, 1, 255, 1, 2, &max_sectors[major][minor], NULL); - ide_add_setting(drive, "dsc_overlap", SETTING_RW, -1, -1, TYPE_BYTE, 0, 1, 1, 1, &drive->dsc_overlap, NULL); + ide_add_setting(drive, "breada_readahead", SETTING_RW, BLKRAGET, BLKRASET, TYPE_INT, 0, 255, 1, 2, &read_ahead[major], NULL); + ide_add_setting(drive, "file_readahead", SETTING_RW, BLKFRAGET, BLKFRASET, TYPE_INTA, 0, INT_MAX, 1, 1024, &max_readahead[major][minor], NULL); + ide_add_setting(drive, "max_kb_per_request", SETTING_RW, BLKSECTGET, BLKSECTSET, TYPE_INTA, 1, 255, 1, 2, &max_sectors[major][minor], NULL); + ide_add_setting(drive, "dsc_overlap", SETTING_RW, -1, -1, TYPE_BYTE, 0, 1, 1, 1, &drive->dsc_overlap, NULL); } static @@ -2959,6 +2960,13 @@ int ide_cdrom_setup (ide_drive_t *drive) CDROM_CONFIG_FLAGS (drive)->cd_rw = 0; CDROM_CONFIG_FLAGS (drive)->no_eject = 1; CDROM_CONFIG_FLAGS (drive)->supp_disc_present = 0; + + /* limit transfer size per interrupt. currently only one Samsung + drive needs this. */ + CDROM_CONFIG_FLAGS (drive)->limit_nframes = 0; + if (drive->id != NULL) + if (strcmp (drive->id->model, "SAMSUNG CD-ROM SCR-2432") == 0) + CDROM_CONFIG_FLAGS (drive)->limit_nframes = 1; #if ! STANDARD_ATAPI /* by default Sanyo 3 CD changer support is turned off and diff --git a/drivers/block/ide-cd.h b/drivers/block/ide-cd.h index e72777fddd92..93d31c0432f8 100644 --- a/drivers/block/ide-cd.h +++ b/drivers/block/ide-cd.h @@ -14,7 +14,7 @@ memory, though. */ #ifndef VERBOSE_IDE_CD_ERRORS -#define VERBOSE_IDE_CD_ERRORS 0 +#define VERBOSE_IDE_CD_ERRORS 1 #endif @@ -130,6 +130,9 @@ struct ide_cd_config_flags { __u8 cd_rw : 1; /* Drive can write to CD-R/W media . */ __u8 supp_disc_present: 1; /* Changer can report exact contents of slots. */ + __u8 limit_nframes : 1; /* Drive does not provide data in + multiples of SECTOR_SIZE when more + than one interrupt is needed. */ __u8 seeking : 1; /* Seeking in progress */ __u8 reserved : 6; byte max_speed; /* Max speed of the drive */ diff --git a/drivers/block/ide-floppy.c b/drivers/block/ide-floppy.c index e5d48249d166..30c862f11ed3 100644 --- a/drivers/block/ide-floppy.c +++ b/drivers/block/ide-floppy.c @@ -633,6 +633,9 @@ static void idefloppy_end_request (byte uptodate, ide_hwgroup_t *hwgroup) } if (error) floppy->failed_pc = NULL; + /* Why does this happen? */ + if (!rq) + return; if (!IDEFLOPPY_RQ_CMD (rq->cmd)) { ide_end_request (uptodate, hwgroup); return; diff --git a/drivers/block/ide-probe.c b/drivers/block/ide-probe.c index bcaa402216e5..f82f3553ab76 100644 --- a/drivers/block/ide-probe.c +++ b/drivers/block/ide-probe.c @@ -291,7 +291,7 @@ static int do_probe (ide_drive_t *drive, byte cmd) delay_50ms(); OUT_BYTE(WIN_SRST, IDE_COMMAND_REG); timeout = jiffies; - while ((GET_STAT() & BUSY_STAT) && jiffies < timeout + WAIT_WORSTCASE) + while ((GET_STAT() & BUSY_STAT) && time_before(jiffies, timeout + WAIT_WORSTCASE)) delay_50ms(); rc = try_to_identify(drive, cmd); } diff --git a/drivers/block/ll_rw_blk.c b/drivers/block/ll_rw_blk.c index 3d26017566d4..3ef4f81c38f7 100644 --- a/drivers/block/ll_rw_blk.c +++ b/drivers/block/ll_rw_blk.c @@ -649,86 +649,6 @@ void ll_rw_block(int rw, int nr, struct buffer_head * bh[]) return; } -void ll_rw_swap_file(int rw, kdev_t dev, unsigned int *b, int nb, char *buf) -{ - int i, j; - int buffersize; - int max_req; - unsigned long rsector; - kdev_t rdev; - struct request * req[8]; - unsigned int major = MAJOR(dev); - struct semaphore sem = MUTEX_LOCKED; - - if (major >= MAX_BLKDEV || !(blk_dev[major].request_fn)) { - printk(KERN_NOTICE "ll_rw_swap_file: trying to swap to" - " nonexistent block-device\n"); - return; - } - max_req = NR_REQUEST; - switch (rw) { - case READ: - break; - case WRITE: - max_req = (NR_REQUEST * 2) / 3; - if (is_read_only(dev)) { - printk(KERN_NOTICE - "Can't swap to read-only device %s\n", - kdevname(dev)); - return; - } - break; - default: - panic("ll_rw_swap: bad block dev cmd, must be R/W"); - } - buffersize = PAGE_SIZE / nb; - - if ((major == LOOP_MAJOR) || (major == NBD_MAJOR)) - max_req >>= 1; - for (j=0, i=0; i> 9); -#ifdef CONFIG_BLK_DEV_MD - if (major==MD_MAJOR && - md_map (MINOR(dev), &rdev, - &rsector, buffersize >> 9)) { - printk (KERN_ERR - "Bad md_map in ll_rw_swap_file\n"); - return; - } -#endif - - if (j == 0) { - req[j] = get_request_wait(max_req, rdev); - } else { - unsigned long flags; - spin_lock_irqsave(&io_request_lock,flags); - req[j] = get_request(max_req, rdev); - spin_unlock_irqrestore(&io_request_lock,flags); - if (req[j] == NULL) - break; - } - req[j]->cmd = rw; - req[j]->errors = 0; - req[j]->sector = rsector; - req[j]->nr_sectors = buffersize >> 9; - req[j]->current_nr_sectors = buffersize >> 9; - req[j]->buffer = buf; - req[j]->sem = &sem; - req[j]->bh = NULL; - req[j]->next = NULL; - add_request(MAJOR(rdev)+blk_dev,req[j]); - } - run_task_queue(&tq_disk); - while (j > 0) { - j--; - down(&sem); - } - } -} #ifdef CONFIG_STRAM_SWAP extern int stram_device_init( void ); #endif diff --git a/drivers/block/paride/pg.c b/drivers/block/paride/pg.c index 1563a2afc185..89c83db655cf 100644 --- a/drivers/block/paride/pg.c +++ b/drivers/block/paride/pg.c @@ -367,21 +367,21 @@ static int pg_wait( int unit, int go, int stop, int tmo, char * msg ) PG.status = 0; j = 0; - while ((((r=RR(1,6))&go)||(stop&&(!(r&stop))))&&(jiffies=tmo)) { + if ((r&(STAT_ERR&stop))||time_after_eq(jiffies, tmo)) { s = RR(0,7); e = RR(0,1); p = RR(0,2); if (verbose > 1) printk("%s: %s: stat=0x%x err=0x%x phase=%d%s\n", - PG.name,msg,s,e,p,(jiffies>=tmo)?" timeout":""); + PG.name,msg,s,e,p,time_after_eq(jiffies, tmo)?" timeout":""); - if (jiffies>=tmo) e |= 0x100; + if (time_after_eq(jiffies, tmo)) e |= 0x100; PG.status = (e >> 4) & 0xff; return -1; } diff --git a/drivers/block/paride/pseudo.h b/drivers/block/paride/pseudo.h index 13924396cf92..3992f3c3018b 100644 --- a/drivers/block/paride/pseudo.h +++ b/drivers/block/paride/pseudo.h @@ -47,7 +47,7 @@ static int ps_timer_active = 0; static int ps_tq_active = 0; static int ps_nice = 0; -static spinlock_t ps_spinlock = SPIN_LOCK_UNLOCKED; +static spinlock_t ps_spinlock __attribute__((unused)) = SPIN_LOCK_UNLOCKED; static struct timer_list ps_timer = {0,0,0,0,ps_timer_int}; static struct tq_struct ps_tq = {0,0,ps_tq_int,NULL}; diff --git a/drivers/cdrom/cdrom.c b/drivers/cdrom/cdrom.c index 85ed482b87e9..7d063f064161 100644 --- a/drivers/cdrom/cdrom.c +++ b/drivers/cdrom/cdrom.c @@ -87,15 +87,20 @@ Thanks to Grant R. Guenther for spotting this bug. -- Made a few things more pedanticly correct. - 2.50 Oct 19, 1998 - Jens Axboe +2.50 Oct 19, 1998 - Jens Axboe -- New maintainers! Erik was too busy to continue the work on the driver, so now Chris Zwilling and Jens Axboe will do their best to follow in his footsteps + + 2.51 Dec 20, 1998 - Jens Axboe + -- Check if drive is capable of doing what we ask before blindly changing + cdi->options in various ioctl. + -- Added version to proc entry. -------------------------------------------------------------------------*/ -#define REVISION "Revision: 2.50" -#define VERSION "Id: cdrom.c 2.50 1998/10/19" +#define REVISION "Revision: 2.51" +#define VERSION "Id: cdrom.c 2.51 1998/12/20" /* I use an error-log mask to give fine grain control over the type of messages dumped to the system logs. The available masks include: */ @@ -211,6 +216,8 @@ int register_cdrom(struct cdrom_device_info *cdi) struct cdrom_device_ops *cdo = cdi->ops; int *change_capability = (int *)&cdo->capability; /* hack */ + cdinfo(CD_OPEN, "entering register_cdrom\n"); + if (major < 0 || major >= MAX_BLKDEV) return -1; if (cdo->open == NULL || cdo->release == NULL) @@ -236,9 +243,10 @@ int register_cdrom(struct cdrom_device_info *cdi) cdi->mc_flags = 0; cdo->n_minors = 0; cdi->options = CDO_USE_FFLAGS; - if (autoclose==1) + + if (autoclose==1 && cdo->capability & ~cdi->mask & CDC_OPEN_TRAY) cdi->options |= (int) CDO_AUTO_CLOSE; - if (autoeject==1) + if (autoeject==1 && cdo->capability & ~cdi->mask & CDC_OPEN_TRAY) cdi->options |= (int) CDO_AUTO_EJECT; if (lockdoor==1) cdi->options |= (int) CDO_LOCK; @@ -257,6 +265,8 @@ int unregister_cdrom(struct cdrom_device_info *unreg) struct cdrom_device_info *cdi, *prev; int major = MAJOR (unreg->dev); + cdinfo(CD_OPEN, "entering unregister_cdrom\n"); + if (major < 0 || major >= MAX_BLKDEV) return -1; @@ -713,6 +723,8 @@ int cdrom_ioctl(struct inode *ip, struct file *fp, case CDROMEJECT_SW: cdinfo(CD_DO_IOCTL, "entering CDROMEJECT_SW\n"); + if (!(cdo->capability & ~cdi->mask & CDC_OPEN_TRAY)) + return -ENOSYS; cdi->options &= ~(CDO_AUTO_CLOSE | CDO_AUTO_EJECT); if (arg) cdi->options |= CDO_AUTO_CLOSE | CDO_AUTO_EJECT; @@ -733,6 +745,8 @@ int cdrom_ioctl(struct inode *ip, struct file *fp, case CDROM_SET_OPTIONS: cdinfo(CD_DO_IOCTL, "entering CDROM_SET_OPTIONS\n"); + if (cdo->capability & arg & ~cdi->mask) + return -ENOSYS; cdi->options |= (int) arg; return cdi->options; @@ -984,7 +998,7 @@ int cdrom_sysctl_info(ctl_table *ctl, int write, struct file * filp, int retv,pos; struct cdrom_device_info *cdi; - pos = sprintf(cdrom_drive_info, "CD-ROM information\n"); + pos = sprintf(cdrom_drive_info, "CD-ROM information, " VERSION "\n"); pos += sprintf(cdrom_drive_info+pos, "\ndrive name:\t"); for (cdi=topCdromPtr;cdi!=NULL;cdi=cdi->next) diff --git a/drivers/char/Config.in b/drivers/char/Config.in index 6fb352f15564..d3933e72d39e 100644 --- a/drivers/char/Config.in +++ b/drivers/char/Config.in @@ -56,12 +56,15 @@ fi bool 'Mouse Support (not serial mice)' CONFIG_MOUSE if [ "$CONFIG_MOUSE" = "y" ]; then + mainmenu_option next_comment + comment 'Mice' tristate 'ATIXL busmouse support' CONFIG_ATIXL_BUSMOUSE tristate 'Logitech busmouse support' CONFIG_BUSMOUSE tristate 'Microsoft busmouse support' CONFIG_MS_BUSMOUSE bool 'PS/2 mouse (aka "auxiliary device") support' CONFIG_PSMOUSE tristate 'C&T 82C710 mouse port support (as on TI Travelmate)' CONFIG_82C710_MOUSE tristate 'PC110 digitizer pad support' CONFIG_PC110_PAD + endmenu fi tristate 'QIC-02 tape support' CONFIG_QIC02_TAPE @@ -72,12 +75,14 @@ if [ "$CONFIG_QIC02_TAPE" != "n" ]; then else comment ' Setting runtime QIC-02 configuration is done with qic02conf' comment ' from the tpqic02-support package. It is available at' - comment ' sunsite.unc.edu or ftp://titus.cfw.com/pub/Linux/util/' + comment ' metalab.unc.edu or ftp://titus.cfw.com/pub/Linux/util/' fi fi bool 'Watchdog Timer Support' CONFIG_WATCHDOG if [ "$CONFIG_WATCHDOG" != "n" ]; then + mainmenu_option next_comment + comment 'Watchdog Cards' bool ' Disable watchdog shutdown on close' CONFIG_WATCHDOG_NOWAYOUT tristate ' WDT Watchdog timer' CONFIG_WDT if [ "$CONFIG_WDT" != "n" ]; then @@ -89,12 +94,19 @@ if [ "$CONFIG_WATCHDOG" != "n" ]; then tristate ' Software Watchdog' CONFIG_SOFT_WATCHDOG tristate ' Berkshire Products PC Watchdog' CONFIG_PCWATCHDOG tristate ' Acquire SBC Watchdog Timer' CONFIG_ACQUIRE_WDT + endmenu fi + + +tristate '/dev/nvram support' CONFIG_NVRAM bool 'Enhanced Real Time Clock Support' CONFIG_RTC if [ "$CONFIG_ALPHA_BOOK1" = "y" ]; then bool 'Tadpole ANA H8 Support' CONFIG_H8 fi +mainmenu_option next_comment +comment 'Video For Linux' + tristate 'Video For Linux' CONFIG_VIDEO_DEV if [ "$CONFIG_VIDEO_DEV" != "n" ]; then dep_tristate 'AIMSlab RadioTrack (aka RadioReveal) support' CONFIG_RADIO_RTRACK $CONFIG_VIDEO_DEV @@ -110,6 +122,10 @@ if [ "$CONFIG_VIDEO_DEV" != "n" ]; then hex ' Aztech/Packard Bell I/O port (0x350 or 0x358)' CONFIG_RADIO_AZTECH_PORT 350 fi dep_tristate 'Miro PCM20 Radio' CONFIG_RADIO_MIROPCM20 $CONFIG_VIDEO_DEV + dep_tristate 'GemTek Radio Card support' CONFIG_RADIO_GEMTEK $CONFIG_VIDEO_DEV + if [ "$CONFIG_RADIO_GEMTEK" = "y" ]; then + hex ' GemTek i/o port (0x20c, 0x30c, 0x24c or 0x34c)' CONFIG_RADIO_GEMTEK_PORT 34c + fi if [ "$CONFIG_PCI" != "n" ]; then dep_tristate 'BT848 Video For Linux' CONFIG_VIDEO_BT848 $CONFIG_VIDEO_DEV fi @@ -128,11 +144,18 @@ if [ "$CONFIG_VIDEO_DEV" != "n" ]; then hex ' ZOLTRIX I/O port (0x20c or 0x30c)' CONFIG_RADIO_ZOLTRIX_PORT 20c fi fi -tristate '/dev/nvram support' CONFIG_NVRAM + +endmenu + +mainmenu_option next_comment +comment 'Joystick support' + tristate 'Joystick support' CONFIG_JOYSTICK if [ "$CONFIG_JOYSTICK" != "n" ]; then source drivers/char/joystick/Config.in fi +endmenu + mainmenu_option next_comment comment 'Ftape, the floppy tape device driver' tristate 'Ftape (QIC-80/Travan) support' CONFIG_FTAPE diff --git a/drivers/char/Makefile b/drivers/char/Makefile index ad7e1f9986e8..b38c4e5f14ba 100644 --- a/drivers/char/Makefile +++ b/drivers/char/Makefile @@ -380,6 +380,14 @@ else endif endif +ifeq ($(CONFIG_RADIO_GEMTEK),y) +L_OBJS += radio-gemtek.o +else + ifeq ($(CONFIG_RADIO_GEMTEK),m) + M_OBJS += radio-gemtek.o + endif +endif + ifeq ($(CONFIG_QIC02_TAPE),y) L_OBJS += tpqic02.o else diff --git a/drivers/char/isicom.c b/drivers/char/isicom.c index 1ccf11bc5bbe..58ce881b30e5 100644 --- a/drivers/char/isicom.c +++ b/drivers/char/isicom.c @@ -152,12 +152,12 @@ static int ISILoad_ioctl(struct inode *inode, struct file *filp, inw(base+0x8); - for(i=jiffies+HZ/100;i>jiffies;); + for(i=jiffies+HZ/100;time_before(jiffies, i);); outw(0,base+0x8); /* Reset */ for(j=1;j<=3;j++) { - for(i=jiffies+HZ;i>jiffies;); + for(i=jiffies+HZ;time_before(jiffies, i);); printk("."); } signature=(inw(base+0x4)) & 0xff; diff --git a/drivers/char/radio-gemtek.c b/drivers/char/radio-gemtek.c new file mode 100644 index 000000000000..1bfe30e30b9c --- /dev/null +++ b/drivers/char/radio-gemtek.c @@ -0,0 +1,310 @@ +/* GemTek radio card driver for Linux (C) 1998 Jonas Munsin + * + * GemTek hasn't released any specs on the card, so the protocol had to + * be reverse engineered with dosemu. + * + * Besides the protocol changes, this is mostly a copy of: + * + * RadioTrack II driver for Linux radio support (C) 1998 Ben Pfaff + * + * Based on RadioTrack I/RadioReveal (C) 1997 M. Kirkwood + * Coverted to new API by Alan Cox + * Various bugfixes and enhancements by Russell Kroll + * + * TODO: Allow for more than one of these foolish entities :-) + * + */ + +#include /* Modules */ +#include /* Initdata */ +#include /* check_region, request_region */ +#include /* udelay */ +#include /* outb, outb_p */ +#include /* copy to/from user */ +#include /* kernel radio structs */ +#include /* CONFIG_RADIO_GEMTEK_PORT */ + +#ifndef CONFIG_RADIO_GEMTEK_PORT +#define CONFIG_RADIO_GEMTEK_PORT -1 +#endif + +static int io = CONFIG_RADIO_GEMTEK_PORT; +static int users = 0; + +struct gemtek_device +{ + int port; + unsigned long curfreq; + int muted; +}; + + +/* local things */ + +/* the correct way to mute the gemtek may be to write the last written + * frequency || 0x10, but just writing 0x10 once seems to do it as well + */ +static void gemtek_mute(struct gemtek_device *dev) +{ + if(dev->muted) + return; + outb(0x10, io); + dev->muted = 1; +} + +static void gemtek_unmute(struct gemtek_device *dev) +{ + if(dev->muted == 0) + return; + outb(0x20, io); + dev->muted = 0; +} + +static void zero(void) +{ + outb_p(0x04, io); + udelay(5); + outb_p(0x05, io); + udelay(5); +} + +static void one(void) +{ + outb_p(0x06, io); + udelay(5); + outb_p(0x07, io); + udelay(5); +} + +static int gemtek_setfreq(struct gemtek_device *dev, unsigned long freq) +{ + int i; + +/* freq = 78.25*((float)freq/16000.0 + 10.52); */ + + freq /= 16; + freq += 10520; + freq *= 7825; + freq /= 100000; + + /* 2 start bits */ + outb_p(0x03, io); + udelay(5); + outb_p(0x07, io); + udelay(5); + + /* 28 frequency bits (lsb first) */ + for (i = 0; i < 14; i++) + if (freq & (1 << i)) + one(); + else + zero(); + /* 36 unknown bits */ + for (i = 0; i < 11; i++) + zero(); + one(); + for (i = 0; i < 4; i++) + zero(); + one(); + zero(); + + /* 2 end bits */ + outb_p(0x03, io); + udelay(5); + outb_p(0x07, io); + udelay(5); + + return 0; +} + +int gemtek_getsigstr(struct gemtek_device *dev) +{ + inb(io); + udelay(5); + if (inb(io) & 8) /* bit set = no signal present */ + return 0; + return 1; /* signal present */ +} + +static int gemtek_ioctl(struct video_device *dev, unsigned int cmd, void *arg) +{ + struct gemtek_device *rt=dev->priv; + + switch(cmd) + { + case VIDIOCGCAP: + { + struct video_capability v; + v.type=VID_TYPE_TUNER; + v.channels=1; + v.audios=1; + /* No we don't do pictures */ + v.maxwidth=0; + v.maxheight=0; + v.minwidth=0; + v.minheight=0; + strcpy(v.name, "GemTek"); + if(copy_to_user(arg,&v,sizeof(v))) + return -EFAULT; + return 0; + } + case VIDIOCGTUNER: + { + struct video_tuner v; + if(copy_from_user(&v, arg,sizeof(v))!=0) + return -EFAULT; + if(v.tuner) /* Only 1 tuner */ + return -EINVAL; + v.rangelow=87*16000; + v.rangehigh=108*16000; + v.flags=VIDEO_TUNER_LOW; + v.mode=VIDEO_MODE_AUTO; + v.signal=0xFFFF*gemtek_getsigstr(rt); + if(copy_to_user(arg,&v, sizeof(v))) + return -EFAULT; + return 0; + } + case VIDIOCSTUNER: + { + struct video_tuner v; + if(copy_from_user(&v, arg, sizeof(v))) + return -EFAULT; + if(v.tuner!=0) + return -EINVAL; + /* Only 1 tuner so no setting needed ! */ + return 0; + } + case VIDIOCGFREQ: + if(copy_to_user(arg, &rt->curfreq, sizeof(rt->curfreq))) + return -EFAULT; + return 0; + case VIDIOCSFREQ: + if(copy_from_user(&rt->curfreq, arg,sizeof(rt->curfreq))) + return -EFAULT; + /* needs to be called twice in order for getsigstr to work */ + gemtek_setfreq(rt, rt->curfreq); + gemtek_setfreq(rt, rt->curfreq); + return 0; + case VIDIOCGAUDIO: + { + struct video_audio v; + memset(&v,0, sizeof(v)); + v.flags|=VIDEO_AUDIO_MUTABLE; + v.volume=1; + v.step=65535; + strcpy(v.name, "Radio"); + if(copy_to_user(arg,&v, sizeof(v))) + return -EFAULT; + return 0; + } + case VIDIOCSAUDIO: + { + struct video_audio v; + if(copy_from_user(&v, arg, sizeof(v))) + return -EFAULT; + if(v.audio) + return -EINVAL; + + if(v.flags&VIDEO_AUDIO_MUTE) + gemtek_mute(rt); + else + gemtek_unmute(rt); + + return 0; + } + default: + return -ENOIOCTLCMD; + } +} + +static int gemtek_open(struct video_device *dev, int flags) +{ + if(users) + return -EBUSY; + users++; + MOD_INC_USE_COUNT; + return 0; +} + +static void gemtek_close(struct video_device *dev) +{ + users--; + MOD_DEC_USE_COUNT; +} + +static struct gemtek_device gemtek_unit; + +static struct video_device gemtek_radio= +{ + "GemTek radio", + VID_TYPE_TUNER, + VID_HARDWARE_GEMTEK, + gemtek_open, + gemtek_close, + NULL, /* Can't read (no capture ability) */ + NULL, /* Can't write */ + NULL, /* Can't poll */ + gemtek_ioctl, + NULL, + NULL +}; + +__initfunc(int gemtek_init(struct video_init *v)) +{ + if (check_region(io, 4)) + { + printk(KERN_ERR "gemtek: port 0x%x already in use\n", io); + return -EBUSY; + } + + gemtek_radio.priv=&gemtek_unit; + + if(video_register_device(&gemtek_radio, VFL_TYPE_RADIO)==-1) + return -EINVAL; + + request_region(io, 4, "gemtek"); + printk(KERN_INFO "GemTek Radio Card driver.\n"); + + /* mute card - prevents noisy bootups */ + outb(0x10, io); + udelay(5); + gemtek_unit.muted = 1; + + /* this is _maybe_ unnecessary */ + outb(0x01, io); + + return 0; +} + +#ifdef MODULE + +MODULE_AUTHOR("Jonas Munsin"); +MODULE_DESCRIPTION("A driver for the GemTek Radio Card"); +MODULE_PARM(io, "i"); +MODULE_PARM_DESC(io, "I/O address of the GemTek card (0x20c, 0x30c, 0x24c or 0x34c)"); + +EXPORT_NO_SYMBOLS; + +int init_module(void) +{ + if(io==-1) + { + printk(KERN_ERR "You must set an I/O address with io=0x20c, io=0x30c, io=0x24c or io=0x34c\n"); + return -EINVAL; + } + return gemtek_init(NULL); +} + +void cleanup_module(void) +{ + video_unregister_device(&gemtek_radio); + release_region(io,4); +} + +#endif + +/* + Local variables: + compile-command: "gcc -c -DMODVERSIONS -D__KERNEL__ -DMODULE -O6 -Wall -Wstrict-prototypes -I /home/blp/tmp/linux-2.1.111-rtrack/include radio-rtrack2.c" + End: +*/ diff --git a/drivers/char/serial.c b/drivers/char/serial.c index f4101d133d71..af9d7848d251 100644 --- a/drivers/char/serial.c +++ b/drivers/char/serial.c @@ -2369,7 +2369,7 @@ static void rs_wait_until_sent(struct tty_struct *tty, int timeout) schedule_timeout(char_time); if (signal_pending(current)) break; - if (timeout && ((orig_jiffies + timeout) < jiffies)) + if (timeout && time_after(jiffies, orig_jiffies + timeout)) break; } current->state = TASK_RUNNING; diff --git a/drivers/char/tpqic02.c b/drivers/char/tpqic02.c index 4878d877efc7..30e0260b783b 100644 --- a/drivers/char/tpqic02.c +++ b/drivers/char/tpqic02.c @@ -571,7 +571,7 @@ static int wait_for_ready(time_t timeout) timeout -= spin_t; spin_t += jiffies; - while (((stat = inb_p(QIC02_STAT_PORT) & QIC02_STAT_MASK) == QIC02_STAT_MASK) && (jiffiesstate = TASK_INTERRUPTIBLE; /* nap 0.30 sec between checks, */ diff --git a/drivers/char/videodev.c b/drivers/char/videodev.c index def6e70391f1..36f9b3855e5d 100644 --- a/drivers/char/videodev.c +++ b/drivers/char/videodev.c @@ -68,6 +68,9 @@ extern int fmi_init(struct video_init *); #ifdef CONFIG_RADIO_MIROPCM20 extern int pcm20_init(struct video_init *); #endif +#ifdef CONFIG_RADIO_GEMTEK +extern int gemtek_init(struct video_init *); +#endif #ifdef CONFIG_VIDEO_PMS extern int init_pms_cards(struct video_init *); #endif @@ -103,6 +106,9 @@ static struct video_init video_init_list[]={ #endif #ifdef CONFIG_RADIO_MIROPCM20 {"PCM20", pcm20_init}, +#endif +#ifdef CONFIG_RADIO_GEMTEK + {"GemTek", gemtek_init}, #endif {"end", NULL} }; diff --git a/drivers/isdn/avmb1/b1lli.c b/drivers/isdn/avmb1/b1lli.c index 1c4c0b80671e..db6fe1453fe8 100644 --- a/drivers/isdn/avmb1/b1lli.c +++ b/drivers/isdn/avmb1/b1lli.c @@ -173,7 +173,7 @@ static inline int B1_rx_full(unsigned short base) static inline unsigned char B1_get_byte(unsigned short base) { unsigned long i = jiffies + 5 * HZ; /* maximum wait time 5 sec */ - while (!B1_rx_full(base) && i > jiffies); + while (!B1_rx_full(base) && time_before(jiffies, i)); if (B1_rx_full(base)) return inb(base + B1_READ); printk(KERN_CRIT "b1lli: rx not full after 5 second\n"); @@ -477,7 +477,7 @@ int B1_loaded(unsigned short base) if (loaddebug) printk(KERN_DEBUG "b1capi: loaded: wait 1 ..\n"); - for (i = jiffies + 10 * HZ; i > jiffies;) { + for (i = jiffies + 10 * HZ; time_before(jiffies, i);) { if (B1_tx_empty(base)) break; } @@ -487,7 +487,7 @@ int B1_loaded(unsigned short base) } B1_put_byte(base, SEND_POLL); printk(KERN_DEBUG "b1capi: loaded: wait 2 ..\n"); - for (i = jiffies + 10 * HZ; i > jiffies;) { + for (i = jiffies + 10 * HZ; time_before(jiffies, i);) { if (B1_rx_full(base)) { if ((ans = B1_get_byte(base)) == RECEIVE_POLL) { if (loaddebug) diff --git a/drivers/isdn/hisax/callc.c b/drivers/isdn/hisax/callc.c index 6924e3f9e547..bcd305058ca9 100644 --- a/drivers/isdn/hisax/callc.c +++ b/drivers/isdn/hisax/callc.c @@ -62,7 +62,7 @@ #include "hisax.h" #ifdef MODULE -#define MOD_USE_COUNT ((&__this_module)->usecount) +#define MOD_USE_COUNT ( GET_USE_COUNT (&__this_module)) #endif /* MODULE */ const char *lli_revision = "$Revision: 2.13 $"; @@ -2055,7 +2055,7 @@ HiSax_command(isdn_ctrl * ic) if (csta->channel[0].debug & 0x400) { jiftime(tmp, jiffies); i = strlen(tmp); - sprintf(tmp + i, " LOCK modcnt %lx\n", MOD_USE_COUNT); + sprintf(tmp + i, " LOCK modcnt %d\n", MOD_USE_COUNT); HiSax_putstatus(csta, tmp); } #endif /* MODULE */ @@ -2066,7 +2066,7 @@ HiSax_command(isdn_ctrl * ic) if (csta->channel[0].debug & 0x400) { jiftime(tmp, jiffies); i = strlen(tmp); - sprintf(tmp + i, " UNLOCK modcnt %lx\n", MOD_USE_COUNT); + sprintf(tmp + i, " UNLOCK modcnt %d\n", MOD_USE_COUNT); HiSax_putstatus(csta, tmp); } #endif /* MODULE */ @@ -2128,7 +2128,8 @@ HiSax_command(isdn_ctrl * ic) break; #ifdef MODULE case (55): - MOD_USE_COUNT = 0; + while ( MOD_USE_COUNT > 0) + MOD_DEC_USE_COUNT; HiSax_mod_inc_use_count(); break; #endif /* MODULE */ diff --git a/drivers/macintosh/macserial.c b/drivers/macintosh/macserial.c index 5af8ad871d45..84f88cd75aea 100644 --- a/drivers/macintosh/macserial.c +++ b/drivers/macintosh/macserial.c @@ -1328,7 +1328,7 @@ static void rs_wait_until_sent(struct tty_struct *tty, int timeout) schedule_timeout(char_time); if (signal_pending(current)) break; - if (timeout && ((orig_jiffies + timeout) < jiffies)) + if (timeout && time_after(jiffies, orig_jiffies + timeout)) break; } current->state = TASK_RUNNING; diff --git a/drivers/macintosh/via-pmu.c b/drivers/macintosh/via-pmu.c index b1bb32a28df0..3b027da3f903 100644 --- a/drivers/macintosh/via-pmu.c +++ b/drivers/macintosh/via-pmu.c @@ -894,7 +894,7 @@ int powerbook_sleep(void) pmu_enable_backlight(0); /* Give the disks a little time to actually finish writing */ - for (wait = jiffies + (HZ/4); jiffies < wait; ) + for (wait = jiffies + (HZ/4); time_before(jiffies, wait); ) mb(); /* Disable all interrupts except pmu */ diff --git a/drivers/net/3c523.c b/drivers/net/3c523.c index 13bf1028a5a2..37843e6df594 100644 --- a/drivers/net/3c523.c +++ b/drivers/net/3c523.c @@ -539,7 +539,7 @@ __initfunc(int elmc_probe(struct device *dev)) } dev->mem_end = dev->mem_start + size; /* set mem_end showed by 'ifconfig' */ - ((struct priv *) (dev->priv))->base = phys_to_virt(dev->mem_start + size - 0x01000000); + ((struct priv *) (dev->priv))->base = (unsigned long)phys_to_virt(dev->mem_start + size - 0x01000000); alloc586(dev); elmc_id_reset586(); /* make sure it doesn't generate spurious ints */ diff --git a/drivers/net/Config.in b/drivers/net/Config.in index 4f865b68c15b..aaec2728eef2 100644 --- a/drivers/net/Config.in +++ b/drivers/net/Config.in @@ -224,6 +224,10 @@ fi # dep_tristate 'Comtrol Hostess SV-11 support' CONFIG_HOSTESS_SV11 m # +# The COSA/SRP driver has not been tested as non-modular yet. +# +dep_tristate 'COSA/SRP sync serial boards support' CONFIG_COSA m +# if [ "$CONFIG_WAN_ROUTER" != "n" ]; then bool 'WAN drivers' CONFIG_WAN_DRIVERS if [ "$CONFIG_WAN_DRIVERS" = "y" ]; then diff --git a/drivers/pci/oldproc.c b/drivers/pci/oldproc.c index b52fea887a77..2ecc6c85b708 100644 --- a/drivers/pci/oldproc.c +++ b/drivers/pci/oldproc.c @@ -886,7 +886,7 @@ static int sprint_dev_config(struct pci_dev *dev, char *buf, int size) if (len + 40 > size) { return -1; } - len += sprintf(buf + len, "IRQ %x. ", dev->irq); + len += sprintf(buf + len, "IRQ %d. ", dev->irq); } if (dev->master) { diff --git a/drivers/sbus/char/bpp.c b/drivers/sbus/char/bpp.c index f445a14b2efc..0121a03e7f40 100644 --- a/drivers/sbus/char/bpp.c +++ b/drivers/sbus/char/bpp.c @@ -337,8 +337,8 @@ static int wait_for(unsigned short set, unsigned short clr, * responds real good. The first while loop guesses an expire * time accounting for possible wraparound of jiffies. */ - while (extime <= jiffies) extime = jiffies + 1; - while ( (jiffies < extime) + while (time_after_eq(jiffies, extime) extime = jiffies + 1; + while ( (time_before(jiffies, extime)) && (((pins & set) != set) || ((pins & clr) != 0)) ) { pins = get_pins(minor); } diff --git a/drivers/sbus/char/sab82532.c b/drivers/sbus/char/sab82532.c index 3f0924525477..1ea317726402 100644 --- a/drivers/sbus/char/sab82532.c +++ b/drivers/sbus/char/sab82532.c @@ -1676,7 +1676,7 @@ static void sab82532_wait_until_sent(struct tty_struct *tty, int timeout) schedule_timeout(char_time); if (signal_pending(current)) break; - if (timeout && (orig_jiffies + timeout) < jiffies) + if (timeout && time_after(jiffies, orig_jiffies + timeout)) break; } current->state = TASK_RUNNING; diff --git a/drivers/sbus/char/su.c b/drivers/sbus/char/su.c index b05acc3143e7..b4ab6693f0dc 100644 --- a/drivers/sbus/char/su.c +++ b/drivers/sbus/char/su.c @@ -1818,7 +1818,7 @@ su_wait_until_sent(struct tty_struct *tty, int timeout) schedule_timeout(char_time); if (signal_pending(current)) break; - if (timeout && ((orig_jiffies + timeout) < jiffies)) + if (timeout && time_after(jiffies, orig_jiffies + timeout)) break; } current->state = TASK_RUNNING; diff --git a/drivers/scsi/README.tmscsim b/drivers/scsi/README.tmscsim index b11cd4df2e2f..99ae1e5a71ff 100644 --- a/drivers/scsi/README.tmscsim +++ b/drivers/scsi/README.tmscsim @@ -17,6 +17,7 @@ The tmscsim driver supports PCI SCSI Host Adapters based on the AM53C974 chip. AM53C974 based SCSI adapters include: Tekram DC390, DC390T Dawicontrol 2974 + QLogic Fast! PCI Basic some on-board adapters (This is most probably not a complete list) @@ -44,7 +45,8 @@ The numbering scheme isn't consistent. The first versions went from 1.00 to 1.12, then 1.20a to 1.20t. Finally I decided to use the ncr53c8xx scheme. So the next revisions will be 2.0a to 2.0X (stable), 2.1a to 2.1X (experimental), 2.2a to 2.2X (stable, again) etc. (X = anything between a and z.) If I send -fixes to people for testing, those will have a digit appended, e.g. 2.0a1. +fixes to people for testing, I create intermediate versions with a digit +appended, e.g. 2.0c3. 2. Installation @@ -55,32 +57,36 @@ driver. Of course you have to choose to compile SCSI support and DC390(T) support into your kernel or as module when configuring your kernel for compiling. -If you got an older kernel with an old version of this driver included, you -should copy the files (dc390.h, tmscsim.h, tmscsim.c, scsiiom.c and -README.tmscsim) from this directory to linux/drivers/scsi. You have to -recompile your kernel/module of course. + If you got an old kernel (pre 2.1.127, pre 2.0.37p1) with an old version of + this driver: Get dc390-21125-20b.diff.gz or dc390-2036p21-20b1.diff.gz from + my website and apply the patch. -You should apply the three patches included in dc390-20-kernel.diff -(Applying them: cd /usr/src; patch -p0 <~/dc390-20-kernel.diff) -The patches are against 2.1.103, so you might have to manually resolve -rejections when applying to another kernel version. + If you want to do it manually, you should copy the files (dc390.h, + tmscsim.h, tmscsim.c, scsiiom.c and README.tmscsim) from this directory to + linux/drivers/scsi. You have to recompile your kernel/module of course. -The patches will update the kernel startup code to allow boot parameters to -be passed to the driver, update the Documentation and finally offer you the -possibility to omit the non-DC390 parts of the driver. -(By selecting "Omit support for non DC390" you basically disable the -emulation of a DC390 EEPROM for non DC390 adapters. This saves a few bytes -of memory.) + You should apply the three patches included in dc390-120-kernel.diff + (Applying them: cd /usr/src; patch -p0 <~/dc390-120-kernel.diff) + The patches are against 2.1.125, so you might have to manually resolve + rejections when applying to another kernel version. + + The patches will update the kernel startup code to allow boot parameters to + be passed to the driver, update the Documentation and finally offer you the + possibility to omit the non-DC390 parts of the driver. + (By selecting "Omit support for non DC390" you basically disable the + emulation of a DC390 EEPROM for non DC390 adapters. This saves a few bytes + of memory.) If you got a very old kernel without the tmscsim driver (pre 2.0.31) I recommend upgrading your kernel. However, if you don't want to, please contact me to get the appropriate patches. -Testing a SCSI driver is always a delicate thing to do. The 2.0 driver has + +Upgrading a SCSI driver is always a delicate thing to do. The 2.0 driver has proven stable on many systems, but it's still a good idea to take some precautions. In an ideal world you would have a full backup of your disks. The world isn't ideal and most people don't have full backups (me neither). -So take at least the following two measures: +So take at least the following measures: * make your kernel remount the FS read-only on detecting an error: tune2fs -e remount-ro /dev/sd?? * have copies of your SCSI disk's partition tables on some safe location: @@ -103,18 +109,19 @@ SA_SHIRQ | SA_INTERRUPT. 3.Features ---------- - SCSI - * Tagged queueing + * Tagged command queueing * Sync speed up to 10 MHz * Disconnection * Multiple LUNs - General / Linux interface - * Support for up to 4 adapters. + * Support for up to 4 AM53C974 adapters. * DC390 EEPROM usage or boot/module params * Information via cat /proc/scsi/tmscsim/? * Dynamically configurable by writing to /proc/scsi/tmscsim/? * Dynamic allocation of resources - * SMP support: Adapter specific locks (Linux 2.1.x) + * SMP support: Locking on io_request lock (Linux 2.1/2.2) or adapter + specific locks (Linux 2.3) * Uniform source code for Linux-2.x.y * Support for dyn. addition/removal of devices via add/remove-single-device (Try: echo "scsi add-single-device H C I L" >/proc/scsi/scsi @@ -336,9 +343,7 @@ to further improve its usability: Further investigation on these problems: -* TagQ and Disconnection (Resel: SRB Tag Seleection) -* Problems with IRQ sharing (IO-APIC on SMP Systems) (??) -* Driver crashes with readcdda (xcdroast) +* Driver hangs with sync readcdda (xcdroast) (most probably VIA PCI error) Known problems: @@ -362,12 +367,9 @@ Known problems: Richard Waltham or Doug Ledford , if you want to help further debugging it. * 2.0.35: CD changers (e.g. NAKAMICHI MBR-7.{0,2}) have problems because - the mid-level code doesn't handle BLIST_SINGLELUN correctly. Apply - the patch 2035-scsi-singlelun.diff. Thanks to Chiaki Ishikawa. - I was told that this fix will be in 2.0.36, so you don't need it for - 2.0.36. -[The patch file is contained in the dc390-XXX.tar.gz files which can be found -on the ftp server. See below.] + the mid-level code doesn't handle BLIST_SINGLELUN correctly. There used + to be a patch included here to fix this, but I was told that it is fixed + in 2.0.36. 7. Bug reports, debugging and updates @@ -379,7 +381,7 @@ If you find something, which you believe to be a bug, please report it to me. Please append the output of /proc/scsi/scsi, /proc/scsi/tmscsim/? and maybe the DC390 log messages to the report. -Bug reports should be send to me (Kurt Garloff ) as well +Bug reports should be send to me (Kurt Garloff ) as well as to the linux-scsi list (), as sometimes bugs are caused by the SCSI mid-level code. @@ -391,7 +393,10 @@ AM53C974, the logging might produce log output again, and you might end having your box spending most of its time doing the logging. The latest version of the driver can be found at: -ftp://student.physik.uni-dortmund.de/pub/linux/kernel/dc390/ + http://www.garloff.de/kurt/linux/dc390/ +and + ftp://student.physik.uni-dortmund.de/pub/linux/kernel/dc390/ +(The latter might shut down some day.) 8. Acknowledgements @@ -408,6 +413,6 @@ doing this during early revisions). ------------------------------------------------------------------------- -Written by Kurt Garloff 1998/06/11 -Last updated 1998/10/15, driver revision 2.0b -$Id: README.tmscsim,v 2.4 1998/10/24 08:45:02 garloff Exp $ +Written by Kurt Garloff 1998/06/11 +Last updated 1998/12/25, driver revision 2.0d +$Id: README.tmscsim,v 2.9 1998/12/25 18:04:20 garloff Exp $ diff --git a/drivers/scsi/advansys.c b/drivers/scsi/advansys.c index 10fae9bbd77b..c5c733739015 100644 --- a/drivers/scsi/advansys.c +++ b/drivers/scsi/advansys.c @@ -5785,8 +5785,8 @@ advansys_reset(Scsi_Cmnd *scp, unsigned int reset_flags) } scp->result = HOST_BYTE(DID_ERROR); ret = SCSI_RESET_ERROR; - } else if (jiffies >= boardp->last_reset && - jiffies < (boardp->last_reset + (10 * HZ))) { + } else if (time_after_eq(jiffies, boardp->last_reset) && + time_before(jiffies, boardp->last_reset + (10 * HZ))) { /* * Don't allow a reset to be attempted within 10 seconds * of the last reset. diff --git a/drivers/scsi/dc390.h b/drivers/scsi/dc390.h index b3a30ebe0724..719df770a060 100644 --- a/drivers/scsi/dc390.h +++ b/drivers/scsi/dc390.h @@ -4,7 +4,7 @@ * Description: Device Driver for Tekram DC-390(T) PCI SCSI * * Bus Master Host Adapter * ***********************************************************************/ -/* $Id: dc390.h,v 2.3 1998/10/24 08:45:02 garloff Exp $ */ +/* $Id: dc390.h,v 2.12 1998/12/25 17:33:27 garloff Exp $ */ #include @@ -16,7 +16,7 @@ #define DC390_H #define DC390_BANNER "Tekram DC390/AM53C974" -#define DC390_VERSION "2.0b 1998/10/24" +#define DC390_VERSION "2.0d 1998/12/25" #if defined(HOSTS_C) || defined(MODULE) diff --git a/drivers/scsi/g_NCR5380.c b/drivers/scsi/g_NCR5380.c index d8c0c9e0d1cb..ec1f6edc8569 100644 --- a/drivers/scsi/g_NCR5380.c +++ b/drivers/scsi/g_NCR5380.c @@ -495,7 +495,7 @@ static inline int NCR5380_pread (struct Scsi_Host *instance, unsigned char *dst, dst[start+i] = NCR5380_read(C400_HOST_BUFFER); #else /* implies CONFIG_SCSI_G_NCR5380_MEM */ - memmove(dst+start,NCR53C400_host_buffer+NCR5380_map_name,128); + memcpy(dst+start,NCR53C400_host_buffer+NCR5380_map_name,128); #endif start+=128; blocks--; @@ -516,7 +516,7 @@ static inline int NCR5380_pread (struct Scsi_Host *instance, unsigned char *dst, dst[start+i] = NCR5380_read(C400_HOST_BUFFER); #else /* implies CONFIG_SCSI_G_NCR5380_MEM */ - memmove(dst+start,NCR53C400_host_buffer+NCR5380_map_name,128); + memcpy(dst+start,NCR53C400_host_buffer+NCR5380_map_name,128); #endif start+=128; blocks--; @@ -603,7 +603,7 @@ static inline int NCR5380_pwrite (struct Scsi_Host *instance, unsigned char *src NCR5380_write(C400_HOST_BUFFER, src[start+i]); #else /* implies CONFIG_SCSI_G_NCR5380_MEM */ - memmove(NCR53C400_host_buffer+NCR5380_map_name,src+start,128); + memcpy(NCR53C400_host_buffer+NCR5380_map_name,src+start,128); #endif start+=128; blocks--; @@ -623,7 +623,7 @@ static inline int NCR5380_pwrite (struct Scsi_Host *instance, unsigned char *src NCR5380_write(C400_HOST_BUFFER, src[start+i]); #else /* implies CONFIG_SCSI_G_NCR5380_MEM */ - memmove(NCR53C400_host_buffer+NCR5380_map_name,src+start,128); + memcpy(NCR53C400_host_buffer+NCR5380_map_name,src+start,128); #endif start+=128; blocks--; diff --git a/drivers/scsi/gdth.c b/drivers/scsi/gdth.c index 18a86415561a..9cf73a89441d 100644 --- a/drivers/scsi/gdth.c +++ b/drivers/scsi/gdth.c @@ -268,7 +268,7 @@ static ulong act_ints=0, act_ios=0, act_stats=0, act_rq=0; #endif #define PTR2USHORT(a) (ushort)(ulong)(a) -#define JIFFYWAIT(a) {ulong gdtjf;gdtjf=jiffies+(a);while(gdtjf>jiffies);} +#define JIFFYWAIT(a) {ulong gdtjf;gdtjf=jiffies+(a);while(time_before(jiffies,gdtjf));} #define GDTOFFSOF(a,b) (size_t)&(((a*)0)->b) #define INDEX_OK(i,t) ((i)sense_buffer[2] & 0xe0) - return FAILED; + return SUCCESS; switch (SCpnt->sense_buffer[2] & 0xf) { case NO_SENSE: return SUCCESS; case RECOVERED_ERROR: - return SOFT_ERROR; + return /* SOFT_ERROR */ SUCCESS; case ABORTED_COMMAND: return NEEDS_RETRY; @@ -1212,18 +1212,17 @@ STATIC int scsi_check_sense (Scsi_Cmnd * SCpnt) case COPY_ABORTED: case VOLUME_OVERFLOW: case MISCOMPARE: + return SUCCESS; case MEDIUM_ERROR: - return FAILED; + return NEEDS_RETRY; case ILLEGAL_REQUEST: - return SUCCESS; - case BLANK_CHECK: case DATA_PROTECT: case HARDWARE_ERROR: default: - return FAILED; + return SUCCESS; } } diff --git a/drivers/scsi/scsiiom.c b/drivers/scsi/scsiiom.c index e09e7dc3b01d..4b7d4af49362 100644 --- a/drivers/scsi/scsiiom.c +++ b/drivers/scsi/scsiiom.c @@ -4,7 +4,7 @@ * Description: Device Driver for Tekram DC-390 (T) PCI SCSI * * Bus Master Host Adapter * ***********************************************************************/ -/* $Id: scsiiom.c,v 2.3 1998/10/24 09:10:28 garloff Exp $ */ +/* $Id: scsiiom.c,v 2.15 1998/12/25 17:33:27 garloff Exp $ */ UCHAR dc390_StartSCSI( PACB pACB, PDCB pDCB, PSRB pSRB ) @@ -36,7 +36,7 @@ dc390_StartSCSI( PACB pACB, PDCB pDCB, PSRB pSRB ) DC390_write8 (ScsiFifo, bval); bval1 = SEL_W_ATN; pSRB->SRBState = SRB_START_; - DEBUG1(printk ("DC390: No DisCn, No TagQ (%02x, %02x)\n", bval, bval1);) + DEBUG1(printk (KERN_DEBUG "DC390: No DisCn, No TagQ (%02x, %02x)\n", bval, bval1);) if( pDCB->SyncMode & SYNC_ENABLE ) { if( !(pDCB->IdentifyMsg & 7) || /* LUN == 0 || Cmd != INQUIRY */ @@ -53,21 +53,21 @@ dc390_StartSCSI( PACB pACB, PDCB pDCB, PSRB pSRB ) if(pDCB->SyncMode & EN_TAG_QUEUEING) { DC390_write8 (ScsiFifo, MSG_SIMPLE_QTAG); - DEBUG1(printk ("DC390: %sDisCn, TagQ (%02x, %02x, %08lx)\n", (bval&0x40?"":"No "), bval, SEL_W_ATN3, pDCB->TagMask);) + DEBUG1(printk (KERN_DEBUG "DC390: %sDisCn, TagQ (%02x, %02x, %08lx)\n", (bval&0x40?"":"No "), bval, SEL_W_ATN3, pDCB->TagMask);) bval = 0; wlval = 1; while (wlval & pDCB->TagMask) { bval++; wlval <<= 1; }; pDCB->TagMask |= wlval; DC390_write8 (ScsiFifo, bval); pSRB->TagNumber = bval; - DEBUG1(printk ("DC390: SRB %p (Cmd %li), Tag %02x queued\n", pSRB, pSRB->pcmd->pid, bval);) + DEBUG1(printk (KERN_DEBUG "DC390: SRB %p (Cmd %li), Tag %02x queued\n", pSRB, pSRB->pcmd->pid, bval);) bval1 = SEL_W_ATN3; pSRB->SRBState = SRB_START_; } else /* No TagQ */ { bval1 = SEL_W_ATN; - DEBUG1(printk ("DC390: %sDisCn, No TagQ (%02x, %02x, %08lx)\n", (bval&0x40?"":"No "), bval, bval1, pDCB->TagMask);) + DEBUG1(printk (KERN_DEBUG "DC390: %sDisCn, No TagQ (%02x, %02x, %08lx)\n", (bval&0x40?"":"No "), bval, bval1, pDCB->TagMask);) pSRB->SRBState = SRB_START_; } } @@ -82,7 +82,7 @@ dc390_StartSCSI( PACB pACB, PDCB pDCB, PSRB pSRB ) bval &= 0xBF; /* No DisConn */ DC390_write8 (ScsiFifo, bval); bval1 = SEL_W_ATN; - DEBUG1(printk ("DC390: No DisCn, No TagQ (%02x, %02x)\n", bval, bval1);) + DEBUG1(printk (KERN_DEBUG "DC390: No DisCn, No TagQ (%02x, %02x)\n", bval, bval1);) pSRB->SRBState = SRB_START_; /* ??? */ if( pDCB->SyncMode & SYNC_ENABLE ) @@ -101,13 +101,13 @@ dc390_StartSCSI( PACB pACB, PDCB pDCB, PSRB pSRB ) if(pDCB->SyncMode & EN_TAG_QUEUEING) { pSRB->MsgOutBuf[0] = MSG_SIMPLE_QTAG; - DEBUG1(printk ("DC390: %sDisCn, TagQ (%02x, %02x, %08lx)\n", (bval&0x40?"":"No "), bval, SEL_W_ATN_STOP, pDCB->TagMask);) + DEBUG1(printk (KERN_DEBUG "DC390: %sDisCn, TagQ (%02x, %02x, %08lx)\n", (bval&0x40?"":"No "), bval, SEL_W_ATN_STOP, pDCB->TagMask);) bval = 0; wlval = 1; while (wlval & pDCB->TagMask) { bval++; wlval <<= 1; }; pDCB->TagMask |= wlval; pSRB->TagNumber = bval; - DEBUG1(printk ("DC390: SRB %p (Cmd %li), Tag %02x queued\n", pSRB, pSRB->pcmd->pid, bval);) + DEBUG1(printk (KERN_DEBUG "DC390: SRB %p (Cmd %li), Tag %02x queued\n", pSRB, pSRB->pcmd->pid, bval);) pSRB->MsgOutBuf[1] = bval; pSRB->MsgCnt = 2; bval1 = SEL_W_ATN_STOP; @@ -119,7 +119,7 @@ dc390_StartSCSI( PACB pACB, PDCB pDCB, PSRB pSRB ) pSRB->MsgCnt = 1; pSRB->SRBState = SRB_START_; bval1 = SEL_W_ATN_STOP; - DEBUG1(printk ("DC390: %sDisCn, No TagQ (%02x, %02x, %08lx)\n", (bval&0x40?"":"No "), bval, bval1, pDCB->TagMask);) + DEBUG1(printk (KERN_DEBUG "DC390: %sDisCn, No TagQ (%02x, %02x, %08lx)\n", (bval&0x40?"":"No "), bval, bval1, pDCB->TagMask);) }; } } @@ -134,7 +134,7 @@ dc390_StartSCSI( PACB pACB, PDCB pDCB, PSRB pSRB ) DC390_write8 (ScsiFifo, bval); DC390_write8 (ScsiFifo, sizeof(pSRB->pcmd->sense_buffer)); DC390_write8 (ScsiFifo, bval); - DEBUG1(printk ("DC390: AutoReqSense !\n");) + DEBUG1(printk (KERN_DEBUG "DC390: AutoReqSense !\n");) } else /* write cmnd to bus */ { @@ -150,16 +150,16 @@ dc390_StartSCSI( PACB pACB, PDCB pDCB, PSRB pSRB ) { pSRB->SRBState = SRB_READY; pDCB->TagMask &= ~( 1 << pSRB->TagNumber ); - DEBUG0(printk ("DC390: Interrupt during StartSCSI!\n");) + DEBUG0(printk (KERN_WARNING "DC390: Interrupt during StartSCSI!\n");) return 1; } else { pSRB->ScsiPhase = SCSI_NOP1; DEBUG0(if (pACB->pActiveDCB) \ - printk ("DC390: ActiveDCB != 0\n");) + printk (KERN_WARNING "DC390: ActiveDCB != 0\n");) DEBUG0(if (pDCB->pActiveSRB) \ - printk ("DC390: ActiveSRB != 0\n");) + printk (KERN_WARNING "DC390: ActiveSRB != 0\n");) pACB->pActiveDCB = pDCB; pDCB->pActiveSRB = pSRB; //DC390_write8 (DMA_Cmd, DMA_IDLE_CMD); @@ -183,12 +183,10 @@ dc390_dma_intr (PACB pACB) DEBUG0(PDEVSET1;) DEBUG0(PCI_READ_CONFIG_WORD (PDEV, PCI_STATUS, &pstate);) DEBUG0(if (pstate & (PCI_STATUS_SIG_SYSTEM_ERROR | PCI_STATUS_DETECTED_PARITY))\ - { printk("DC390: PCI state = %04x!\n", pstate); \ + { printk(KERN_WARNING "DC390: PCI state = %04x!\n", pstate); \ PCI_WRITE_CONFIG_WORD (PDEV, PCI_STATUS, (PCI_STATUS_SIG_SYSTEM_ERROR | PCI_STATUS_DETECTED_PARITY));};) - dstate = DC390_read8 (DMA_Status); - DC390_write8 (DMA_Status, dstate); /* clear */ - //DC390_write8 (DMA_Status, DMA_XFER_DONE | DMA_XFER_ABORT | DMA_XFER_ERROR | PCI_MS_ABORT); /* clear */ + dstate = DC390_read8 (DMA_Status); if (! pACB->pActiveDCB || ! pACB->pActiveDCB->pActiveSRB) return dstate; else pSRB = pACB->pActiveDCB->pActiveSRB; @@ -207,12 +205,11 @@ dc390_dma_intr (PACB pACB) { DEBUG1(printk (KERN_DEBUG "DC390: read residual bytes ... \n");) dstate = DC390_read8 (DMA_Status); - DC390_write8 (DMA_Status, dstate); /* clear */ residual = DC390_read8 (CtcReg_Low) | DC390_read8 (CtcReg_Mid) << 8 | DC390_read8 (CtcReg_High) << 16; residual += DC390_read8 (Current_Fifo) & 0x1f; } while (residual && ! (dstate & SCSI_INTERRUPT) && --ctr); - if (!ctr) printk (KERN_CRIT "DC390: dma_intr: DMA aborted unfinished: %06x bytes remain!\n", DC390_read32 (DMA_Wk_ByteCntr)); + if (!ctr) printk (KERN_CRIT "DC390: dma_intr: DMA aborted unfinished: %06x bytes remain!!\n", DC390_read32 (DMA_Wk_ByteCntr)); /* residual = ... */ } else @@ -231,6 +228,7 @@ dc390_dma_intr (PACB pACB) DC390_write8 (DMA_Cmd, DMA_IDLE_CMD); } + dc390_laststatus &= ~0xff000000; dc390_laststatus |= dstate << 24; return dstate; }; #endif @@ -245,14 +243,16 @@ DC390_Interrupt( int irq, void *dev_id, struct pt_regs *regs) UCHAR phase, i; void (*stateV)( PACB, PSRB, PUCHAR ); UCHAR istate, istatus; +#if DMA_INT UCHAR dstatus; +#endif DC390_AFLAGS DC390_IFLAGS DC390_DFLAGS pACB = dc390_pACB_start; if (pACB == 0) { - printk(KERN_ERR "DC390: Interrupt on uninitialized adapter!\n"); + printk(KERN_WARNING "DC390: Interrupt on uninitialized adapter!\n"); return; } DC390_LOCK_DRV; @@ -275,8 +275,8 @@ DC390_Interrupt( int irq, void *dev_id, struct pt_regs *regs) DEBUG1(printk (KERN_DEBUG "sstatus=%02x,", sstatus);) - if( pACB == (PACB )-1) { DC390_UNLOCK_DRV; return; }; - + if( !pACB ) { DC390_UNLOCK_DRV; return; }; + #if DMA_INT DC390_LOCK_IO; DC390_LOCK_ACB; @@ -284,15 +284,17 @@ DC390_Interrupt( int irq, void *dev_id, struct pt_regs *regs) DC390_UNLOCK_ACB; DC390_UNLOCK_IO; - DEBUG1(printk ("dstatus=%02x,", dstatus);) + DEBUG1(printk (KERN_DEBUG "dstatus=%02x,", dstatus);) if (! (dstatus & SCSI_INTERRUPT)) { - DEBUG0(printk ("DC390 Int w/o SCSI actions (only DMA?)\n");) + DEBUG0(printk (KERN_WARNING "DC390 Int w/o SCSI actions (only DMA?)\n");) DC390_UNLOCK_DRV; return; }; #else - dstatus = DC390_read8 (DMA_Status); + //DC390_write32 (DMA_ScsiBusCtrl, WRT_ERASE_DMA_STAT | EN_INT_ON_PCI_ABORT); + //dstatus = DC390_read8 (DMA_Status); + //DC390_write32 (DMA_ScsiBusCtrl, EN_INT_ON_PCI_ABORT); #endif DC390_LOCK_IO; @@ -302,14 +304,15 @@ DC390_Interrupt( int irq, void *dev_id, struct pt_regs *regs) istate = DC390_read8 (Intern_State); istatus = DC390_read8 (INT_Status); /* This clears Scsi_Status, Intern_State and INT_Status ! */ - DEBUG1(printk ("Istatus(Res,Inv,Dis,Serv,Succ,ReS,SelA,Sel)=%02x,",istatus);) - dc390_laststatus = dstatus<<24 | sstatus<<16 | istate<<8 | istatus; + DEBUG1(printk (KERN_INFO "Istatus(Res,Inv,Dis,Serv,Succ,ReS,SelA,Sel)=%02x,",istatus);) + dc390_laststatus &= ~0x00ffffff; + dc390_laststatus |= /* dstatus<<24 | */ sstatus<<16 | istate<<8 | istatus; if (sstatus & ILLEGAL_OP_ERR) - { - printk ("DC390: Illegal Operation detected (%08lx)!\n", dc390_laststatus); - dc390_dumpinfo (pACB, pACB->pActiveDCB, pACB->pActiveDCB->pActiveSRB); - }; + { + printk ("DC390: Illegal Operation detected (%08lx)!\n", dc390_laststatus); + dc390_dumpinfo (pACB, pACB->pActiveDCB, pACB->pActiveDCB->pActiveSRB); + }; if(istatus & DISCONNECTED) { @@ -323,18 +326,6 @@ DC390_Interrupt( int irq, void *dev_id, struct pt_regs *regs) goto unlock; } - if(istatus & INVALID_CMD) - { - dc390_InvalidCmd( pACB ); - goto unlock; - } - - if(istatus & SCSI_RESET) - { - dc390_ScsiRstDetect( pACB ); - goto unlock; - } - if( istatus & (SUCCESSFUL_OP|SERVICE_REQUEST) ) { pDCB = pACB->pActiveDCB; @@ -345,7 +336,7 @@ DC390_Interrupt( int irq, void *dev_id, struct pt_regs *regs) }; pSRB = pDCB->pActiveSRB; if( pDCB->DCBFlag & ABORT_DEV_ ) - dc390_EnableMsgOut( pACB, pSRB ); + dc390_EnableMsgOut_Abort (pACB, pSRB); phase = pSRB->ScsiPhase; DEBUG1(printk (KERN_INFO "DC390: [%i]%s(0) (%02x)\n", phase, dc390_p0_str[phase], sstatus);) @@ -357,7 +348,21 @@ DC390_Interrupt( int irq, void *dev_id, struct pt_regs *regs) DEBUG1(printk (KERN_INFO "DC390: [%i]%s(1) (%02x)\n", phase, dc390_p1_str[phase], sstatus);) stateV = (void *) dc390_phase1[phase]; ( *stateV )( pACB, pSRB, &sstatus ); + goto unlock; } + + if(istatus & INVALID_CMD) + { + dc390_InvalidCmd( pACB ); + goto unlock; + } + + if(istatus & SCSI_RESET) + { + dc390_ScsiRstDetect( pACB ); + goto unlock; + } + unlock: DC390_LOCK_DRV_NI; DC390_UNLOCK_ACB; @@ -380,6 +385,7 @@ dc390_DataOut_0( PACB pACB, PSRB pSRB, PUCHAR psstatus) UCHAR sstatus; PSGL psgl; ULONG ResidCnt, xferCnt; + UCHAR dstate = 0; sstatus = *psstatus; @@ -391,10 +397,9 @@ dc390_DataOut_0( PACB pACB, PSRB pSRB, PUCHAR psstatus) if( sstatus & COUNT_2_ZERO ) { int ctr = 5000000; /* only try for about a tenth of a second */ - while( --ctr && !(DC390_read8 (DMA_Status) & DMA_XFER_DONE) && pSRB->SGToBeXferLen ) - DC390_write8 (DMA_Status, DMA_XFER_DONE | DMA_XFER_ABORT | DMA_XFER_ERROR | PCI_MS_ABORT); /* clear */ - if (!ctr) printk (KERN_CRIT "DC390: DataOut_0: DMA aborted unfinished: %06x bytes remain!\n", DC390_read32 (DMA_Wk_ByteCntr)); - DC390_write8 (DMA_Status, DMA_XFER_DONE | DMA_XFER_ABORT | DMA_XFER_ERROR | PCI_MS_ABORT); /* clear */ + while( --ctr && !((dstate = DC390_read8 (DMA_Status)) & DMA_XFER_DONE) && pSRB->SGToBeXferLen ); + if (!ctr) printk (KERN_CRIT "DC390: Deadlock in DataOut_0: DMA aborted unfinished: %06x bytes remain!!\n", DC390_read32 (DMA_Wk_ByteCntr)); + dc390_laststatus &= ~0xff000000; dc390_laststatus |= dstate << 24; pSRB->TotalXferredLen += pSRB->SGToBeXferLen; pSRB->SGIndex++; if( pSRB->SGIndex < pSRB->SGcount ) @@ -443,15 +448,14 @@ dc390_DataIn_0( PACB pACB, PSRB pSRB, PUCHAR psstatus) { int ctr = 5000000; /* only try for about a tenth of a second */ int dstate = 0; - while( --ctr && !((dstate = DC390_read8 (DMA_Status)) & DMA_XFER_DONE) && pSRB->SGToBeXferLen ) - DC390_write8 (DMA_Status, DMA_XFER_DONE | DMA_XFER_ABORT | DMA_XFER_ERROR | PCI_MS_ABORT); /* clear */ - if (!ctr) printk (KERN_CRIT "DC390: DataIn_0: DMA aborted unfinished: %06x bytes remain!\n", DC390_read32 (DMA_Wk_ByteCntr)); + while( --ctr && !((dstate = DC390_read8 (DMA_Status)) & DMA_XFER_DONE) && pSRB->SGToBeXferLen ); + if (!ctr) printk (KERN_CRIT "DC390: Deadlock in DataIn_0: DMA aborted unfinished: %06x bytes remain!!\n", DC390_read32 (DMA_Wk_ByteCntr)); if (!ctr) printk (KERN_CRIT "DC390: DataIn_0: DMA State: %i\n", dstate); + dc390_laststatus &= ~0xff000000; dc390_laststatus |= dstate << 24; DEBUG1(ResidCnt = ((ULONG) DC390_read8 (CtcReg_High) << 16) \ + ((ULONG) DC390_read8 (CtcReg_Mid) << 8) \ + ((ULONG) DC390_read8 (CtcReg_Low));) - DEBUG1(printk ("Count_2_Zero (ResidCnt=%li,ToBeXfer=%li),", ResidCnt, pSRB->SGToBeXferLen);) - DC390_write8 (DMA_Status, DMA_XFER_DONE | DMA_XFER_ABORT | DMA_XFER_ERROR | PCI_MS_ABORT); /* clear */ + DEBUG1(printk (KERN_DEBUG "Count_2_Zero (ResidCnt=%li,ToBeXfer=%li),", ResidCnt, pSRB->SGToBeXferLen);) DC390_write8 (DMA_Cmd, READ_DIRECTION+DMA_IDLE_CMD); /* | DMA_INT */ @@ -474,7 +478,7 @@ dc390_DataIn_0( PACB pACB, PSRB pSRB, PUCHAR psstatus) bval = DC390_read8 (Current_Fifo); while( bval & 0x1f ) { - DEBUG1(printk ("Check for residuals,");) + DEBUG1(printk (KERN_DEBUG "Check for residuals,");) if( (bval & 0x1f) == 1 ) { for(i=0; i < 0x100; i++) @@ -494,17 +498,18 @@ dc390_DataIn_0( PACB pACB, PSRB pSRB, PUCHAR psstatus) } din_1: DC390_write8 (DMA_Cmd, READ_DIRECTION+DMA_BLAST_CMD); - for (i=0; i<0x8000; i++) + for (i = 0xa000; i; i--) { bval = DC390_read8 (DMA_Status); - DC390_write8 (DMA_Status, BLAST_COMPLETE | DMA_XFER_DONE | DMA_XFER_ABORT | DMA_XFER_ERROR | PCI_MS_ABORT); /* clear */ if (bval & BLAST_COMPLETE) break; } - if (i == 0x8000) printk (KERN_CRIT "DC390: DMA Blast aborted unfinished!!\n"); + /* It seems a DMA Blast abort isn't that bad ... */ + if (!i) printk (KERN_ERR "DC390: DMA Blast aborted unfinished!\n"); //DC390_write8 (DMA_Cmd, READ_DIRECTION+DMA_IDLE_CMD); /* | DMA_INT */ + dc390_laststatus &= ~0xff000000; dc390_laststatus |= bval << 24; - DEBUG1(printk ("Blast: Read %i times DMA_Status %02x", i, bval);) + DEBUG1(printk (KERN_DEBUG "Blast: Read %li times DMA_Status %02x", 0xa000-i, bval);) ResidCnt = (ULONG) DC390_read8 (CtcReg_High); ResidCnt <<= 8; ResidCnt |= (ULONG) DC390_read8 (CtcReg_Mid); @@ -525,7 +530,7 @@ din_1: pSRB->TotalXferredLen++; pSRB->SGToBeXferLen--; } - DEBUG1(printk ("Xfered: %li, Total: %li, Remaining: %li\n", xferCnt,\ + DEBUG1(printk (KERN_DEBUG "Xfered: %li, Total: %li, Remaining: %li\n", xferCnt,\ pSRB->TotalXferredLen, pSRB->SGToBeXferLen);) } @@ -558,164 +563,278 @@ dc390_MsgOut_0( PACB pACB, PSRB pSRB, PUCHAR psstatus) //DC390_write8 (DMA_Cmd, DMA_IDLE_CMD); } -void -dc390_MsgIn_0( PACB pACB, PSRB pSRB, PUCHAR psstatus) + +static void __inline__ +dc390_reprog (PACB pACB, PDCB pDCB) { - UCHAR bval; - USHORT wval, wval1; - PDCB pDCB; - PSRB psrb; + DC390_write8 (Sync_Period, pDCB->SyncPeriod); + DC390_write8 (Sync_Offset, pDCB->SyncOffset); + DC390_write8 (CtrlReg3, pDCB->CtrlR3); + DC390_write8 (CtrlReg4, pDCB->CtrlR4); + dc390_SetXferRate (pACB, pDCB); +}; - pDCB = pACB->pActiveDCB; - bval = DC390_read8 (ScsiFifo); - if( !(pSRB->SRBState & SRB_MSGIN_MULTI) ) +#ifdef DC390_DEBUG0 +static void +dc390_printMsg (UCHAR *MsgBuf, UCHAR len) +{ + int i; + printk (" %02x", MsgBuf[0]); + for (i = 1; i < len; i++) + printk (" %02x", MsgBuf[i]); + printk ("\n"); +}; +#endif + +#define DC390_ENABLE_MSGOUT DC390_write8 (ScsiCmd, SET_ATN_CMD) + +/* reject_msg */ +static void __inline__ +dc390_MsgIn_reject (PACB pACB, PSRB pSRB) +{ + pSRB->MsgOutBuf[0] = MSG_REJECT_; + pSRB->MsgCnt = 1; DC390_ENABLE_MSGOUT; + DEBUG0 (printk (KERN_INFO "DC390: Reject message\n");) +} + +/* abort command */ +static void __inline__ +dc390_EnableMsgOut_Abort ( PACB pACB, PSRB pSRB ) +{ + pSRB->MsgOutBuf[0] = MSG_ABORT; + pSRB->MsgCnt = 1; DC390_ENABLE_MSGOUT; + pSRB->pSRBDCB->DCBFlag &= ~ABORT_DEV_; +} + +static PSRB +dc390_MsgIn_QTag (PACB pACB, PDCB pDCB, UCHAR tag) +{ + PSRB lastSRB = pDCB->pGoingLast; + PSRB pSRB = pDCB->pGoingSRB; + + if (pSRB) { - if(bval == MSG_DISCONNECT) - { - pSRB->SRBState = SRB_DISCONNECT; - } - else if( bval == MSG_SAVE_PTR ) - goto min6; - else if( (bval == MSG_EXTENDED) || ((bval >= MSG_SIMPLE_QTAG) && - (bval <= MSG_ORDER_QTAG)) ) + for( ;pSRB ; ) { - pSRB->SRBState |= SRB_MSGIN_MULTI; - pSRB->MsgInBuf[0] = bval; - pSRB->MsgCnt = 1; - pSRB->pMsgPtr = &(pSRB->MsgInBuf[1]); + if (pSRB->TagNumber == tag) break; + if (pSRB == lastSRB) goto mingx0; + pSRB = pSRB->pNextSRB; } - else if(bval == MSG_REJECT_) + + if( pDCB->DCBFlag & ABORT_DEV_ ) { - DC390_write8 (ScsiCmd, RESET_ATN_CMD); - pDCB->NegoPeriod = 50; - if( pSRB->SRBState & DO_SYNC_NEGO) - goto set_async; + pSRB->SRBState = SRB_ABORT_SENT; + dc390_EnableMsgOut_Abort( pACB, pSRB ); } - else if( bval == MSG_RESTORE_PTR) - goto min6; - else - goto min6; + + if( !(pSRB->SRBState & SRB_DISCONNECT) ) + goto mingx0; + + pDCB->pActiveSRB = pSRB; + pSRB->SRBState = SRB_DATA_XFER; } - else - { /* minx: */ + else + { + mingx0: + pSRB = pACB->pTmpSRB; + pSRB->SRBState = SRB_UNEXPECT_RESEL; + pDCB->pActiveSRB = pSRB; + pSRB->MsgOutBuf[0] = MSG_ABORT_TAG; + pSRB->MsgCnt = 1; DC390_ENABLE_MSGOUT; + } + return pSRB; +} - *pSRB->pMsgPtr = bval; - pSRB->MsgCnt++; - pSRB->pMsgPtr++; - if( (pSRB->MsgInBuf[0] >= MSG_SIMPLE_QTAG) && - (pSRB->MsgInBuf[0] <= MSG_ORDER_QTAG) ) - { - if( pSRB->MsgCnt == 2) - { - pSRB->SRBState = 0; - bval = pSRB->MsgInBuf[1]; - pSRB = pDCB->pGoingSRB; - psrb = pDCB->pGoingLast; - if( pSRB ) - { - for( ;pSRB ; ) - { - if(pSRB->TagNumber != bval) - { - if( pSRB == psrb ) - goto mingx0; - pSRB = pSRB->pNextSRB; - } - else - break; - } - if( pDCB->DCBFlag & ABORT_DEV_ ) - { - pSRB->SRBState = SRB_ABORT_SENT; - dc390_EnableMsgOut( pACB, pSRB ); - } - if( !(pSRB->SRBState & SRB_DISCONNECT) ) - goto mingx0; - pDCB->pActiveSRB = pSRB; - pSRB->SRBState = SRB_DATA_XFER; - } - else - { -mingx0: - pSRB = pACB->pTmpSRB; - pSRB->SRBState = SRB_UNEXPECT_RESEL; - pDCB->pActiveSRB = pSRB; - pSRB->MsgOutBuf[0] = MSG_ABORT_TAG; - dc390_EnableMsgOut2( pACB, pSRB ); - } - } + +/* set async transfer mode */ +static void +dc390_MsgIn_set_async (PACB pACB, PSRB pSRB) +{ + PDCB pDCB = pSRB->pSRBDCB; + if (!(pSRB->SRBState & DO_SYNC_NEGO)) + printk ("DC390: Target %i initiates Non-Sync?\n", pDCB->UnitSCSIID); + pSRB->SRBState &= ~DO_SYNC_NEGO; + pDCB->SyncMode &= ~(SYNC_ENABLE+SYNC_NEGO_DONE); + pDCB->SyncPeriod = 0; + pDCB->SyncOffset = 0; + //pDCB->NegoPeriod = 50; /* 200ns <=> 5 MHz */ + pDCB->CtrlR3 = FAST_CLK; /* fast clock / normal scsi */ + pDCB->CtrlR4 &= 0x3f; + pDCB->CtrlR4 |= pACB->glitch_cfg; /* glitch eater */ + dc390_reprog (pACB, pDCB); +} + +/* set sync transfer mode */ +static void +dc390_MsgIn_set_sync (PACB pACB, PSRB pSRB) +{ + UCHAR bval; + USHORT wval, wval1; + PDCB pDCB = pSRB->pSRBDCB; + UCHAR oldsyncperiod = pDCB->SyncPeriod; + UCHAR oldsyncoffset = pDCB->SyncOffset; + + if (!(pSRB->SRBState & DO_SYNC_NEGO)) + { + printk ("DC390: Target %i initiates Sync: %ins %i ... answer ...\n", + pDCB->UnitSCSIID, pSRB->MsgInBuf[3]<<2, pSRB->MsgInBuf[4]); + + /* reject */ + //dc390_MsgIn_reject (pACB, pSRB); + //return dc390_MsgIn_set_async (pACB, pSRB); + + /* Reply with corrected SDTR Message */ + if (pSRB->MsgInBuf[4] > 15) + { + printk ("DC390: Lower Sync Offset to 15\n"); + pSRB->MsgInBuf[4] = 15; } - else if( (pSRB->MsgInBuf[0] == MSG_EXTENDED) && (pSRB->MsgCnt == 5) ) - { /* Note: This will fail for target initiated SDTR ? */ - pSRB->SRBState &= ~(SRB_MSGIN_MULTI); - if( (pSRB->MsgInBuf[1] != 3) || (pSRB->MsgInBuf[2] != EXTENDED_SDTR) ) - { /* reject_msg: */ - pSRB->MsgCnt = 1; - pSRB->MsgInBuf[0] = MSG_REJECT_; - DC390_write8 (ScsiCmd, SET_ATN_CMD); - } - else if( !(pSRB->MsgInBuf[3]) || !(pSRB->MsgInBuf[4]) ) - { -set_async: - pDCB = pSRB->pSRBDCB; - if (!(pSRB->SRBState & DO_SYNC_NEGO)) - printk ("DC390: Target (%i,%i) initiates Non-Sync?\n", pDCB->UnitSCSIID, pDCB->UnitSCSILUN); - pSRB->SRBState &= ~DO_SYNC_NEGO; - pDCB->SyncMode &= ~(SYNC_ENABLE+SYNC_NEGO_DONE); - pDCB->SyncPeriod = 0; - pDCB->SyncOffset = 0; - pDCB->CtrlR3 = FAST_CLK; /* fast clock / normal scsi */ - pDCB->CtrlR4 &= 0x3f; - pDCB->CtrlR4 |= pACB->glitch_cfg; /* glitch eater */ - goto re_prog; - } + if (pSRB->MsgInBuf[3] < pDCB->NegoPeriod) + { + printk ("DC390: Set sync nego period to %ins\n", pDCB->NegoPeriod << 2); + pSRB->MsgInBuf[3] = pDCB->NegoPeriod; + }; + memcpy (pSRB->MsgOutBuf, pSRB->MsgInBuf, 5); + pSRB->MsgCnt = 5; + DC390_ENABLE_MSGOUT; + }; + + pSRB->SRBState &= ~DO_SYNC_NEGO; + pDCB->SyncMode |= SYNC_ENABLE+SYNC_NEGO_DONE; + pDCB->SyncOffset &= 0x0f0; + pDCB->SyncOffset |= pSRB->MsgInBuf[4]; + pDCB->NegoPeriod = pSRB->MsgInBuf[3]; + + wval = (USHORT) pSRB->MsgInBuf[3]; + wval = wval << 2; wval -= 3; wval1 = wval / 25; /* compute speed */ + if( (wval1 * 25) != wval) wval1++; + bval = FAST_CLK+FAST_SCSI; /* fast clock / fast scsi */ + + pDCB->CtrlR4 &= 0x3f; /* Glitch eater: 12ns less than normal */ + if (pACB->glitch_cfg != NS_TO_GLITCH(0)) + pDCB->CtrlR4 |= NS_TO_GLITCH(((GLITCH_TO_NS(pACB->glitch_cfg)) - 1)); + else + pDCB->CtrlR4 |= NS_TO_GLITCH(0); + if (wval1 < 4) pDCB->CtrlR4 |= NS_TO_GLITCH(0); /* Ultra */ + + if (wval1 >= 8) + { + wval1--; /* Timing computation differs by 1 from FAST_SCSI */ + bval = FAST_CLK; /* fast clock / normal scsi */ + pDCB->CtrlR4 |= pACB->glitch_cfg; /* glitch eater */ + } + + pDCB->CtrlR3 = bval; + pDCB->SyncPeriod = (UCHAR)wval1; + + if ((oldsyncperiod != wval1 || oldsyncoffset != pDCB->SyncOffset) && pDCB->UnitSCSILUN == 0) + { + if (! (bval & FAST_SCSI)) wval1++; + printk ("DC390: Target %i: Sync transfer %i.%1i MHz, Offset %i\n", pDCB->UnitSCSIID, + 40/wval1, ((40%wval1)*10+wval1/2)/wval1, pDCB->SyncOffset & 0x0f); + } + + dc390_reprog (pACB, pDCB); +}; + + +/* According to the docs, the AM53C974 reads the message and + * generates a Succesful Operation IRQ before asserting ACK for + * the last byte (how does it know whether it's the last ?) */ +/* The old code handled it in another way, indicating, that on + * every message byte an IRQ is generated and every byte has to + * be manually ACKed. Hmmm ? (KG, 98/11/28) */ +/* The old implementation was correct. Sigh! */ + +/* Check if the message is complete */ +static UCHAR __inline__ +dc390_MsgIn_complete (UCHAR *msgbuf, ULONG len) +{ + if (*msgbuf == MSG_EXTENDED) + { + if (len < 2) return 0; + if (len < msgbuf[1] + 2) return 0; + } + else if (*msgbuf >= 0x20 && *msgbuf <= 0x2f) // two byte messages + if (len < 2) return 0; + return 1; +} + + + +/* read and eval received messages */ +void +dc390_MsgIn_0( PACB pACB, PSRB pSRB, PUCHAR psstatus) +{ + PDCB pDCB = pACB->pActiveDCB; + + /* Read the msg */ + + pSRB->MsgInBuf[pACB->MsgLen++] = DC390_read8 (ScsiFifo); + //pSRB->SRBState = 0; + + /* Msg complete ? */ + if (dc390_MsgIn_complete (pSRB->MsgInBuf, pACB->MsgLen)) + { + DEBUG0 (printk (KERN_INFO "DC390: MsgIn:"); dc390_printMsg (pSRB->MsgInBuf, pACB->MsgLen);) + /* Now eval the msg */ + switch (pSRB->MsgInBuf[0]) + { + case MSG_DISCONNECT: + pSRB->SRBState = SRB_DISCONNECT; break; + + case MSG_SIMPLE_QTAG: + case MSG_HEAD_QTAG: + case MSG_ORDER_QTAG: + pSRB = dc390_MsgIn_QTag (pACB, pDCB, pSRB->MsgInBuf[1]); + break; + + case MSG_REJECT_: + DC390_write8 (ScsiCmd, RESET_ATN_CMD); + pDCB->NegoPeriod = 50; /* 200ns <=> 5 MHz */ + if( pSRB->SRBState & DO_SYNC_NEGO) + dc390_MsgIn_set_async (pACB, pSRB); + break; + + case MSG_EXTENDED: + /* reject every extended msg but SDTR */ + if (pSRB->MsgInBuf[1] != 3 || pSRB->MsgInBuf[2] != EXTENDED_SDTR) + dc390_MsgIn_reject (pACB, pSRB); else - { /* set_sync: */ - - pDCB = pSRB->pSRBDCB; - if (!(pSRB->SRBState & DO_SYNC_NEGO)) - printk ("DC390: Target (%i,%i) initiates Sync: %ins %i ?\n", - pDCB->UnitSCSIID, pDCB->UnitSCSILUN, pSRB->MsgInBuf[3]<<2, pSRB->MsgInBuf[4]); - pSRB->SRBState &= ~DO_SYNC_NEGO; - pDCB->SyncMode |= SYNC_ENABLE+SYNC_NEGO_DONE; - pDCB->SyncOffset &= 0x0f0; - pDCB->SyncOffset |= pSRB->MsgInBuf[4]; - pDCB->NegoPeriod = pSRB->MsgInBuf[3]; - wval = (USHORT) pSRB->MsgInBuf[3]; - wval = wval << 2; wval -= 3; wval1 = wval / 25; /* compute speed */ - if( (wval1 * 25) != wval) - wval1++; - bval = FAST_CLK+FAST_SCSI; /* fast clock / fast scsi */ - pDCB->CtrlR4 &= 0x3f; /* Glitch eater: 12ns less than normal */ - if (pACB->glitch_cfg != NS_TO_GLITCH(0)) - pDCB->CtrlR4 |= NS_TO_GLITCH(((GLITCH_TO_NS(pACB->glitch_cfg)) - 1)); + { + if (pSRB->MsgInBuf[3] == 0 || pSRB->MsgInBuf[4] == 0) + dc390_MsgIn_set_async (pACB, pSRB); else - pDCB->CtrlR4 |= NS_TO_GLITCH(0); - if (wval1 < 4) pDCB->CtrlR4 |= NS_TO_GLITCH(0); /* Ultra */ - if (wval1 >= 8) - { - wval1--; /* Timing computation differs by 1 from FAST_SCSI */ - bval = FAST_CLK; /* fast clock / normal scsi */ - pDCB->CtrlR4 |= pACB->glitch_cfg; /* glitch eater */ - } - pDCB->CtrlR3 = bval; - pDCB->SyncPeriod = (UCHAR)wval1; -re_prog: - DC390_write8 (Sync_Period, pDCB->SyncPeriod); - DC390_write8 (Sync_Offset, pDCB->SyncOffset); - DC390_write8 (CtrlReg3, pDCB->CtrlR3); - DC390_write8 (CtrlReg4, pDCB->CtrlR4); - dc390_SetXferRate (pACB, pDCB); - } - } - } -min6: + dc390_MsgIn_set_sync (pACB, pSRB); + }; + + // nothing has to be done + case MSG_COMPLETE: break; + + // SAVE POINTER my be ignored as we have the PSRB associated with the + // scsi command. Thanks, Gerard, for pointing it out. + case MSG_SAVE_PTR: break; + // The device might want to restart transfer with a RESTORE + case MSG_RESTORE_PTR: + printk ("DC390: RESTORE POINTER message received ... reject\n"); + // fall through + + // reject unknown messages + default: dc390_MsgIn_reject (pACB, pSRB); + } + + /* Clear counter and MsgIn state */ + pSRB->SRBState &= ~SRB_MSGIN; + pACB->MsgLen = 0; + }; + *psstatus = SCSI_NOP0; DC390_write8 (ScsiCmd, MSG_ACCEPTED_CMD); //DC390_write8 (DMA_Cmd, DMA_IDLE_CMD); } + void dc390_DataIO_Comm( PACB pACB, PSRB pSRB, UCHAR ioDir) { @@ -730,10 +849,10 @@ dc390_DataIO_Comm( PACB pACB, PSRB pSRB, UCHAR ioDir) psgl = pSRB->pSegmentList; pSRB->SGBusAddr = virt_to_bus( psgl->address ); pSRB->SGToBeXferLen = (ULONG) psgl->length; - DEBUG1(printk (" DC390: Next SG segment.");) + DEBUG1(printk (KERN_DEBUG " DC390: Next SG segment.");) } lval = pSRB->SGToBeXferLen; - DEBUG1(printk (" DC390: Transfer %li bytes (address %08lx)\n", lval, pSRB->SGBusAddr);) + DEBUG1(printk (KERN_DEBUG " DC390: Transfer %li bytes (address %08lx)\n", lval, pSRB->SGBusAddr);) DC390_write8 (CtcReg_Low, (UCHAR) lval); lval >>= 8; DC390_write8 (CtcReg_Mid, (UCHAR) lval); @@ -749,21 +868,22 @@ dc390_DataIO_Comm( PACB pACB, PSRB pSRB, UCHAR ioDir) DC390_write8 (ScsiCmd, DMA_COMMAND+INFO_XFER_CMD); DC390_write8 (DMA_Cmd, DMA_START_CMD | ioDir | DMA_INT); - //DEBUG1(printk ("DC390: DMA_Status: %02x\n", DC390_read8 (DMA_Status));) + //DEBUG1(DC390_write32 (DMA_ScsiBusCtrl, WRT_ERASE_DMA_STAT | EN_INT_ON_PCI_ABORT);) + //DEBUG1(printk (KERN_DEBUG "DC390: DMA_Status: %02x\n", DC390_read8 (DMA_Status));) + //DEBUG1(DC390_write32 (DMA_ScsiBusCtrl, EN_INT_ON_PCI_ABORT);) } else /* xfer pad */ { - UCHAR bval = 0; if( pSRB->SGcount ) { pSRB->AdaptStatus = H_OVER_UNDER_RUN; pSRB->SRBStatus |= OVER_RUN; - DEBUG0(printk (" DC390: Overrun -");) + DEBUG0(printk (KERN_WARNING " DC390: Overrun -");) } - DEBUG0(printk (" Clear transfer pad \n");) - DC390_write8 (CtcReg_Low, bval); - DC390_write8 (CtcReg_Mid, bval); - DC390_write8 (CtcReg_High, bval); + DEBUG0(printk (KERN_WARNING " Clear transfer pad \n");) + DC390_write8 (CtcReg_Low, 0); + DC390_write8 (CtcReg_Mid, 0); + DC390_write8 (CtcReg_High, 0); pSRB->SRBState |= SRB_XFERPAD; DC390_write8 (ScsiCmd, DMA_COMMAND+XFER_PAD_BYTE); @@ -1017,7 +1137,7 @@ disc1: dc390_SRBdone( pACB, pDCB, pSRB); } } - return; + pACB->MsgLen = 0; } @@ -1032,7 +1152,7 @@ dc390_Reselect( PACB pACB ) DEBUG0(printk(KERN_INFO "RSEL,");) pDCB = pACB->pActiveDCB; if( pDCB ) - { /* Arbitration lost but Reselection win */ + { /* Arbitration lost but Reselection won */ DEBUG0(printk ("(ActiveDCB != 0)");) pSRB = pDCB->pActiveSRB; if( !( pACB->scan_devices ) ) @@ -1075,23 +1195,23 @@ dc390_Reselect( PACB pACB ) printk (KERN_ERR "DC390: Reselect without outstanding cmnd (ID %02x, LUN %02x)\n", wval & 0xff, (wval & 0xff00) >> 8); pDCB->pActiveSRB = pSRB; - dc390_EnableMsgOut( pACB, pSRB ); + dc390_EnableMsgOut_Abort ( pACB, pSRB ); } else { if( pDCB->DCBFlag & ABORT_DEV_ ) { pSRB->SRBState = SRB_ABORT_SENT; - printk (KERN_NOTICE "DC390: Reselect: Abort (ID %02x, LUN %02x)\n", + printk (KERN_INFO "DC390: Reselect: Abort (ID %02x, LUN %02x)\n", wval & 0xff, (wval & 0xff00) >> 8); - dc390_EnableMsgOut( pACB, pSRB ); + dc390_EnableMsgOut_Abort( pACB, pSRB ); } else pSRB->SRBState = SRB_DATA_XFER; } } - DEBUG1(printk ("Resel SRB(%p): TagNum (%02x)\n", pSRB, pSRB->TagNumber);) + DEBUG1(printk (KERN_DEBUG "Resel SRB(%p): TagNum (%02x)\n", pSRB, pSRB->TagNumber);) pSRB->ScsiPhase = SCSI_NOP0; DC390_write8 (Scsi_Dest_ID, pDCB->UnitSCSIID); DC390_write8 (Sync_Period, pDCB->SyncPeriod); @@ -1244,7 +1364,7 @@ dc390_SRBdone( PACB pACB, PDCB pDCB, PSRB pSRB ) else pcmd->result = (DRIVER_SENSE << 24) | (DRIVER_OK << 16) | SCSI_STAT_CHECKCOND; - REMOVABLEDEBUG(printk("Cmd=%02x,Result=%08x,XferL=%08x\n",pSRB->CmdBlock[0],\ + REMOVABLEDEBUG(printk(KERN_INFO "Cmd=%02x,Result=%08x,XferL=%08x\n",pSRB->CmdBlock[0],\ (UINT) pcmd->result, (UINT) pSRB->TotalXferredLen);) goto ckc_e; } @@ -1260,7 +1380,7 @@ dc390_SRBdone( PACB pACB, PDCB pDCB, PSRB pSRB ) { pcmd->result = (DRIVER_SENSE << 24) | (DRIVER_OK << 16) | SCSI_STAT_CHECKCOND; - REMOVABLEDEBUG(printk("Cmd=%02x, Result=%08x, XferL=%08x\n",pSRB->CmdBlock[0],\ + REMOVABLEDEBUG(printk(KERN_INFO "Cmd=%02x, Result=%08x, XferL=%08x\n",pSRB->CmdBlock[0],\ (UINT) pcmd->result, (UINT) pSRB->TotalXferredLen);) goto ckc_e; } @@ -1299,7 +1419,7 @@ dc390_SRBdone( PACB pACB, PDCB pDCB, PSRB pSRB ) swlval += ptr2->length; ptr2++; } - REMOVABLEDEBUG(printk("XferredLen=%08x,NotXferLen=%08x\n",\ + REMOVABLEDEBUG(printk(KERN_INFO "XferredLen=%08x,NotXferLen=%08x\n",\ (UINT) pSRB->TotalXferredLen, (UINT) swlval);) } dc390_RequestSense( pACB, pDCB, pSRB ); @@ -1587,22 +1707,6 @@ dc390_RequestSense( PACB pACB, PDCB pDCB, PSRB pSRB ) } -static void __inline__ -dc390_EnableMsgOut2( PACB pACB, PSRB pSRB ) -{ - pSRB->MsgCnt = 1; - DC390_write8 (ScsiCmd, SET_ATN_CMD); -} - - -static void __inline__ -dc390_EnableMsgOut( PACB pACB, PSRB pSRB ) -{ - pSRB->MsgOutBuf[0] = MSG_ABORT; - dc390_EnableMsgOut2( pACB, pSRB ); - pSRB->pSRBDCB->DCBFlag &= ~ABORT_DEV_; -} - static void __inline__ dc390_InvalidCmd( PACB pACB ) diff --git a/drivers/scsi/st.c b/drivers/scsi/st.c index 8ec3dbc0696a..8ffabde7ecc2 100644 --- a/drivers/scsi/st.c +++ b/drivers/scsi/st.c @@ -11,7 +11,7 @@ Copyright 1992 - 1998 Kai Makisara email Kai.Makisara@metla.fi - Last modified: Sun Sep 6 09:34:49 1998 by root@home + Last modified: Thu Dec 3 20:27:46 1998 by makisara@home Some small formal changes - aeb, 950809 */ @@ -707,7 +707,7 @@ scsi_tape_open(struct inode * inode, struct file * filp) STp->density = 0; /* Clear the erroneous "residue" */ STp->write_prot = 0; STp->block_size = 0; - STp->ps[0].drv_file = STp->ps[0].drv_block = 0; + STp->ps[0].drv_file = STp->ps[0].drv_block = (-1); STp->partition = STp->new_partition = 0; STp->door_locked = ST_UNLOCKED; STp->in_use = 1; @@ -785,6 +785,7 @@ scsi_tape_open(struct inode * inode, struct file * filp) !enlarge_buffer(STp->buffer, STp->block_size, STp->restr_dma)) { printk(KERN_NOTICE "st%d: Blocksize %d too large for buffer.\n", dev, STp->block_size); + scsi_release_command(SCpnt); (STp->buffer)->in_use = 0; STp->buffer = NULL; if (scsi_tapes[dev].device->host->hostt->module) @@ -3414,8 +3415,8 @@ static int st_attach(Scsi_Device * SDp){ STps->eof = ST_NOEOF; STps->at_sm = 0; STps->last_block_valid = FALSE; - STps->drv_block = 0; - STps->drv_file = 0; + STps->drv_block = (-1); + STps->drv_file = (-1); } tpnt->current_mode = 0; diff --git a/drivers/scsi/tmscsim.c b/drivers/scsi/tmscsim.c index cafd9280c407..af47e706c70e 100644 --- a/drivers/scsi/tmscsim.c +++ b/drivers/scsi/tmscsim.c @@ -5,9 +5,11 @@ * Bus Master Host Adapter * * (C)Copyright 1995-1996 Tekram Technology Co., Ltd. * ***********************************************************************/ -/* $Id: tmscsim.c,v 2.4 1998/10/24 08:50:47 garloff Exp $ */ +/* (C) Copyright: put under GNU GPL in 10/96 * +*************************************************************************/ +/* $Id: tmscsim.c,v 2.16 1998/12/25 17:54:44 garloff Exp $ */ /* Enhancements and bugfixes by * - * Kurt Garloff * + * Kurt Garloff * ***********************************************************************/ /* HISTORY: * * * @@ -90,6 +92,11 @@ * bios_param() now respects part. table. * * 2.0b 98/10/24 KG Docu fixes. Timeout Msg in DMA Blast. * * Disallow illegal idx in INQUIRY/REMOVE * + * 2.0c 98/11/19 KG Cleaned up detect/init for SMP boxes, * + * Write Erase DMA (1.20t) caused problems * + * 2.0d 98/12/25 KG Christmas release ;-) Message handling * + * competely reworked. Handle target ini- * + * tiated SDTR correctly. * ***********************************************************************/ /* Uncomment SA_INTERRUPT, if the driver refuses to share its IRQ with other devices */ @@ -206,9 +213,9 @@ # if USE_SPINLOCKS == 3 /* both */ # if defined (__SMP__) || DEBUG_SPINLOCKS > 0 -# define DC390_LOCK_INIT { spinlock_t __unlocked = SPIN_LOCK_UNLOCKED; pACB->lock = __unlocked; }; +# define DC390_LOCKA_INIT { spinlock_t __unlocked = SPIN_LOCK_UNLOCKED; pACB->lock = __unlocked; }; # else -# define DC390_LOCK_INIT +# define DC390_LOCKA_INIT # endif spinlock_t dc390_drvlock = SPIN_LOCK_UNLOCKED; @@ -228,16 +235,16 @@ # define DC390_UNLOCK_ACB spin_unlock_irqrestore (&(pACB->lock), aflags) # define DC390_LOCK_ACB_NI spin_lock (&(pACB->lock)) # define DC390_UNLOCK_ACB_NI spin_unlock (&(pACB->lock)) -//# define DC390_LOCK_INIT spin_lock_init (&(pACB->lock)) +//# define DC390_LOCKA_INIT spin_lock_init (&(pACB->lock)) # else # if USE_SPINLOCKS == 2 /* adapter specific locks */ # if defined (__SMP__) || DEBUG_SPINLOCKS > 0 -# define DC390_LOCK_INIT { spinlock_t __unlocked = SPIN_LOCK_UNLOCKED; pACB->lock = __unlocked; }; +# define DC390_LOCKA_INIT { spinlock_t __unlocked = SPIN_LOCK_UNLOCKED; pACB->lock = __unlocked; }; # else -# define DC390_LOCK_INIT +# define DC390_LOCKA_INIT # endif spinlock_t dc390_drvlock = SPIN_LOCK_UNLOCKED; # define DC390_AFLAGS unsigned long aflags; @@ -253,7 +260,7 @@ # define DC390_UNLOCK_ACB spin_unlock_irqrestore (&(pACB->lock), aflags) # define DC390_LOCK_ACB_NI spin_lock (&(pACB->lock)) # define DC390_UNLOCK_ACB_NI spin_unlock (&(pACB->lock)) -//# define DC390_LOCK_INIT spin_lock_init (&(pACB->lock)) +//# define DC390_LOCKA_INIT spin_lock_init (&(pACB->lock)) # else /* USE_SPINLOCKS == 1: global lock io_request_lock */ @@ -271,7 +278,7 @@ # define DC390_UNLOCK_ACB /* DC390_UNLOCK_IO */ # define DC390_LOCK_ACB_NI /* spin_lock (&(pACB->lock)) */ # define DC390_UNLOCK_ACB_NI /* spin_unlock (&(pACB->lock)) */ -# define DC390_LOCK_INIT /* DC390_LOCK_INIT */ +# define DC390_LOCKA_INIT /* DC390_LOCKA_INIT */ # endif /* 2 */ # endif /* 3 */ @@ -291,7 +298,7 @@ # define DC390_UNLOCK_ACB restore_flags (aflags) # define DC390_LOCK_ACB_NI # define DC390_UNLOCK_ACB_NI -# define DC390_LOCK_INIT +# define DC390_LOCKA_INIT #endif /* def */ @@ -365,9 +372,8 @@ void dc390_DoingSRB_Done( PACB pACB ); static void dc390_ScsiRstDetect( PACB pACB ); static void dc390_ResetSCSIBus( PACB pACB ); static void __inline__ dc390_RequestSense( PACB pACB, PDCB pDCB, PSRB pSRB ); -static void __inline__ dc390_EnableMsgOut2( PACB pACB, PSRB pSRB ); -static void __inline__ dc390_EnableMsgOut( PACB pACB, PSRB pSRB ); static void __inline__ dc390_InvalidCmd( PACB pACB ); +static void __inline__ dc390_EnableMsgOut_Abort (PACB, PSRB); static void dc390_remove_dev (PACB pACB, PDCB pDCB); void do_DC390_Interrupt( int, void *, struct pt_regs *); @@ -481,9 +487,190 @@ struct proc_dir_entry DC390_proc_scsi_tmscsim ={ S_IFDIR | S_IRUGO | S_IXUGO, 2 }; + /*********************************************************************** + * Functions for access to DC390 EEPROM + * and some to emulate it * - * + **********************************************************************/ + + +static void __init dc390_EnDisableCE( UCHAR mode, PDEVDECL, PUCHAR regval ) +{ + UCHAR bval; + + bval = 0; + if(mode == ENABLE_CE) + *regval = 0xc0; + else + *regval = 0x80; + PCI_WRITE_CONFIG_BYTE(PDEV, *regval, bval); + if(mode == DISABLE_CE) + PCI_WRITE_CONFIG_BYTE(PDEV, *regval, bval); + udelay(160); +} + +#ifndef CONFIG_SCSI_DC390T_NOGENSUPP +static void __init dc390_EEpromDefaults (UCHAR index) +{ + PUCHAR ptr; + UCHAR id; + ptr = (PUCHAR) dc390_eepromBuf[index]; + + /* Adapter Settings */ + ptr[EE_ADAPT_SCSI_ID] = (UCHAR)tmscsim[0]; /* Adapter ID */ + ptr[EE_MODE2] = (UCHAR)tmscsim[3]; + ptr[EE_DELAY] = 0; /* ?? */ + ptr[EE_TAG_CMD_NUM] = (UCHAR)tmscsim[4]; /* Tagged Comds */ + + /* Device Settings */ + for (id = 0; id < MAX_SCSI_ID; id++) + { + ptr[id<<2] = (UCHAR)tmscsim[2]; /* EE_MODE1 */ + ptr[(id<<2) + 1] = (UCHAR)tmscsim[1]; /* EE_Speed */ + }; + dc390_adapname = "AM53C974"; +} + +static void __init dc390_checkparams (void) +{ + PARSEDEBUG(printk(KERN_INFO "DC390: setup %08x %08x %08x %08x %08x\n", tmscsim[0],\ + tmscsim[1], tmscsim[2], tmscsim[3], tmscsim[4]);) + if (tmscsim[0] < 0 || tmscsim[0] > 7) /* modules-2.0.0 passes -1 as string */ + { + tmscsim[0] = 7; tmscsim[1] = 4; + tmscsim[2] = 9; tmscsim[3] = 15; + tmscsim[4] = 2; + printk (KERN_INFO "DC390: Using safe settings.\n"); + } + else + { + /* if (tmscsim[0] < 0 || tmscsim[0] > 7) tmscsim[0] = 7; */ + if (tmscsim[1] < 0 || tmscsim[1] > 7) tmscsim[1] = 4; + if (tmscsim[4] < 0 || tmscsim[4] > 5) tmscsim[4] = 4; + }; +}; +/* Override defaults on cmdline: + * tmscsim: AdaptID, MaxSpeed (Index), DevMode (Bitmapped), AdaptMode (Bitmapped) + */ +void __init dc390_setup (char *str, int *ints) +{ + int i; + for (i = 0; i < ints[0]; i++) + tmscsim[i] = ints[i+1]; + if (ints[0] > 5) + printk (KERN_NOTICE "DC390: ignore extra params!\n"); + /* dc390_checkparams (); */ +}; +#endif /* CONFIG_SCSI_DC390T_NOGENSUPP */ + + +static void __init dc390_EEpromOutDI( PDEVDECL, PUCHAR regval, UCHAR Carry ) +{ + UCHAR bval; + + bval = 0; + if(Carry) + { + bval = 0x40; + *regval = 0x80; + PCI_WRITE_CONFIG_BYTE(PDEV, *regval, bval); + } + udelay(160); + bval |= 0x80; + PCI_WRITE_CONFIG_BYTE(PDEV, *regval, bval); + udelay(160); + bval = 0; + PCI_WRITE_CONFIG_BYTE(PDEV, *regval, bval); + udelay(160); +} + + +static UCHAR __init dc390_EEpromInDO( PDEVDECL ) +{ + UCHAR bval; + + PCI_WRITE_CONFIG_BYTE(PDEV, 0x80, 0x80); + udelay(160); + PCI_WRITE_CONFIG_BYTE(PDEV, 0x80, 0x40); + udelay(160); + PCI_READ_CONFIG_BYTE(PDEV, 0x00, &bval); + if(bval == 0x22) + return(1); + else + return(0); +} + + +static USHORT __init dc390_EEpromGetData1( PDEVDECL ) +{ + UCHAR i; + UCHAR carryFlag; + USHORT wval; + + wval = 0; + for(i=0; i<16; i++) + { + wval <<= 1; + carryFlag = dc390_EEpromInDO(PDEV); + wval |= carryFlag; + } + return(wval); +} + + +static void __init dc390_Prepare( PDEVDECL, PUCHAR regval, UCHAR EEpromCmd ) +{ + UCHAR i,j; + UCHAR carryFlag; + + carryFlag = 1; + j = 0x80; + for(i=0; i<9; i++) + { + dc390_EEpromOutDI(PDEV,regval,carryFlag); + carryFlag = (EEpromCmd & j) ? 1 : 0; + j >>= 1; + } +} + + +static void __init dc390_ReadEEprom( PDEVDECL, PUSHORT ptr) +{ + UCHAR regval,cmd; + UCHAR i; + + cmd = EEPROM_READ; + for(i=0; i<0x40; i++) + { + dc390_EnDisableCE(ENABLE_CE, PDEV, ®val); + dc390_Prepare(PDEV, ®val, cmd++); + *ptr++ = dc390_EEpromGetData1(PDEV); + dc390_EnDisableCE(DISABLE_CE, PDEV, ®val); + } +} + + +static UCHAR __init dc390_CheckEEpromCheckSum( PDEVDECL, UCHAR index ) +{ + UCHAR i; + char EEbuf[128]; + USHORT wval, *ptr = (PUSHORT)EEbuf; + + dc390_ReadEEprom( PDEV, ptr ); + memcpy (dc390_eepromBuf[index], EEbuf, EE_ADAPT_SCSI_ID); + memcpy (&dc390_eepromBuf[index][EE_ADAPT_SCSI_ID], + &EEbuf[REAL_EE_ADAPT_SCSI_ID], EE_LEN - EE_ADAPT_SCSI_ID); + wval = 0; + for(i=0; i<0x40; i++, ptr++) + wval += *ptr; + return (wval == 0x1234 ? 0 : 1); +} + + +/*********************************************************************** + * Functions for the management of the internal structures + * (DCBs, SRBs, Queueing) * **********************************************************************/ static PDCB __inline__ dc390_findDCB ( PACB pACB, Scsi_Cmnd *cmd) @@ -494,7 +681,7 @@ static PDCB __inline__ dc390_findDCB ( PACB pACB, Scsi_Cmnd *cmd) pDCB = pDCB->pNextDCB; if (pDCB == pACB->pLinkDCB) { - printk (KERN_ERR "DC390: DCB not found (DCB=%08x, DCBmap[%2x]=%2x)\n", + printk (KERN_WARNING "DC390: DCB not found (DCB=%08x, DCBmap[%2x]=%2x)\n", (int)pDCB, cmd->target, pACB->DCBmap[cmd->target]); return 0; } @@ -578,7 +765,7 @@ static void dc390_RewaitSRB( PDCB pDCB, PSRB pSRB ) UCHAR bval; pDCB->GoingSRBCnt--; pDCB->pDCBACB->SelLost++; - DEBUG0(printk("DC390: RewaitSRB (%p, %p) pid = %li\n", pDCB, pSRB, pSRB->pcmd->pid);) + DEBUG0(printk(KERN_INFO "DC390: RewaitSRB (%p, %p) pid = %li\n", pDCB, pSRB, pSRB->pcmd->pid);) psrb1 = pDCB->pGoingSRB; if( pSRB == psrb1 ) { @@ -678,6 +865,13 @@ static __inline__ void dc390_SRBwaiting( PDCB pDCB, PSRB pSRB) } +/*********************************************************************** + * Function: static void dc390_SendSRB (PACB pACB, PSRB pSRB) + * + * Purpose: Send SCSI Request Block (pSRB) to adapter (pACB) + * + ***********************************************************************/ + static void dc390_SendSRB( PACB pACB, PSRB pSRB ) { PDCB pDCB; @@ -720,6 +914,14 @@ SND_EXIT: return; } +/*********************************************************************** + * Function: static void dc390_BuildSRB (Scsi_Cmd *pcmd, PDCB pDCB, + * PSRB pSRB) + * + * Purpose: Prepare SRB for being sent to Device DCB w/ command *pcmd + * + ***********************************************************************/ + static void dc390_BuildSRB (Scsi_Cmnd* pcmd, PDCB pDCB, PSRB pSRB) { pSRB->pSRBDCB = pDCB; @@ -790,7 +992,7 @@ int DC390_queue_command (Scsi_Cmnd *cmd, void (* done)(Scsi_Cmnd *)) DEBUG0(/* if(pACB->scan_devices) */ \ - printk(KERN_DEBUG "DC390: Queue Cmd=%02x,ID=%d,LUN=%d (pid=%li)\n",\ + printk(KERN_INFO "DC390: Queue Cmd=%02x,ID=%d,LUN=%d (pid=%li)\n",\ cmd->cmnd[0],cmd->target,cmd->lun,cmd->pid);) DC390_LOCK_ACB; @@ -1056,15 +1258,17 @@ void dc390_dumpinfo (PACB pACB, PDCB pDCB, PSRB pSRB) printk (" %02x %02x %02x %02x %02x %02x\n", DC390_read8(INT_Status), DC390_read8(Current_Fifo), DC390_read8(CtrlReg1), DC390_read8(CtrlReg2), DC390_read8(CtrlReg3), DC390_read8(CtrlReg4)); + DC390_write32 (DMA_ScsiBusCtrl, WRT_ERASE_DMA_STAT | EN_INT_ON_PCI_ABORT); printk ("DC390: Register dump: DMA engine:\n"); printk ("DC390: Cmd STrCnt SBusA WrkBC WrkAC Stat SBusCtrl\n"); printk ("DC390: %02x %08x %08x %08x %08x %02x %08x\n", DC390_read8(DMA_Cmd), DC390_read32(DMA_XferCnt), DC390_read32(DMA_XferAddr), DC390_read32(DMA_Wk_ByteCntr), DC390_read32(DMA_Wk_AddrCntr), DC390_read8(DMA_Status), DC390_read32(DMA_ScsiBusCtrl)); + DC390_write32 (DMA_ScsiBusCtrl, EN_INT_ON_PCI_ABORT); PDEVSET1; PCI_READ_CONFIG_WORD(PDEV, PCI_STATUS, &pstat); printk ("DC390: Register dump: PCI Status: %04x\n", pstat); - printk ("DC390: Please report driver trouble to K.Garloff@ping.de\n"); + printk ("DC390: In case of driver trouble read linux/drivers/scsi/README.tmscsim\n"); }; @@ -1076,6 +1280,8 @@ void dc390_dumpinfo (PACB pACB, PDCB pDCB, PSRB pSRB) * Inputs : cmd - command to abort * * Returns : 0 on success, -1 on failure. + * + * Status: Buggy ! ***********************************************************************/ int DC390_abort (Scsi_Cmnd *cmd) @@ -1347,13 +1553,13 @@ int DC390_reset(Scsi_Cmnd *cmd, unsigned int resetFlags) /*********************************************************************** - * Function : static void dc390_initDCB + * Function : static void dc390_initDCB() * * Purpose : initialize the internal structures for a given DCB * * Inputs : cmd - pointer to this scsi cmd request block structure - * ***********************************************************************/ + void dc390_initDCB( PACB pACB, PDCB *ppDCB, PSCSICMD cmd ) { PEEprom prom; @@ -1412,11 +1618,11 @@ void dc390_initDCB( PACB pACB, PDCB *ppDCB, PSCSICMD cmd ) } /*********************************************************************** - * Function : static void dc390_updateDCB + * Function : static void dc390_updateDCB() * * Purpose : Set the configuration dependent DCB parameters - * ***********************************************************************/ + void dc390_updateDCB (PACB pACB, PDCB pDCB) { pDCB->IdentifyMsg = IDENTIFY (pDCB->DevMode & EN_DISCONNECT_, pDCB->UnitSCSILUN); @@ -1441,11 +1647,11 @@ void dc390_updateDCB (PACB pACB, PDCB pDCB) /*********************************************************************** - * Function : static void dc390_updateDCBs + * Function : static void dc390_updateDCBs () * * Purpose : Set the configuration dependent DCB params for all DCBs - * ***********************************************************************/ + static void dc390_updateDCBs (PACB pACB) { int i; @@ -1459,13 +1665,13 @@ static void dc390_updateDCBs (PACB pACB) /*********************************************************************** - * Function : static void dc390_initSRB + * Function : static void dc390_initSRB() * * Purpose : initialize the internal structures for a given SRB * * Inputs : psrb - pointer to this scsi request block structure - * ***********************************************************************/ + static void __inline__ dc390_initSRB( PSRB psrb ) { /* psrb->PhysSRB = virt_to_phys( psrb ); */ @@ -1489,13 +1695,14 @@ void dc390_linkSRB( PACB pACB ) /*********************************************************************** - * Function : static void dc390_initACB + * Function : static void dc390_initACB () * * Purpose : initialize the internal structures for a given SCSI host * * Inputs : psh - pointer to this host adapter's structure - * + * io_port, Irq, index: Resources and adapter index ***********************************************************************/ + void __init dc390_initACB (PSH psh, ULONG io_port, UCHAR Irq, UCHAR index) { PACB pACB; @@ -1510,14 +1717,14 @@ void __init dc390_initACB (PSH psh, ULONG io_port, UCHAR Irq, UCHAR index) psh->irq = Irq; pACB = (PACB) psh->hostdata; - DC390_LOCK_INIT; + DC390_LOCKA_INIT; DC390_LOCK_ACB; pACB->pScsiHost = psh; pACB->IOPortBase = (USHORT) io_port; pACB->IRQLevel = Irq; - DEBUG0(printk (KERN_DEBUG "DC390: Adapter index %i, ID %i, IO 0x%08x, IRQ 0x%02x\n", \ + DEBUG0(printk (KERN_INFO "DC390: Adapter index %i, ID %i, IO 0x%08x, IRQ 0x%02x\n", \ index, psh->this_id, (int)io_port, Irq);) psh->max_id = 8; @@ -1541,6 +1748,8 @@ void __init dc390_initACB (PSH psh, ULONG io_port, UCHAR Irq, UCHAR index) pACB->TagMaxNum = 2 << dc390_eepromBuf[index][EE_TAG_CMD_NUM]; pACB->ACBFlag = 0; pACB->scan_devices = 1; + pACB->MsgLen = 0; + pACB->Ignore_IRQ = 0; pACB->Gmode2 = dc390_eepromBuf[index][EE_MODE2]; dc390_linkSRB( pACB ); pACB->pTmpSRB = &pACB->TmpSRB; @@ -1554,33 +1763,44 @@ void __init dc390_initACB (PSH psh, ULONG io_port, UCHAR Irq, UCHAR index) /*********************************************************************** - * Function : static int dc390_initAdapter + * Function : static int dc390_initAdapter () * * Purpose : initialize the SCSI chip ctrl registers * * Inputs : psh - pointer to this host adapter's structure + * io_port, Irq, index: Resources * + * Outputs: 0 on success, -1 on error ***********************************************************************/ + int __init dc390_initAdapter (PSH psh, ULONG io_port, UCHAR Irq, UCHAR index) { - PACB pACB, pacb; + PACB pACB, pACB2; UCHAR used_irq = 0, dstate; int i; + + pACB = (PACB) psh->hostdata; + + for ( pACB2 = dc390_pACB_start; pACB2 ; ) + { + if( pACB2->IRQLevel == Irq ) + { + used_irq = 1; + break; + } + else + pACB2 = pACB2->pNextACB; + } - pacb = dc390_pACB_start; - if( pacb != NULL ) - { - for ( ; (pacb != (PACB) -1) ; ) + if (check_region (io_port, psh->n_io_port)) { - if( pacb->IRQLevel == Irq ) - { - used_irq = 1; - break; - } - else - pacb = pacb->pNextACB; + printk(KERN_ERR "DC390: register IO ports error!\n"); + return( -1 ); } - } + else + request_region (io_port, psh->n_io_port, "tmscsim"); + + DC390_read8_ (INT_Status, io_port); /* Reset Pending INT */ if( !used_irq ) { @@ -1591,18 +1811,22 @@ int __init dc390_initAdapter (PSH psh, ULONG io_port, UCHAR Irq, UCHAR index) } } - if (check_region (io_port, psh->n_io_port)) - { - printk(KERN_ERR "DC390: register IO ports error!\n"); - return( -1 ); - } + if( !dc390_pACB_start ) + { + pACB2 = NULL; + dc390_pACB_start = pACB; + dc390_pACB_current = pACB; + pACB->pNextACB = NULL; + } else - request_region (io_port, psh->n_io_port, "tmscsim"); - - pACB = (PACB) psh->hostdata; - /* pACB->IOPortBase = (USHORT) io_port; */ + { + pACB2 = dc390_pACB_current; + dc390_pACB_current->pNextACB = pACB; + dc390_pACB_current = pACB; + pACB->pNextACB = NULL; + }; - DC390_write8_ (CtrlReg1, DIS_INT_ON_SCSI_RST | psh->this_id, io_port); /* Disable SCSI bus reset interrupt */ + DC390_write8 (CtrlReg1, DIS_INT_ON_SCSI_RST | psh->this_id); /* Disable SCSI bus reset interrupt */ if (pACB->Gmode2 & RST_SCSI_BUS) { @@ -1612,6 +1836,7 @@ int __init dc390_initAdapter (PSH psh, ULONG io_port, UCHAR Irq, UCHAR index) udelay(1000); }; pACB->ACBFlag = 0; + DC390_read8 (INT_Status); /* Reset Pending INT */ DC390_write8 (Scsi_TimeOut, SEL_TIMEOUT); /* 250ms selection timeout */ DC390_write8 (Clk_Factor, CLK_FREQ_40MHZ); /* Conversion factor = 0 , 40MHz clock */ @@ -1622,7 +1847,7 @@ int __init dc390_initAdapter (PSH psh, ULONG io_port, UCHAR Irq, UCHAR index) (dc390_eepromBuf[index][EE_MODE2] & ACTIVE_NEGATION) ? NEGATE_REQACKDATA : 0); /* Negation */ DC390_write8 (DMA_Cmd, DMA_IDLE_CMD); DC390_write8 (ScsiCmd, CLEAR_FIFO_CMD); - DC390_write32 (DMA_ScsiBusCtrl, WRT_ERASE_DMA_STAT | EN_INT_ON_PCI_ABORT); + DC390_write32 (DMA_ScsiBusCtrl, EN_INT_ON_PCI_ABORT); dstate = DC390_read8 (DMA_Status); DC390_write8 (DMA_Status, dstate); /* clear */ @@ -1630,194 +1855,24 @@ int __init dc390_initAdapter (PSH psh, ULONG io_port, UCHAR Irq, UCHAR index) } -static void __init dc390_EnDisableCE( UCHAR mode, PDEVDECL, PUCHAR regval ) -{ - UCHAR bval; - - bval = 0; - if(mode == ENABLE_CE) - *regval = 0xc0; - else - *regval = 0x80; - PCI_WRITE_CONFIG_BYTE(PDEV, *regval, bval); - if(mode == DISABLE_CE) - PCI_WRITE_CONFIG_BYTE(PDEV, *regval, bval); - udelay(160); -} - -#ifndef CONFIG_SCSI_DC390T_NOGENSUPP -static void __init dc390_EEpromDefaults (UCHAR index) -{ - PUCHAR ptr; - UCHAR id; - ptr = (PUCHAR) dc390_eepromBuf[index]; - - /* Adapter Settings */ - ptr[EE_ADAPT_SCSI_ID] = (UCHAR)tmscsim[0]; /* Adapter ID */ - ptr[EE_MODE2] = (UCHAR)tmscsim[3]; - ptr[EE_DELAY] = 0; /* ?? */ - ptr[EE_TAG_CMD_NUM] = (UCHAR)tmscsim[4]; /* Tagged Comds */ - - /* Device Settings */ - for (id = 0; id < MAX_SCSI_ID; id++) - { - ptr[id<<2] = (UCHAR)tmscsim[2]; /* EE_MODE1 */ - ptr[(id<<2) + 1] = (UCHAR)tmscsim[1]; /* EE_Speed */ - }; - dc390_adapname = "AM53C974"; -} - -static void __init dc390_checkparams (void) -{ - PARSEDEBUG(printk(KERN_INFO "DC390: setup %08x %08x %08x %08x %08x\n", tmscsim[0],\ - tmscsim[1], tmscsim[2], tmscsim[3], tmscsim[4]);) - if (tmscsim[0] < 0 || tmscsim[0] > 7) /* modules-2.0.0 passes -1 as string */ - { - tmscsim[0] = 7; tmscsim[1] = 4; - tmscsim[2] = 9; tmscsim[3] = 15; - tmscsim[4] = 2; - printk (KERN_INFO "DC390: Using safe settings.\n"); - } - else - { - /* if (tmscsim[0] < 0 || tmscsim[0] > 7) tmscsim[0] = 7; */ - if (tmscsim[1] < 0 || tmscsim[1] > 7) tmscsim[1] = 4; - if (tmscsim[4] < 0 || tmscsim[4] > 5) tmscsim[4] = 4; - }; -}; -/* Override defaults on cmdline: - * tmscsim: AdaptID, MaxSpeed (Index), DevMode (Bitmapped), AdaptMode (Bitmapped) - */ -void __init dc390_setup (char *str, int *ints) -{ - int i; - for (i = 0; i < ints[0]; i++) - tmscsim[i] = ints[i+1]; - if (ints[0] > 5) - printk (KERN_NOTICE "DC390: ignore extra params!\n"); - /* dc390_checkparams (); */ -}; -#endif /* CONFIG_SCSI_DC390T_NOGENSUPP */ - - -static void __init dc390_EEpromOutDI( PDEVDECL, PUCHAR regval, UCHAR Carry ) -{ - UCHAR bval; - - bval = 0; - if(Carry) - { - bval = 0x40; - *regval = 0x80; - PCI_WRITE_CONFIG_BYTE(PDEV, *regval, bval); - } - udelay(160); - bval |= 0x80; - PCI_WRITE_CONFIG_BYTE(PDEV, *regval, bval); - udelay(160); - bval = 0; - PCI_WRITE_CONFIG_BYTE(PDEV, *regval, bval); - udelay(160); -} - - -static UCHAR __init dc390_EEpromInDO( PDEVDECL ) -{ - UCHAR bval; - - PCI_WRITE_CONFIG_BYTE(PDEV, 0x80, 0x80); - udelay(160); - PCI_WRITE_CONFIG_BYTE(PDEV, 0x80, 0x40); - udelay(160); - PCI_READ_CONFIG_BYTE(PDEV, 0x00, &bval); - if(bval == 0x22) - return(1); - else - return(0); -} - - -static USHORT __init dc390_EEpromGetData1( PDEVDECL ) -{ - UCHAR i; - UCHAR carryFlag; - USHORT wval; - - wval = 0; - for(i=0; i<16; i++) - { - wval <<= 1; - carryFlag = dc390_EEpromInDO(PDEV); - wval |= carryFlag; - } - return(wval); -} - - -static void __init dc390_Prepare( PDEVDECL, PUCHAR regval, UCHAR EEpromCmd ) -{ - UCHAR i,j; - UCHAR carryFlag; - - carryFlag = 1; - j = 0x80; - for(i=0; i<9; i++) - { - dc390_EEpromOutDI(PDEV,regval,carryFlag); - carryFlag = (EEpromCmd & j) ? 1 : 0; - j >>= 1; - } -} - - -static void __init dc390_ReadEEprom( PDEVDECL, PUSHORT ptr) -{ - UCHAR regval,cmd; - UCHAR i; - - cmd = EEPROM_READ; - for(i=0; i<0x40; i++) - { - dc390_EnDisableCE(ENABLE_CE, PDEV, ®val); - dc390_Prepare(PDEV, ®val, cmd++); - *ptr++ = dc390_EEpromGetData1(PDEV); - dc390_EnDisableCE(DISABLE_CE, PDEV, ®val); - } -} - - -static UCHAR __init dc390_CheckEEpromCheckSum( PDEVDECL, UCHAR index ) -{ - UCHAR i; - char EEbuf[128]; - USHORT wval, *ptr = (PUSHORT)EEbuf; - - dc390_ReadEEprom( PDEV, ptr ); - memcpy (dc390_eepromBuf[index], EEbuf, EE_ADAPT_SCSI_ID); - memcpy (&dc390_eepromBuf[index][EE_ADAPT_SCSI_ID], - &EEbuf[REAL_EE_ADAPT_SCSI_ID], EE_LEN - EE_ADAPT_SCSI_ID); - wval = 0; - for(i=0; i<0x40; i++, ptr++) - wval += *ptr; - return (wval == 0x1234 ? 0 : 1); -} - - /*********************************************************************** - * Function : static int DC390_init (struct Scsi_Host *host) + * Function : static int DC390_init (struct Scsi_Host *host, ...) * * Purpose : initialize the internal structures for a given SCSI host * - * Inputs : host - pointer to this host adapter's structure/ + * Inputs : host - pointer to this host adapter's structure + * io_port - IO ports mapped to this adapter + * Irq - IRQ assigned to this adpater + * PDEVDECL - PCI access handle + * index - Adapter index * - * Preconditions : when this function is called, the chip_type - * field of the pACB structure MUST have been set. + * Outputs: 0 on success, -1 on error * * Note: written in capitals, because the locking is only done here, * not in DC390_detect, called from outside ***********************************************************************/ -static int __init DC390_init (PSHT psht, ULONG io_port, UCHAR Irq, PDEVDECL, int index) +static int __init DC390_init (PSHT psht, ULONG io_port, UCHAR Irq, PDEVDECL, UCHAR index) { PSH psh; PACB pACB; @@ -1846,7 +1901,7 @@ static int __init DC390_init (PSHT psht, ULONG io_port, UCHAR Irq, PDEVDECL, int if( !psh ) return( -1 ); pACB = (PACB) psh->hostdata; - DC390_LOCK_INIT; + DC390_LOCKA_INIT; DC390_LOCK_ACB; #if 0 @@ -1862,37 +1917,21 @@ static int __init DC390_init (PSHT psht, ULONG io_port, UCHAR Irq, PDEVDECL, int } #endif - DEBUG0(printk("DC390: pSH = %8x,", (UINT) psh);) - DEBUG0(printk("DC390: Index %02i,", index);) + DEBUG0(printk(KERN_INFO "DC390: pSH = %8x,", (UINT) psh);) + DEBUG0(printk(" Index %02i,", index);) dc390_initACB( psh, io_port, Irq, index ); + pACB = (PACB) psh->hostdata; + PDEVSET; - DC390_read8_ (INT_Status, io_port); /* Reset Pending INT */ - if( !dc390_initAdapter( psh, io_port, Irq, index ) ) { - pACB = (PACB) psh->hostdata; - if( !dc390_pACB_start ) - { - dc390_pACB_start = pACB; - dc390_pACB_current = pACB; - pACB->pNextACB = (PACB) -1; - } - else - { - dc390_pACB_current->pNextACB = pACB; - dc390_pACB_current = pACB; - pACB->pNextACB = (PACB) -1; - } - - DEBUG0(printk("DC390: pACB = %8x, pDCBmap = %8x, pSRB_array = %8x\n",\ + DEBUG0(printk("\nDC390: pACB = %8x, pDCBmap = %8x, pSRB_array = %8x\n",\ (UINT) pACB, (UINT) pACB->DCBmap, (UINT) pACB->SRB_array);) DEBUG0(printk("DC390: ACB size= %4x, DCB size= %4x, SRB size= %4x\n",\ sizeof(DC390_ACB), sizeof(DC390_DCB), sizeof(DC390_SRB) );) - DC390_read8_ (INT_Status, io_port); /* Reset Pending INT */ - DC390_UNLOCK_ACB; return (0); } @@ -1960,7 +1999,6 @@ int __init DC390_detect (Scsi_Host_Template *psht) PDEVDECL0; UCHAR irq; UINT io_port; - UCHAR adaptCnt = 0; /* Number of boards detected */ DC390_IFLAGS DC390_DFLAGS DC390_LOCK_DRV; @@ -1972,29 +2010,36 @@ int __init DC390_detect (Scsi_Host_Template *psht) { DC390_LOCK_IO; /* Remove this when going to new eh */ PCI_GET_IO_AND_IRQ; - DEBUG0(printk(KERN_DEBUG "DC390(%i): IO_PORT=%04x,IRQ=%x\n", adaptCnt, (UINT) io_port, irq);) + DEBUG0(printk(KERN_INFO "DC390(%i): IO_PORT=%04x,IRQ=%x\n", dc390_adapterCnt, (UINT) io_port, irq);) - if( !DC390_init(psht, io_port, irq, PDEV, adaptCnt)) + if( !DC390_init(psht, io_port, irq, PDEV, dc390_adapterCnt)) { PCI_SET_MASTER; dc390_set_pci_cfg (PDEV); - adaptCnt++; + dc390_adapterCnt++; }; DC390_UNLOCK_IO; /* Remove when going to new eh */ } else printk (KERN_ERR "DC390: No PCI BIOS found!\n"); - if (adaptCnt) + if (dc390_adapterCnt) psht->proc_dir = &DC390_proc_scsi_tmscsim; - printk(KERN_INFO "DC390: %i adapters found\n", adaptCnt); - dc390_adapterCnt = adaptCnt; + printk(KERN_INFO "DC390: %i adapters found\n", dc390_adapterCnt); DC390_UNLOCK_DRV; - return( adaptCnt ); + return( dc390_adapterCnt ); } +/*********************************************************************** + * Functions: dc390_inquiry(), dc390_inquiry_done() + * + * Purpose: When changing speed etc., we have to issue an INQUIRY + * command to make sure, we agree upon the nego parameters + * with the device + ***********************************************************************/ + static void dc390_inquiry_done (Scsi_Cmnd* cmd) { printk (KERN_INFO "DC390: INQUIRY (ID %02x LUN %02x) returned %08x\n", @@ -2211,7 +2256,7 @@ int dc390_set_info (char *buffer, int length, PACB pACB) /* NegoPeriod */ if (*pos != '-') { - SCANF (pos, p0, dum, 76, 800); + SCANF (pos, p0, dum, 72, 800); pDCB->NegoPeriod = dum >> 2; if (pDCB->NegoPeriod != olddevmode) needs_inquiry++; if (!pos) goto ok; @@ -2367,8 +2412,6 @@ int dc390_set_info (char *buffer, int length, PACB pACB) * ********************************************************************/ -/* KG: proc_info taken from driver aha152x.c */ - #undef SPRINTF #define SPRINTF(args...) pos += sprintf(pos, ## args) @@ -2529,14 +2572,14 @@ int DC390_release(struct Scsi_Host *host) if (host->irq != IRQ_NONE) { for (irq_count = 0, pACB = dc390_pACB_start; - pACB && pACB != (PACB)-1; pACB = pACB->pNextACB) + pACB; pACB = pACB->pNextACB) { if ( pACB->IRQLevel == host->irq ) ++irq_count; } if (irq_count == 1) { - DEBUG0(printk(KERN_DEBUG "DC390: Free IRQ %i\n",host->irq);) + DEBUG0(printk(KERN_INFO "DC390: Free IRQ %i\n",host->irq);) free_irq(host->irq,NULL); } } diff --git a/drivers/scsi/tmscsim.h b/drivers/scsi/tmscsim.h index 6cee55837786..acc6526fdfec 100644 --- a/drivers/scsi/tmscsim.h +++ b/drivers/scsi/tmscsim.h @@ -3,7 +3,7 @@ ;* TEKRAM DC-390(T) PCI SCSI Bus Master Host Adapter * ;* Device Driver * ;***********************************************************************/ -/* $Id: tmscsim.h,v 2.1 1998/10/14 10:31:48 garloff Exp $ */ +/* $Id: tmscsim.h,v 2.4 1998/12/25 17:33:27 garloff Exp $ */ #ifndef _TMSCSIM_H #define _TMSCSIM_H @@ -95,15 +95,13 @@ UCHAR MsgOutBuf[6]; /* 0x48: */ SGL Segmentx; /* make a one entry of S/G list table */ -PUCHAR pMsgPtr; - UCHAR ScsiCmdLen; UCHAR ScsiPhase; UCHAR AdaptStatus; UCHAR TargetStatus; -/* 0x5c: */ +/* 0x58: */ UCHAR MsgCnt; UCHAR EndMessage; UCHAR RetryCnt; @@ -115,7 +113,7 @@ UCHAR SGIndex; UCHAR SRBStatus; //UCHAR IORBFlag; /*;81h-Reset, 2-retry */ -/* 0x64: */ +/* 0x60: */ }; @@ -218,14 +216,16 @@ spinlock_t lock; UCHAR sel_timeout; UCHAR glitch_cfg; -UCHAR reserved[2]; /* alignment */ +UCHAR MsgLen; +UCHAR Ignore_IRQ; /* Not used */ PDEVDECL1; /* Pointer to PCI cfg. space */ -/* 0x44/0x40: */ +/* 0x40/0x3c: */ ULONG Cmds; ULONG CmdInQ; ULONG CmdOutOfSRB; ULONG SelLost; + /* 0x50/0x4c: */ DC390_SRB TmpSRB; diff --git a/drivers/sound/Config.in b/drivers/sound/Config.in index dc8beb9610c3..53cf0ba76655 100644 --- a/drivers/sound/Config.in +++ b/drivers/sound/Config.in @@ -131,7 +131,7 @@ if [ "$CONFIG_SOUND_OSS" = "y" -o "$CONFIG_SOUND_OSS" = "m" ]; then int 'PSS MIDI IRQ 3, 4, 5, 7, 9, 10, 11, 12' CONFIG_PSS_MPU_IRQ 9 bool ' Have DSPxxx.LD firmware file' CONFIG_PSS_HAVE_BOOT if [ "$CONFIG_PSS_HAVE_BOOT" = "y" ]; then - string ' Full pathname of DSPxxx.LD firmware file' CONFIG_PSS_BOOT_FILE + string ' Full pathname of DSPxxx.LD firmware file' CONFIG_PSS_BOOT_FILE /etc/sound/dsp001.ld fi fi if [ "$CONFIG_SOUND_PSS" = "y" -o "$CONFIG_SOUND_PSS" = "m" ]; then @@ -168,7 +168,7 @@ if [ "$CONFIG_SOUND_OSS" = "y" -o "$CONFIG_SOUND_OSS" = "m" ]; then int 'TRIX SB DMA 1 or 3' CONFIG_TRIX_SB_DMA 1 bool ' Have TRXPRO.HEX firmware file' CONFIG_TRIX_HAVE_BOOT if [ "$CONFIG_TRIX_HAVE_BOOT" = "y" ]; then - string ' Full pathname of TRXPRO.HEX firmware file' CONFIG_TRIX_BOOT_FILE + string ' Full pathname of TRXPRO.HEX firmware file' CONFIG_TRIX_BOOT_FILE /etc/sound/trxpro.hex fi fi @@ -185,7 +185,7 @@ if [ "$CONFIG_SOUND_OSS" = "y" -o "$CONFIG_SOUND_OSS" = "m" ]; then int 'MAD16 MIDI IRQ 5, 7, 9 or 10' CONFIG_MAD16_MPU_IRQ 9 fi - dep_tristate 'Full support for Turtle Beach WaveFront (Tropez Plus, Tropez, Maui) synth/soundcards' CONFIG_SOUND_WAVEFRONT $CONFIG_SOUND_OSS + dep_tristate 'Full support for Turtle Beach WaveFront (Tropez Plus, Tropez, Maui) synth/soundcards' CONFIG_SOUND_WAVEFRONT $CONFIG_SOUND_OSS m if [ "$CONFIG_SOUND_WAVEFRONT" = "y" ]; then hex 'I/O base for WaveFront 210, 230, 260, 290, 300, 320, 338 or 330' CONFIG_WAVEFRONT_BASE 330 int 'WaveFront IRQ 5, 9, 12 or 15' CONFIG_WAVEFRONT_IRQ 9 @@ -218,7 +218,7 @@ if [ "$CONFIG_SOUND_OSS" = "y" -o "$CONFIG_SOUND_OSS" = "m" ]; then int 'Maui IRQ 5, 9, 12 or 15' CONFIG_MAUI_IRQ 9 bool ' Have OSWF.MOT firmware file' CONFIG_MAUI_HAVE_BOOT if [ "$CONFIG_MAUI_HAVE_BOOT" = "y" ]; then - string ' Full pathname of OSWF.MOT firmware file' CONFIG_MAUI_BOOT_FILE + string ' Full pathname of OSWF.MOT firmware file' CONFIG_MAUI_BOOT_FILE /etc/sound/oswf.mot fi fi diff --git a/drivers/sound/ad1848.c b/drivers/sound/ad1848.c index af172bac2137..240e0dd68a11 100644 --- a/drivers/sound/ad1848.c +++ b/drivers/sound/ad1848.c @@ -71,6 +71,7 @@ typedef struct #define MD_4232 5 #define MD_C930 6 #define MD_IWAVE 7 +#define MD_4235 8 /* Crystal Audio CS4235 */ /* Mixer parameters */ int recmask; @@ -111,7 +112,7 @@ static int timer_installed = -1; #endif -static int ad_format_mask[8 /*devc->model */ ] = +static int ad_format_mask[9 /*devc->model */ ] = { 0, AFMT_U8 | AFMT_S16_LE | AFMT_MU_LAW | AFMT_A_LAW, @@ -120,7 +121,8 @@ static int ad_format_mask[8 /*devc->model */ ] = AFMT_U8 | AFMT_S16_LE | AFMT_MU_LAW | AFMT_A_LAW, /* AD1845 */ AFMT_U8 | AFMT_S16_LE | AFMT_MU_LAW | AFMT_A_LAW | AFMT_S16_BE | AFMT_IMA_ADPCM, AFMT_U8 | AFMT_S16_LE | AFMT_MU_LAW | AFMT_A_LAW | AFMT_S16_BE | AFMT_IMA_ADPCM, - AFMT_U8 | AFMT_S16_LE | AFMT_MU_LAW | AFMT_A_LAW | AFMT_S16_BE | AFMT_IMA_ADPCM + AFMT_U8 | AFMT_S16_LE | AFMT_MU_LAW | AFMT_A_LAW | AFMT_S16_BE | AFMT_IMA_ADPCM, + AFMT_U8 | AFMT_S16_LE /* CS4235 */ }; static ad1848_info adev_info[MAX_AUDIO_DEV]; @@ -1594,103 +1596,107 @@ int ad1848_detect(int io_base, int *ad_flags, int *osp) ad_write(devc, 25, ~tmp1); /* Invert all bits */ if ((ad_read(devc, 25) & 0xe7) == (tmp1 & 0xe7)) { - int id, full_id; + int id; /* * It's at least CS4231 */ - devc->chip_name = "CS4231"; - devc->model = MD_4231; - /* * It could be an AD1845 or CS4231A as well. * CS4231 and AD1845 report the same revision info in I25 * while the CS4231A reports different. */ - id = ad_read(devc, 25) & 0xe7; - full_id = ad_read(devc, 25); - if (id == 0x80) /* Device busy??? */ - id = ad_read(devc, 25) & 0xe7; - if (id == 0x80) /* Device still busy??? */ - id = ad_read(devc, 25) & 0xe7; + id = ad_read(devc, 25); + if ((id & 0xe7) == 0x80) /* Device busy??? */ + id = ad_read(devc, 25); + if ((id & 0xe7) == 0x80) /* Device still busy??? */ + id = ad_read(devc, 25); DDB(printk("ad1848_detect() - step J (%02x/%02x)\n", id, ad_read(devc, 25))); - switch (id) + if ((id & 0xe7) == 0x80) { + /* + * It must be a CS4231 or AD1845. The register I23 of + * CS4231 is undefined and it appears to be read only. + * AD1845 uses I23 for setting sample rate. Assume + * the chip is AD1845 if I23 is changeable. + */ + + unsigned char tmp = ad_read(devc, 23); + ad_write(devc, 23, ~tmp); + + if (interwave) + { + devc->model = MD_IWAVE; + devc->chip_name = "IWave"; + } + else if (ad_read(devc, 23) != tmp) /* AD1845 ? */ + { + devc->chip_name = "AD1845"; + devc->model = MD_1845; + } + else if (cs4248_flag) + { + if (ad_flags) + *ad_flags |= AD_F_CS4248; + devc->chip_name = "CS4248"; + devc->model = MD_1848; + ad_write(devc, 12, ad_read(devc, 12) & ~0x40); /* Mode2 off */ + } + ad_write(devc, 23, tmp); /* Restore */ + } + else { - - case 0xa0: - devc->chip_name = "CS4231A"; - devc->model = MD_4231A; + switch (id & 0x1f) { + case 3: /* CS4236/CS4235 */ + { + int xid; + ad_write(devc, 12, ad_read(devc, 12) | 0x60); /* switch to mode 3 */ + ad_write(devc, 23, 0x9c); /* select extended register 25 */ + xid = inb(io_Indexed_Data(devc)); + ad_write(devc, 12, ad_read(devc, 12) & ~0x60); /* back to mode 0 */ + if ((xid & 0x1f) == 0x1d) { + devc->chip_name = "CS4235"; + devc->model = MD_4235; + } else { + devc->chip_name = "CS4236"; + devc->model = MD_4232; + } + } break; - case 0xa2: + case 2: /* CS4232/CS4232A */ devc->chip_name = "CS4232"; devc->model = MD_4232; break; - - case 0xb2: - devc->chip_name = "CS4232A"; - devc->model = MD_4232; - break; - - case 0x03: - case 0x83: - devc->chip_name = "CS4236"; - devc->model = MD_4232; - break; - - case 0x41: - devc->chip_name = "CS4236B"; - devc->model = MD_4232; - break; - - case 0x80: + + case 0: + if ((id & 0xe0) == 0xa0) { - /* - * It must be a CS4231 or AD1845. The register I23 of - * CS4231 is undefined and it appears to be read only. - * AD1845 uses I23 for setting sample rate. Assume - * the chip is AD1845 if I23 is changeable. - */ - - unsigned char tmp = ad_read(devc, 23); - ad_write(devc, 23, ~tmp); - - if (interwave) - { - devc->model = MD_IWAVE; - devc->chip_name = "IWave"; - } - else if (ad_read(devc, 23) != tmp) /* AD1845 ? */ - { - devc->chip_name = "AD1845"; - devc->model = MD_1845; - } - else if (cs4248_flag) - { - if (ad_flags) - *ad_flags |= AD_F_CS4248; - devc->chip_name = "CS4248"; - devc->model = MD_1848; - ad_write(devc, 12, ad_read(devc, 12) & ~0x40); /* Mode2 off */ - } - ad_write(devc, 23, tmp); /* Restore */ + devc->chip_name = "CS4231A"; + devc->model = MD_4231A; + } + else + { + devc->chip_name = "CS4321"; + devc->model = MD_4231; } break; - default: /* Assume CS4231 or OPTi 82C930 */ + default: /* maybe */ DDB(printk("ad1848: I25 = %02x/%02x\n", ad_read(devc, 25), ad_read(devc, 25) & 0xe7)); - if (optiC930) - { - devc->chip_name = "82C930"; - devc->model = MD_C930; - } + if (optiC930) + { + devc->chip_name = "82C930"; + devc->model = MD_C930; + } else { + devc->chip_name = "CS4231"; devc->model = MD_4231; } + } } } ad_write(devc, 25, tmp1); /* Restore bits */ diff --git a/drivers/sound/cs4232.c b/drivers/sound/cs4232.c index 4d529bcaf5e1..11feddcccb0b 100644 --- a/drivers/sound/cs4232.c +++ b/drivers/sound/cs4232.c @@ -369,9 +369,6 @@ int init_module(void) cfg.dma = dma; cfg.dma2 = dma2; - if (probe_cs4232(&cfg) == 0) - return -ENODEV; - mpu_cfg.io_base = -1; mpu_cfg.irq = -1; @@ -381,6 +378,9 @@ int init_module(void) probe_cs4232_mpu(&mpu_cfg); /* Bug always returns 0 not OK -- AC */ } + if (probe_cs4232(&cfg) == 0) + return -ENODEV; + attach_cs4232(&cfg); if (mpuio != -1 && mpuirq != -1) { diff --git a/drivers/sound/es1370.c b/drivers/sound/es1370.c index 7471afcc3010..b202c38f0403 100644 --- a/drivers/sound/es1370.c +++ b/drivers/sound/es1370.c @@ -80,6 +80,7 @@ * 08.10.98 0.14 Joystick support fixed * -- Oliver Neukum * 10.12.98 0.15 Fix drain_dac trying to wait on not yet initialized DMA + * 16.12.98 0.16 Don't wake up app until there are fragsize bytes to read/write * * some important things missing in Ensoniq documentation: * @@ -603,17 +604,14 @@ static void es1370_update_ptr(struct es1370_state *s) diff = get_hwptr(s, &s->dma_adc, ES1370_REG_ADC_FRAMECNT); s->dma_adc.total_bytes += diff; s->dma_adc.count += diff; - if (s->dma_adc.mapped) { - if (s->dma_adc.count >= (signed)s->dma_adc.fragsize) - wake_up(&s->dma_adc.wait); - } else { + if (s->dma_adc.count >= (signed)s->dma_adc.fragsize) + wake_up(&s->dma_adc.wait); + if (!s->dma_adc.mapped) { if (s->dma_adc.count > (signed)(s->dma_adc.dmasize - ((3 * s->dma_adc.fragsize) >> 1))) { s->ctrl &= ~CTRL_ADC_EN; outl(s->ctrl, s->io+ES1370_REG_CONTROL); s->dma_adc.error++; } - if (s->dma_adc.count > 0) - wake_up(&s->dma_adc.wait); } } /* update DAC1 pointer */ @@ -635,7 +633,7 @@ static void es1370_update_ptr(struct es1370_state *s) s->dma_dac1.fragsize, (s->sctrl & SCTRL_P1SEB) ? 0 : 0x80); s->dma_dac1.endcleared = 1; } - if (s->dma_dac1.count < (signed)s->dma_dac1.dmasize) + if (s->dma_dac1.count + (signed)s->dma_dac1.fragsize <= (signed)s->dma_dac1.dmasize) wake_up(&s->dma_dac1.wait); } } @@ -658,7 +656,7 @@ static void es1370_update_ptr(struct es1370_state *s) s->dma_dac2.fragsize, (s->sctrl & SCTRL_P2SEB) ? 0 : 0x80); s->dma_dac2.endcleared = 1; } - if (s->dma_dac2.count < (signed)s->dma_dac2.dmasize) + if (s->dma_dac2.count + (signed)s->dma_dac2.fragsize <= (signed)s->dma_dac2.dmasize) wake_up(&s->dma_dac2.wait); } } @@ -1186,20 +1184,15 @@ static unsigned int es1370_poll(struct file *file, struct poll_table_struct *wai spin_lock_irqsave(&s->lock, flags); es1370_update_ptr(s); if (file->f_mode & FMODE_READ) { - if (s->dma_adc.mapped) { - if (s->dma_adc.count >= (signed)s->dma_adc.fragsize) - mask |= POLLIN | POLLRDNORM; - } else { - if (s->dma_adc.count > 0) - mask |= POLLIN | POLLRDNORM; - } + if (s->dma_adc.count >= (signed)s->dma_adc.fragsize) + mask |= POLLIN | POLLRDNORM; } if (file->f_mode & FMODE_WRITE) { if (s->dma_dac2.mapped) { if (s->dma_dac2.count >= (signed)s->dma_dac2.fragsize) mask |= POLLOUT | POLLWRNORM; } else { - if ((signed)s->dma_dac2.dmasize > s->dma_dac2.count) + if ((signed)s->dma_dac2.dmasize >= s->dma_dac2.count + (signed)s->dma_dac2.fragsize) mask |= POLLOUT | POLLWRNORM; } } @@ -1704,7 +1697,7 @@ static unsigned int es1370_poll_dac(struct file *file, struct poll_table_struct if (s->dma_dac1.count >= (signed)s->dma_dac1.fragsize) mask |= POLLOUT | POLLWRNORM; } else { - if ((signed)s->dma_dac1.dmasize > s->dma_dac1.count) + if ((signed)s->dma_dac1.dmasize >= s->dma_dac1.count + (signed)s->dma_dac1.fragsize) mask |= POLLOUT | POLLWRNORM; } spin_unlock_irqrestore(&s->lock, flags); @@ -2277,7 +2270,7 @@ __initfunc(int init_es1370(void)) if (!pci_present()) /* No PCI bus in this machine! */ return -ENODEV; - printk(KERN_INFO "es1370: version v0.15 time " __TIME__ " " __DATE__ "\n"); + printk(KERN_INFO "es1370: version v0.16 time " __TIME__ " " __DATE__ "\n"); while (index < NR_DEVICE && (pcidev = pci_find_device(PCI_VENDOR_ID_ENSONIQ, PCI_DEVICE_ID_ENSONIQ_ES1370, pcidev))) { if (pcidev->base_address[0] == 0 || diff --git a/drivers/sound/es1371.c b/drivers/sound/es1371.c index 3a4ceb8c9ca6..e759ae819033 100644 --- a/drivers/sound/es1371.c +++ b/drivers/sound/es1371.c @@ -50,6 +50,8 @@ * 27.10.98 0.5 Fix joystick support * -- Oliver Neukum (c188@org.chemie.uni-muenchen.de) * 10.12.98 0.6 Fix drain_dac trying to wait on not yet initialized DMA + * 23.12.98 0.7 Fix a few f_file & FMODE_ bugs + * Don't wake up app until there are fragsize bytes to read/write * */ @@ -837,17 +839,14 @@ static void es1371_update_ptr(struct es1371_state *s) diff = get_hwptr(s, &s->dma_adc, ES1371_REG_ADC_FRAMECNT); s->dma_adc.total_bytes += diff; s->dma_adc.count += diff; - if (s->dma_adc.mapped) { - if (s->dma_adc.count >= s->dma_adc.fragsize) - wake_up(&s->dma_adc.wait); - } else { + if (s->dma_adc.count >= (signed)s->dma_adc.fragsize) + wake_up(&s->dma_adc.wait); + if (!s->dma_adc.mapped) { if (s->dma_adc.count > (signed)(s->dma_adc.dmasize - ((3 * s->dma_adc.fragsize) >> 1))) { s->ctrl &= ~CTRL_ADC_EN; outl(s->ctrl, s->io+ES1371_REG_CONTROL); s->dma_adc.error++; } - if (s->dma_adc.count > 0) - wake_up(&s->dma_adc.wait); } } /* update DAC1 pointer */ @@ -869,7 +868,7 @@ static void es1371_update_ptr(struct es1371_state *s) s->dma_dac1.fragsize, (s->sctrl & SCTRL_P1SEB) ? 0 : 0x80); s->dma_dac1.endcleared = 1; } - if (s->dma_dac1.count < (signed)s->dma_dac1.dmasize) + if (s->dma_dac1.count + (signed)s->dma_dac1.fragsize <= (signed)s->dma_dac1.dmasize) wake_up(&s->dma_dac1.wait); } } @@ -892,7 +891,7 @@ static void es1371_update_ptr(struct es1371_state *s) s->dma_dac2.fragsize, (s->sctrl & SCTRL_P2SEB) ? 0 : 0x80); s->dma_dac2.endcleared = 1; } - if (s->dma_dac2.count < (signed)s->dma_dac2.dmasize) + if (s->dma_dac2.count + (signed)s->dma_dac2.fragsize <= (signed)s->dma_dac2.dmasize) wake_up(&s->dma_dac2.wait); } } @@ -1625,27 +1624,22 @@ static unsigned int es1371_poll(struct file *file, struct poll_table_struct *wai unsigned int mask = 0; VALIDATE_STATE(s); - if (file->f_flags & FMODE_WRITE) + if (file->f_mode & FMODE_WRITE) poll_wait(file, &s->dma_dac2.wait, wait); - if (file->f_flags & FMODE_READ) + if (file->f_mode & FMODE_READ) poll_wait(file, &s->dma_adc.wait, wait); spin_lock_irqsave(&s->lock, flags); es1371_update_ptr(s); - if (file->f_flags & FMODE_READ) { - if (s->dma_adc.mapped) { + if (file->f_mode & FMODE_READ) { if (s->dma_adc.count >= (signed)s->dma_adc.fragsize) mask |= POLLIN | POLLRDNORM; - } else { - if (s->dma_adc.count > 0) - mask |= POLLIN | POLLRDNORM; - } } - if (file->f_flags & FMODE_WRITE) { + if (file->f_mode & FMODE_WRITE) { if (s->dma_dac2.mapped) { if (s->dma_dac2.count >= (signed)s->dma_dac2.fragsize) mask |= POLLOUT | POLLWRNORM; } else { - if ((signed)s->dma_dac2.dmasize > s->dma_dac2.count) + if ((signed)s->dma_dac2.dmasize >= s->dma_dac2.count + (signed)s->dma_dac2.fragsize) mask |= POLLOUT | POLLWRNORM; } } @@ -2046,11 +2040,11 @@ static int es1371_release(struct inode *inode, struct file *file) if (file->f_mode & FMODE_WRITE) drain_dac2(s, file->f_flags & O_NONBLOCK); down(&s->open_sem); - if (file->f_flags & FMODE_WRITE) { + if (file->f_mode & FMODE_WRITE) { stop_dac2(s); dealloc_dmabuf(&s->dma_dac2); } - if (file->f_flags & FMODE_READ) { + if (file->f_mode & FMODE_READ) { stop_adc(s); dealloc_dmabuf(&s->dma_adc); } @@ -2150,7 +2144,7 @@ static unsigned int es1371_poll_dac(struct file *file, struct poll_table_struct if (s->dma_dac1.count >= (signed)s->dma_dac1.fragsize) mask |= POLLOUT | POLLWRNORM; } else { - if ((signed)s->dma_dac1.dmasize > s->dma_dac1.count) + if ((signed)s->dma_dac1.dmasize >= s->dma_dac1.count + (signed)s->dma_dac1.fragsize) mask |= POLLOUT | POLLWRNORM; } spin_unlock_irqrestore(&s->lock, flags); @@ -2540,16 +2534,16 @@ static unsigned int es1371_midi_poll(struct file *file, struct poll_table_struct unsigned int mask = 0; VALIDATE_STATE(s); - if (file->f_flags & FMODE_WRITE) + if (file->f_mode & FMODE_WRITE) poll_wait(file, &s->midi.owait, wait); - if (file->f_flags & FMODE_READ) + if (file->f_mode & FMODE_READ) poll_wait(file, &s->midi.iwait, wait); spin_lock_irqsave(&s->lock, flags); - if (file->f_flags & FMODE_READ) { + if (file->f_mode & FMODE_READ) { if (s->midi.icnt > 0) mask |= POLLIN | POLLRDNORM; } - if (file->f_flags & FMODE_WRITE) { + if (file->f_mode & FMODE_WRITE) { if (s->midi.ocnt < MIDIOUTBUF) mask |= POLLOUT | POLLWRNORM; } @@ -2716,7 +2710,7 @@ __initfunc(int init_es1371(void)) if (!pci_present()) /* No PCI bus in this machine! */ return -ENODEV; - printk(KERN_INFO "es1371: version v0.6 time " __TIME__ " " __DATE__ "\n"); + printk(KERN_INFO "es1371: version v0.7 time " __TIME__ " " __DATE__ "\n"); while (index < NR_DEVICE && (pcidev = pci_find_device(PCI_VENDOR_ID_ENSONIQ, PCI_DEVICE_ID_ENSONIQ_ES1371, pcidev))) { if (pcidev->base_address[0] == 0 || diff --git a/drivers/sound/lowlevel/Config.in b/drivers/sound/lowlevel/Config.in index 36928af081c8..09a9f7249621 100644 --- a/drivers/sound/lowlevel/Config.in +++ b/drivers/sound/lowlevel/Config.in @@ -6,6 +6,7 @@ if [ "$CONFIG_SOUND_OSS" = "y" -o "$CONFIG_SOUND" = "m" ]; then dep_tristate 'Gallant Audio Cards (SC-6000 and SC-6600 based)' CONFIG_AEDSP16 $CONFIG_SOUND_OSS if [ "$CONFIG_AEDSP16" = "y" -o "$CONFIG_AEDSP16" = "m" ]; then hex ' I/O base for Audio Excel DSP 16 220 or 240' CONFIG_AEDSP16_BASE 220 + hex 'I/O base for MPU401 Check from manual of the card' CONFIG_MPU_BASE 330 fi if [ "$CONFIG_AEDSP16" = "y" -o "$CONFIG_AEDSP16" = "m" ]; then @@ -23,9 +24,9 @@ if [ "$CONFIG_SOUND_OSS" = "y" -o "$CONFIG_SOUND" = "m" ]; then bool 'Audio Excel DSP 16 (SBPro emulation)' CONFIG_AEDSP16_SBPRO if [ "$CONFIG_AEDSP16_SBPRO" = "y" ]; then comment 'Audio Excel DSP 16 [Sound Blaster Pro]' - hex 'I/O base for Audio Excel DSP 16 220, 240' CONFIG_AEDSP16_BASE $CONFIG_SB_BASE - int 'Audio Excel DSP 16 IRQ 5, 7, 9, 10, 11' CONFIG_AEDSP16_SB_IRQ $CONFIG_SB_IRQ - int 'Audio Excel DSP 16 DMA 0, 1 or 3' CONFIG_AEDSP16_SB_DMA $CONFIG_SB_DMA + hex 'I/O base for Audio Excel DSP 16 220, 240' CONFIG_AEDSP16_BASE $CONFIG_SB_BASE 220 + int 'Audio Excel DSP 16 IRQ 5, 7, 9, 10, 11' CONFIG_AEDSP16_SB_IRQ $CONFIG_SB_IRQ 5 + int 'Audio Excel DSP 16 DMA 0, 1 or 3' CONFIG_AEDSP16_SB_DMA $CONFIG_SB_DMA 0 fi fi fi @@ -36,8 +37,8 @@ if [ "$CONFIG_SOUND_OSS" = "y" -o "$CONFIG_SOUND" = "m" ]; then if [ "$CONFIG_AEDSP16_MSS" = "y" ]; then comment 'Audio Excel DSP 16 [Microsoft Sound System]' hex 'I/O base for Audio Excel DSP 16 220 or 240' CONFIG_AEDSP16_BASE 220 - int 'Audio Excel DSP 16 IRQ 5, 7, 9, 10, 11' CONFIG_AEDSP16_MSS_IRQ $CONFIG_MSS_IRQ - int 'Audio Excel DSP 16 DMA 0, 1 or 3' CONFIG_AEDSP16_MSS_DMA $CONFIG_MSS_DMA + int 'Audio Excel DSP 16 IRQ 5, 7, 9, 10, 11' CONFIG_AEDSP16_MSS_IRQ $CONFIG_MSS_IRQ 5 + int 'Audio Excel DSP 16 DMA 0, 1 or 3' CONFIG_AEDSP16_MSS_DMA $CONFIG_MSS_DMA 1 fi fi fi diff --git a/drivers/sound/opl3sa.c b/drivers/sound/opl3sa.c index 8be3b91a92d5..341438748842 100644 --- a/drivers/sound/opl3sa.c +++ b/drivers/sound/opl3sa.c @@ -260,6 +260,7 @@ void unload_opl3sa_wss(struct address_info *hw_config) hw_config->dma, dma2, 0); + sound_unload_audiodev(hw_config->slots[0]); } void unload_opl3sa_mpu(struct address_info *hw_config) diff --git a/drivers/sound/sb.h b/drivers/sound/sb.h index dc864646e14c..16fcba273d3a 100644 --- a/drivers/sound/sb.h +++ b/drivers/sound/sb.h @@ -48,6 +48,7 @@ #define MDL_ES1868MIDI 14 /* MIDI port of ESS1868 */ #define MDL_AEDSP 15 /* Audio Excel DSP 16 */ +#define SUBMDL_ES18XX 0x10 /* Introduced a subtype ESS 18XX (Rolf) */ #define SUBMDL_ALS007 42 /* ALS-007 differs from SB16 only in mixer */ /* register assignment */ /* diff --git a/drivers/sound/sb_common.c b/drivers/sound/sb_common.c index bb8063ab5efa..b05d7eb2d915 100644 --- a/drivers/sound/sb_common.c +++ b/drivers/sound/sb_common.c @@ -13,6 +13,8 @@ /* * Daniel J. Rodriksson: Modified sbintr to handle 8 and 16 bit interrupts * for full duplex support ( only sb16 by now ) + * Rolf Fokkens: Added (BETA?) support for ES18XX chips. + * Which means: you can adjust the recording levels. */ #include #include @@ -484,6 +486,24 @@ static void relocate_ess1688(sb_devc * devc) #endif } +/* + * ESS technology describes a detection scheme in their docs. It involves + * fiddling with the bits in certain mixer registers. ess_probe is supposed + * to help. + */ +static int ess_probe (sb_devc * devc, int reg, int xorval) +{ + int val1, val2, val3; + + val1 = sb_getmixer (devc, reg); + val2 = val1 ^ xorval; + sb_setmixer (devc, reg, val2); + val3 = sb_getmixer (devc, reg); + sb_setmixer (devc, reg, val1); + + return (val2 == val3); +} + static int ess_init(sb_devc * devc, struct address_info *hw_config) { unsigned char cfg, irq_bits = 0, dma_bits = 0; @@ -522,12 +542,30 @@ static int ess_init(sb_devc * devc, struct address_info *hw_config) devc->model = MDL_SBPRO; return 1; } - else if (ess_major == 0x68 && (ess_minor & 0xf0) == 0x80) + + /* + * This the detection heuristic of ESS technology, though somewhat + * changed to actually make it work :-) + * This is the most BETA part of the software: Will it work? + */ + devc->model = MDL_ESS; + devc->submodel = ess_minor & 0x0f; + + if (ess_major == 0x68 && (ess_minor & 0xf0) == 0x80) { char *chip = "ES688"; - if ((ess_minor & 0x0f) >= 8) - chip = "ES1688"; + if ((ess_minor & 0x0f) >= 8) { + if ( !ess_probe (devc, 0x64, (1 << 3)) + && ess_probe (devc, 0x70, 0x7f)) { + chip = "ES18XX"; + devc->submodel = SUBMDL_ES18XX; + } else { + chip = "ES1688"; + }; + } else { + chip = "ES688"; + }; sprintf(name,"ESS %s AudioDrive (rev %d)", chip, ess_minor & 0x0f); @@ -535,8 +573,6 @@ static int ess_init(sb_devc * devc, struct address_info *hw_config) else strcpy(name, "Jazz16"); - devc->model = MDL_ESS; - devc->submodel = ess_minor & 0x0f; hw_config->name = name; sb_dsp_reset(devc); /* Turn on extended mode */ @@ -998,19 +1034,28 @@ void sb_dsp_unload(struct address_info *hw_config, int sbmpu) /* * Mixer access routines + * + * ES18XX modifications: some mixer registers reside in the + * range above 0xa0. These must be accessed in another way. */ void sb_setmixer(sb_devc * devc, unsigned int port, unsigned int value) { unsigned long flags; + /* MDB(printk("ESS: write port %x: %x\n", port, value)); */ + save_flags(flags); cli(); - outb(((unsigned char) (port & 0xff)), MIXER_ADDR); - - udelay(20); - outb(((unsigned char) (value & 0xff)), MIXER_DATA); - udelay(20); + if (devc->model == MDL_ESS && port >= 0xa0 && port <= 0xbf) { + ess_write (devc, port, value); + } else { + outb(((unsigned char) (port & 0xff)), MIXER_ADDR); + + udelay(20); + outb(((unsigned char) (value & 0xff)), MIXER_DATA); + udelay(20); + }; restore_flags(flags); } diff --git a/drivers/sound/sb_mixer.c b/drivers/sound/sb_mixer.c index aaab4907d3c3..a96c4e392118 100644 --- a/drivers/sound/sb_mixer.c +++ b/drivers/sound/sb_mixer.c @@ -13,6 +13,25 @@ * * * Thomas Sailer : ioctl code reworked (vmalloc/vfree removed) + * Rolf Fokkens : ES18XX recording level support + */ + +/* + * About ES18XX support: + * + * The standard ES688 support doesn't take care of the ES18XX recording + * levels very well. Whenever a device is selected (recmask) for recording + * it's recording level is loud, and it cannot be changed. + * + * The ES18XX has separate registers to controll the recording levels. The + * ES18XX specific software makes these level the same as their corresponding + * playback levels, unless recmask says they aren't recorded. In tha latter + * case the recording volumens are 0. + * + * Now recording levels of inputs can be controlled, by changing the playback + * levels. + * Futhermore several devices can be recorded together (which is not possible + * with the ES688. */ #include @@ -78,22 +97,62 @@ void smw_mixer_init(sb_devc * devc) sb_mixer_reset(devc); } -static int smw_mixer_set(sb_devc * devc, int dev, int value) +static int common_mixer_set(sb_devc * devc, int dev, int left, int right) { - int left = value & 0x000000ff; - int right = (value & 0x0000ff00) >> 8; - int reg, val; + int regoffs; + unsigned char val; - if (left > 100) - left = 100; - if (right > 100) - right = 100; + regoffs = (*devc->iomap)[dev][LEFT_CHN].regno; - if (dev > 31) + if (regoffs == 0) return -EINVAL; - if (!(devc->supported_devices & (1 << dev))) /* Not supported */ - return -EINVAL; + val = sb_getmixer(devc, regoffs); + change_bits(devc, &val, dev, LEFT_CHN, left); + + devc->levels[dev] = left | (left << 8); + + if ((*devc->iomap)[dev][RIGHT_CHN].regno != regoffs) /* + * Change register + */ + { + sb_setmixer(devc, regoffs, val); /* + * Save the old one + */ + regoffs = (*devc->iomap)[dev][RIGHT_CHN].regno; + + if (regoffs == 0) + return left | (left << 8); /* + * Just left channel present + */ + + val = sb_getmixer(devc, regoffs); /* + * Read the new one + */ + } + change_bits(devc, &val, dev, RIGHT_CHN, right); + + sb_setmixer(devc, regoffs, val); + + devc->levels[dev] = left | (right << 8); + return left | (right << 8); +} + +/* + * Changing input levels at ES18XX means having to take care of recording + * levels of recorded inputs too! + */ +static int es18XX_mixer_set(sb_devc * devc, int dev, int left, int right) +{ + if (devc->recmask & (1 << dev)) { + common_mixer_set(devc, dev + ES18XX_MIXER_RECDIFF, left, right); + } + return common_mixer_set(devc, dev, left, right); +} + +static int smw_mixer_set(sb_devc * devc, int dev, int left, int right) +{ + int reg, val; switch (dev) { @@ -134,12 +193,6 @@ static int sb_mixer_set(sb_devc * devc, int dev, int value) int left = value & 0x000000ff; int right = (value & 0x0000ff00) >> 8; - int regoffs; - unsigned char val; - - if (devc->model == MDL_SMW) - return smw_mixer_set(devc, dev, value); - if (left > 100) left = 100; if (right > 100) @@ -153,47 +206,60 @@ static int sb_mixer_set(sb_devc * devc, int dev, int value) */ return -EINVAL; - regoffs = (*devc->iomap)[dev][LEFT_CHN].regno; - - if (regoffs == 0) - return -EINVAL; - - val = sb_getmixer(devc, regoffs); - change_bits(devc, &val, dev, LEFT_CHN, left); - - devc->levels[dev] = left | (left << 8); - - if ((*devc->iomap)[dev][RIGHT_CHN].regno != regoffs) /* - * Change register - */ - { - sb_setmixer(devc, regoffs, val); /* - * Save the old one - */ - regoffs = (*devc->iomap)[dev][RIGHT_CHN].regno; - - if (regoffs == 0) - return left | (left << 8); /* - * Just left channel present - */ - - val = sb_getmixer(devc, regoffs); /* - * Read the new one - */ + /* Differentiate dependong on the chipsets */ + switch (devc->model) { + case MDL_SMW: + return smw_mixer_set(devc, dev, left, right); + break; + case MDL_ESS: + if (devc->submodel == SUBMDL_ES18XX) { + return es18XX_mixer_set(devc, dev, left, right); + } + break; } - change_bits(devc, &val, dev, RIGHT_CHN, right); - - sb_setmixer(devc, regoffs, val); - devc->levels[dev] = left | (right << 8); - return left | (right << 8); + return common_mixer_set(devc, dev, left, right); } +/* + * set_recsrc doesn't apply to ES18XX + */ static void set_recsrc(sb_devc * devc, int src) { sb_setmixer(devc, RECORD_SRC, (sb_getmixer(devc, RECORD_SRC) & ~7) | (src & 0x7)); } +/* + * Changing the recmask on a ES18XX means: + * (1) Find the differences + * (2) For "turned-on" inputs: make the recording level the playback level + * (3) For "turned-off" inputs: make the recording level zero + */ +static int es18XX_set_recmask(sb_devc * devc, int mask) +{ + int i, i_mask, cur_mask, diff_mask; + int value, left, right; + + cur_mask = devc->recmask; + diff_mask = (cur_mask ^ mask); + + for (i = 0; i < 32; i++) { + i_mask = (1 << i); + if (diff_mask & i_mask) { + if (mask & i_mask) { /* Turn it on (2) */ + value = devc->levels[i]; + left = value & 0x000000ff; + right = (value & 0x0000ff00) >> 8; + } else { /* Turn it off (3) */ + left = 0; + right = 0; + } + common_mixer_set(devc, i + ES18XX_MIXER_RECDIFF, left, right); + } + } + return mask; +} + static int set_recmask(sb_devc * devc, int mask) { int devmask, i; @@ -203,8 +269,12 @@ static int set_recmask(sb_devc * devc, int mask) switch (devc->model) { + case MDL_ESS: /* ES18XX needs a separate approach */ + if (devc->submodel == SUBMDL_ES18XX) { + devmask = es18XX_set_recmask(devc, devmask); + break; + }; case MDL_SBPRO: - case MDL_ESS: case MDL_JAZZ: case MDL_SMW: @@ -423,7 +493,7 @@ static struct mixer_operations als007_mixer_operations = static void sb_mixer_reset(sb_devc * devc) { char name[32]; - int i; + int i, regval; extern int sm_games; sprintf(name, "SB_%d", devc->sbmixnum); @@ -435,6 +505,24 @@ static void sb_mixer_reset(sb_devc * devc) for (i = 0; i < SOUND_MIXER_NRDEVICES; i++) sb_mixer_set(devc, i, devc->levels[i]); + + /* + * Separate actions for ES18XX: + * Change registers 7a and 1c to make the record mixer the input for + * + * Then call set_recmask twice to do extra ES18XX initializations + */ + if (devc->model == MDL_ESS && devc->submodel == SUBMDL_ES18XX) { + regval = sb_getmixer(devc, 0x7a); + regval = (regval & 0xe7) | 0x08; + sb_setmixer(devc, 0x7a, regval); + regval = sb_getmixer(devc, 0x1c); + regval = (regval & 0xf8) | 0x07; + sb_setmixer(devc, 0x1c, regval); + + set_recmask(devc, ES18XX_RECORDING_DEVICES); + set_recmask(devc, 0); + } set_recmask(devc, SOUND_MASK_MIC); } @@ -464,9 +552,26 @@ int sb_mixer_init(sb_devc * devc) case MDL_ESS: devc->mixer_caps = SOUND_CAP_EXCL_INPUT; - devc->supported_devices = ES688_MIXER_DEVICES; - devc->supported_rec_devices = ES688_RECORDING_DEVICES; - devc->iomap = &es688_mix; + + /* + * Take care of ES18XX specifics... + */ + switch (devc->submodel) { + case SUBMDL_ES18XX: + devc->supported_devices + = ES18XX_MIXER_DEVICES; + devc->supported_rec_devices + = ES18XX_RECORDING_DEVICES; + devc->iomap = &es18XX_mix; + break; + default: + devc->supported_devices + = ES688_MIXER_DEVICES; + devc->supported_rec_devices + = ES688_RECORDING_DEVICES; + devc->iomap = &es688_mix; + } + break; case MDL_SMW: diff --git a/drivers/sound/sb_mixer.h b/drivers/sound/sb_mixer.h index 7f61e6e0c7d9..2785567e5beb 100644 --- a/drivers/sound/sb_mixer.h +++ b/drivers/sound/sb_mixer.h @@ -15,7 +15,11 @@ * Modified: * Hunyue Yau Jan 6 1994 * Added defines for the Sound Galaxy NX Pro mixer. - * + * + * Rolf Fokkens Dec 20 1998 + * Added (BETA?) support for ES18XX chips. + * Which means: you can adjust the recording levels. + * */ #include #include "legacy.h" @@ -47,6 +51,10 @@ #define ES688_RECORDING_DEVICES SBPRO_RECORDING_DEVICES #define ES688_MIXER_DEVICES (SBPRO_MIXER_DEVICES|SOUND_MASK_LINE2|SOUND_MASK_SPEAKER) +#define ES18XX_RECORDING_DEVICES (ES688_RECORDING_DEVICES | SOUND_MASK_LINE2 \ + |SOUND_MASK_SYNTH) +#define ES18XX_MIXER_DEVICES (ES688_MIXER_DEVICES) + #define SB16_MIXER_DEVICES (SOUND_MASK_SYNTH | SOUND_MASK_PCM | SOUND_MASK_SPEAKER | SOUND_MASK_LINE | SOUND_MASK_MIC | \ SOUND_MASK_CD | \ SOUND_MASK_IGAIN | SOUND_MASK_OGAIN | \ @@ -109,6 +117,31 @@ #define LEFT_CHN 0 #define RIGHT_CHN 1 +/* + * Mixer registers of ES18XX + * + * These register specifically take care of recording levels. To make the + * mapping from playback devices to recording devices every recording + * devices = playback device + ES18XX_MIXER_RECDIFF + */ +#define ES18XX_MIXER_RECBASE (SOUND_MIXER_LINE3 + 1) +#define ES18XX_MIXER_RECDIFF (ES18XX_MIXER_RECBASE - SOUND_MIXER_SYNTH) + +#define ES18XX_MIXER_RECSYNTH (SOUND_MIXER_SYNTH + ES18XX_MIXER_RECDIFF) +#define ES18XX_MIXER_RECPCM (SOUND_MIXER_PCM + ES18XX_MIXER_RECDIFF) +#define ES18XX_MIXER_RECSPEAKER (SOUND_MIXER_SPEAKER + ES18XX_MIXER_RECDIFF) +#define ES18XX_MIXER_RECLINE (SOUND_MIXER_LINE + ES18XX_MIXER_RECDIFF) +#define ES18XX_MIXER_RECMIC (SOUND_MIXER_MIC + ES18XX_MIXER_RECDIFF) +#define ES18XX_MIXER_RECCD (SOUND_MIXER_CD + ES18XX_MIXER_RECDIFF) +#define ES18XX_MIXER_RECIMIX (SOUND_MIXER_IMIX + ES18XX_MIXER_RECDIFF) +#define ES18XX_MIXER_RECALTPCM (SOUND_MIXER_ALTPCM + ES18XX_MIXER_RECDIFF) +#define ES18XX_MIXER_RECRECLEV (SOUND_MIXER_RECLEV + ES18XX_MIXER_RECDIFF) +#define ES18XX_MIXER_RECIGAIN (SOUND_MIXER_IGAIN + ES18XX_MIXER_RECDIFF) +#define ES18XX_MIXER_RECOGAIN (SOUND_MIXER_OGAIN + ES18XX_MIXER_RECDIFF) +#define ES18XX_MIXER_RECLINE1 (SOUND_MIXER_LINE1 + ES18XX_MIXER_RECDIFF) +#define ES18XX_MIXER_RECLINE2 (SOUND_MIXER_LINE2 + ES18XX_MIXER_RECDIFF) +#define ES18XX_MIXER_RECLINE3 (SOUND_MIXER_LINE3 + ES18XX_MIXER_RECDIFF) + /* * Mixer registers of ALS007 */ @@ -154,6 +187,48 @@ MIX_ENT(SOUND_MIXER_LINE2, 0x3a, 7, 4, 0x3a, 3, 4), MIX_ENT(SOUND_MIXER_LINE3, 0x00, 0, 0, 0x00, 0, 0) }; +/* + * The ES18XX specifics. + * Note that de master volume unlike ES688 is now controlled by two + * 6 bit registers. + * Also Note that the recording levels (ES18XX_MIXER_REC...) have own + * entries as if they were playback devices. They are used internally only! + */ +static mixer_tab es18XX_mix = { +MIX_ENT(SOUND_MIXER_VOLUME, 0x60, 5, 6, 0x62, 5, 6), +MIX_ENT(SOUND_MIXER_BASS, 0x00, 0, 0, 0x00, 0, 0), +MIX_ENT(SOUND_MIXER_TREBLE, 0x00, 0, 0, 0x00, 0, 0), +MIX_ENT(SOUND_MIXER_SYNTH, 0x36, 7, 4, 0x36, 3, 4), +MIX_ENT(SOUND_MIXER_PCM, 0x14, 7, 4, 0x14, 3, 4), +MIX_ENT(SOUND_MIXER_SPEAKER, 0x3c, 2, 3, 0x00, 0, 0), +MIX_ENT(SOUND_MIXER_LINE, 0x3e, 7, 4, 0x3e, 3, 4), +MIX_ENT(SOUND_MIXER_MIC, 0x1a, 7, 4, 0x1a, 3, 4), +MIX_ENT(SOUND_MIXER_CD, 0x38, 7, 4, 0x38, 3, 4), +MIX_ENT(SOUND_MIXER_IMIX, 0x00, 0, 0, 0x00, 0, 0), +MIX_ENT(SOUND_MIXER_ALTPCM, 0x00, 0, 0, 0x00, 0, 0), +MIX_ENT(SOUND_MIXER_RECLEV, 0x00, 0, 0, 0x00, 0, 0), +MIX_ENT(SOUND_MIXER_IGAIN, 0x00, 0, 0, 0x00, 0, 0), +MIX_ENT(SOUND_MIXER_OGAIN, 0x00, 0, 0, 0x00, 0, 0), +MIX_ENT(SOUND_MIXER_LINE1, 0x00, 0, 0, 0x00, 0, 0), +MIX_ENT(SOUND_MIXER_LINE2, 0x3a, 7, 4, 0x3a, 3, 4), +MIX_ENT(SOUND_MIXER_LINE3, 0x00, 0, 0, 0x00, 0, 0), +MIX_ENT(ES18XX_MIXER_RECSYNTH, 0x6b, 7, 4, 0x6b, 3, 4), +MIX_ENT(ES18XX_MIXER_RECPCM, 0x00, 0, 0, 0x00, 0, 0), +MIX_ENT(ES18XX_MIXER_RECSPEAKER,0x00, 0, 0, 0x00, 0, 0), +MIX_ENT(ES18XX_MIXER_RECLINE, 0x6e, 7, 4, 0x6e, 3, 4), +MIX_ENT(ES18XX_MIXER_RECMIC, 0x68, 7, 4, 0x68, 3, 4), +MIX_ENT(ES18XX_MIXER_RECCD, 0x6a, 7, 4, 0x6a, 3, 4), + +MIX_ENT(ES18XX_MIXER_RECIMIX, 0x00, 0, 0, 0x00, 0, 0), +MIX_ENT(ES18XX_MIXER_RECALTPCM, 0x00, 0, 0, 0x00, 0, 0), +MIX_ENT(ES18XX_MIXER_RECRECLEV, 0x00, 0, 0, 0x00, 0, 0), +MIX_ENT(ES18XX_MIXER_RECIGAIN, 0x00, 0, 0, 0x00, 0, 0), +MIX_ENT(ES18XX_MIXER_RECOGAIN, 0x00, 0, 0, 0x00, 0, 0), +MIX_ENT(ES18XX_MIXER_RECLINE1, 0x00, 0, 0, 0x00, 0, 0), +MIX_ENT(ES18XX_MIXER_RECLINE2, 0x6c, 7, 4, 0x6c, 3, 4), +MIX_ENT(ES18XX_MIXER_RECLINE3, 0x00, 0, 0, 0x00, 0, 0) +}; + #ifdef __SGNXPRO__ #if 0 static mixer_tab sgnxpro_mix = { /* not used anywhere */ diff --git a/drivers/sound/softoss_rs.c b/drivers/sound/softoss_rs.c index ac9714ff5617..2fa95f748b35 100644 --- a/drivers/sound/softoss_rs.c +++ b/drivers/sound/softoss_rs.c @@ -49,7 +49,7 @@ void softsynth_resample_loop(short *buf, int loops) #endif /* Interpolation (resolution of 512 steps) */ { - int fract = v->ptr & 0x1f; /* 9 bits */ + int fract = v->ptr & 0x1ff; /* 9 bits */ /* This method works with less arithmetic operations */ register int v1 = v->wave[ix]; diff --git a/drivers/sound/sonicvibes.c b/drivers/sound/sonicvibes.c index 20d273eeaa50..84b0bf978a67 100644 --- a/drivers/sound/sonicvibes.c +++ b/drivers/sound/sonicvibes.c @@ -48,6 +48,7 @@ * "OSS documented" and "OSS actual" behaviour * 31.08.98 0.7 Fix realplayer problems - dac.count issues * 10.12.98 0.8 Fix drain_dac trying to wait on not yet initialized DMA + * 16.12.98 0.9 Fix a few f_file & FMODE_ bugs * */ @@ -764,17 +765,14 @@ static void sv_update_ptr(struct sv_state *s) s->dma_adc.hwptr = hwptr; s->dma_adc.total_bytes += diff; s->dma_adc.count += diff; - if (s->dma_adc.mapped) { - if (s->dma_adc.count >= (signed)s->dma_adc.fragsize) - wake_up(&s->dma_adc.wait); - } else { + if (s->dma_adc.count >= (signed)s->dma_adc.fragsize) + wake_up(&s->dma_adc.wait); + if (!s->dma_adc.mapped) { if (s->dma_adc.count > (signed)(s->dma_adc.dmasize - ((3 * s->dma_adc.fragsize) >> 1))) { s->enable &= ~SV_CENABLE_RE; wrindir(s, SV_CIENABLE, s->enable); s->dma_adc.error++; } - if (s->dma_adc.count > 0) - wake_up(&s->dma_adc.wait); } } /* update DAC pointer */ @@ -797,7 +795,7 @@ static void sv_update_ptr(struct sv_state *s) clear_advance(s); s->dma_dac.endcleared = 1; } - if (s->dma_dac.count < (signed)s->dma_dac.dmasize) + if (s->dma_dac.count + (signed)s->dma_dac.fragsize <= (signed)s->dma_dac.dmasize) wake_up(&s->dma_dac.wait); } } @@ -1382,27 +1380,22 @@ static unsigned int sv_poll(struct file *file, struct poll_table_struct *wait) unsigned int mask = 0; VALIDATE_STATE(s); - if (file->f_flags & FMODE_WRITE) + if (file->f_mode & FMODE_WRITE) poll_wait(file, &s->dma_dac.wait, wait); - if (file->f_flags & FMODE_READ) + if (file->f_mode & FMODE_READ) poll_wait(file, &s->dma_adc.wait, wait); spin_lock_irqsave(&s->lock, flags); sv_update_ptr(s); - if (file->f_flags & FMODE_READ) { - if (s->dma_adc.mapped) { - if (s->dma_adc.count >= (signed)s->dma_adc.fragsize) - mask |= POLLIN | POLLRDNORM; - } else { - if (s->dma_adc.count > 0) - mask |= POLLIN | POLLRDNORM; - } + if (file->f_mode & FMODE_READ) { + if (s->dma_adc.count >= (signed)s->dma_adc.fragsize) + mask |= POLLIN | POLLRDNORM; } - if (file->f_flags & FMODE_WRITE) { + if (file->f_mode & FMODE_WRITE) { if (s->dma_dac.mapped) { if (s->dma_dac.count >= (signed)s->dma_dac.fragsize) mask |= POLLOUT | POLLWRNORM; } else { - if ((signed)s->dma_dac.dmasize > s->dma_dac.count) + if ((signed)s->dma_dac.dmasize >= s->dma_dac.count + (signed)s->dma_dac.fragsize) mask |= POLLOUT | POLLWRNORM; } } @@ -1786,11 +1779,11 @@ static int sv_release(struct inode *inode, struct file *file) if (file->f_mode & FMODE_WRITE) drain_dac(s, file->f_flags & O_NONBLOCK); down(&s->open_sem); - if (file->f_flags & FMODE_WRITE) { + if (file->f_mode & FMODE_WRITE) { stop_dac(s); dealloc_dmabuf(&s->dma_dac); } - if (file->f_flags & FMODE_READ) { + if (file->f_mode & FMODE_READ) { stop_adc(s); dealloc_dmabuf(&s->dma_adc); } @@ -1923,16 +1916,16 @@ static unsigned int sv_midi_poll(struct file *file, struct poll_table_struct *wa unsigned int mask = 0; VALIDATE_STATE(s); - if (file->f_flags & FMODE_WRITE) + if (file->f_mode & FMODE_WRITE) poll_wait(file, &s->midi.owait, wait); - if (file->f_flags & FMODE_READ) + if (file->f_mode & FMODE_READ) poll_wait(file, &s->midi.iwait, wait); spin_lock_irqsave(&s->lock, flags); - if (file->f_flags & FMODE_READ) { + if (file->f_mode & FMODE_READ) { if (s->midi.icnt > 0) mask |= POLLIN | POLLRDNORM; } - if (file->f_flags & FMODE_WRITE) { + if (file->f_mode & FMODE_WRITE) { if (s->midi.ocnt < MIDIOUTBUF) mask |= POLLOUT | POLLWRNORM; } @@ -2278,7 +2271,7 @@ __initfunc(int init_sonicvibes(void)) if (!pci_present()) /* No PCI bus in this machine! */ return -ENODEV; - printk(KERN_INFO "sv: version v0.8 time " __TIME__ " " __DATE__ "\n"); + printk(KERN_INFO "sv: version v0.9 time " __TIME__ " " __DATE__ "\n"); #if 0 if (!(wavetable_mem = __get_free_pages(GFP_KERNEL, 20-PAGE_SHIFT))) printk(KERN_INFO "sv: cannot allocate 1MB of contiguous nonpageable memory for wavetable data\n"); diff --git a/drivers/sound/trix.c b/drivers/sound/trix.c index 97113a838b71..1a6b79c769d4 100644 --- a/drivers/sound/trix.c +++ b/drivers/sound/trix.c @@ -26,6 +26,7 @@ #ifdef CONFIG_TRIX #ifdef INCLUDE_TRIX_BOOT +#include #include "trix_boot.h" #else static unsigned char *trix_boot = NULL; diff --git a/fs/Config.in b/fs/Config.in index a88af3709716..4b29613e58c6 100644 --- a/fs/Config.in +++ b/fs/Config.in @@ -5,23 +5,53 @@ mainmenu_option next_comment comment 'Filesystems' bool 'Quota support' CONFIG_QUOTA +tristate 'Kernel automounter support' CONFIG_AUTOFS_FS -tristate 'Minix fs support' CONFIG_MINIX_FS -tristate 'Second extended fs support' CONFIG_EXT2_FS + +if [ "$CONFIG_EXPERIMENTAL" = "y" ]; then + tristate 'ADFS filesystem support (read only) (EXPERIMENTAL)' CONFIG_ADFS_FS +fi +tristate 'Amiga FFS filesystem support' CONFIG_AFFS_FS +tristate 'Apple Macintosh filesystem support (experimental)' CONFIG_HFS_FS +# msdos filesystems +tristate 'DOS FAT fs support' CONFIG_FAT_FS +dep_tristate ' MSDOS fs support' CONFIG_MSDOS_FS $CONFIG_FAT_FS +dep_tristate ' UMSDOS: Unix-like filesystem on top of standard MSDOS filesystem' CONFIG_UMSDOS_FS $CONFIG_MSDOS_FS +dep_tristate ' VFAT (Windows-95) fs support' CONFIG_VFAT_FS $CONFIG_FAT_FS tristate 'ISO 9660 CDROM filesystem support' CONFIG_ISO9660_FS if [ "$CONFIG_ISO9660_FS" != "n" ]; then bool 'Microsoft Joliet CDROM extensions' CONFIG_JOLIET fi -# msdos filesystems -tristate 'DOS FAT fs support' CONFIG_FAT_FS -dep_tristate 'MSDOS fs support' CONFIG_MSDOS_FS $CONFIG_FAT_FS -dep_tristate 'UMSDOS: Unix-like filesystem on top of standard MSDOS filesystem' CONFIG_UMSDOS_FS $CONFIG_MSDOS_FS -dep_tristate 'VFAT (Windows-95) fs support' CONFIG_VFAT_FS $CONFIG_FAT_FS - +tristate 'Minix fs support' CONFIG_MINIX_FS +tristate 'NTFS filesystem support (read only)' CONFIG_NTFS_FS +if [ "$CONFIG_NTFS_FS" != "n" -a "$CONFIG_EXPERIMENTAL" = "y" ]; then + bool ' NTFS read-write support (experimental)' CONFIG_NTFS_RW +fi +tristate 'OS/2 HPFS filesystem support (read only)' CONFIG_HPFS_FS bool '/proc filesystem support' CONFIG_PROC_FS +if [ "$CONFIG_UNIX98_PTYS" = "y" ]; then + tristate '/dev/pts filesystem for Unix98 PTYs' CONFIG_DEVPTS_FS +fi +if [ "$CONFIG_EXPERIMENTAL" = "y" ]; then + tristate 'QNX filesystem support (EXPERIMENTAL)' CONFIG_QNX4FS_FS + if [ "$CONFIG_QNX4FS_FS" != "n" ]; then + bool ' QNXFS read-write support (FOR TESTING ONLY)' CONFIG_QNX4FS_RW + fi +fi +tristate 'ROM filesystem support' CONFIG_ROMFS_FS +tristate 'Second extended fs support' CONFIG_EXT2_FS +tristate 'System V and Coherent filesystem support' CONFIG_SYSV_FS +tristate 'UFS filesystem support' CONFIG_UFS_FS + + + +mainmenu_option next_comment +comment 'Network File Systems' + if [ "$CONFIG_INET" = "y" ]; then + tristate 'Coda filesystem support (advanced network fs)' CONFIG_CODA_FS tristate 'NFS filesystem support' CONFIG_NFS_FS if [ "$CONFIG_NFS_FS" = "y" -a "$CONFIG_IP_PNP" = "y" ]; then bool ' Root file system on NFS' CONFIG_ROOT_NFS @@ -42,7 +72,6 @@ if [ "$CONFIG_INET" = "y" ]; then define_bool CONFIG_LOCKD n fi fi - tristate 'Coda filesystem support (advanced network fs)' CONFIG_CODA_FS tristate 'SMB filesystem support (to mount WfW shares etc.)' CONFIG_SMB_FS if [ "$CONFIG_SMB_FS" != "n" ]; then bool 'SMB Win95 bug work-around' CONFIG_SMB_WIN95 @@ -54,34 +83,23 @@ if [ "$CONFIG_IPX" != "n" -o "$CONFIG_INET" != "n" ]; then source fs/ncpfs/Config.in fi fi -tristate 'OS/2 HPFS filesystem support (read only)' CONFIG_HPFS_FS -tristate 'NTFS filesystem support (read only)' CONFIG_NTFS_FS -if [ "$CONFIG_NTFS_FS" != "n" -a "$CONFIG_EXPERIMENTAL" = "y" ]; then - bool ' NTFS read-write support (experimental)' CONFIG_NTFS_RW -fi +endmenu -tristate 'System V and Coherent filesystem support' CONFIG_SYSV_FS -tristate 'Amiga FFS filesystem support' CONFIG_AFFS_FS -tristate 'Apple Macintosh filesystem support (experimental)' CONFIG_HFS_FS -tristate 'ROM filesystem support' CONFIG_ROMFS_FS -tristate 'Kernel automounter support' CONFIG_AUTOFS_FS if [ "$CONFIG_AFFS_FS" != "n" ]; then define_bool CONFIG_AMIGA_PARTITION y fi -tristate 'UFS filesystem support' CONFIG_UFS_FS + +mainmenu_option next_comment +comment 'Partition Types' + bool 'BSD disklabel (BSD partition tables) support' CONFIG_BSD_DISKLABEL +bool 'Macintosh partition map support' CONFIG_MAC_PARTITION bool 'SMD disklabel (Sun partition tables) support' CONFIG_SMD_DISKLABEL bool 'Solaris (x86) partition table support' CONFIG_SOLARIS_X86_PARTITION -if [ "$CONFIG_UNIX98_PTYS" = "y" ]; then - tristate '/dev/pts filesystem for Unix98 PTYs' CONFIG_DEVPTS_FS -fi if [ "$CONFIG_EXPERIMENTAL" = "y" ]; then - tristate 'ADFS filesystem support (read only) (EXPERIMENTAL)' CONFIG_ADFS_FS - tristate 'QNX filesystem support (EXPERIMENTAL)' CONFIG_QNX4FS_FS - if [ "$CONFIG_QNX4FS_FS" != "n" ]; then - bool ' QNXFS read-write support (FOR TESTING ONLY)' CONFIG_QNX4FS_RW - fi + bool 'Unixware slices support (EXPERIMENTAL)' CONFIG_UNIXWARE_DISKLABEL fi -bool 'Macintosh partition map support' CONFIG_MAC_PARTITION +endmenu + endmenu diff --git a/fs/binfmt_misc.c b/fs/binfmt_misc.c index 8acea3b64ab4..f1b44f1020f9 100644 --- a/fs/binfmt_misc.c +++ b/fs/binfmt_misc.c @@ -15,6 +15,7 @@ * 1997-08-09 removed extension stripping, locking cleanup */ +#include #include #include @@ -451,7 +452,9 @@ static int proc_write_status(struct file *file, const char *buffer, */ static void entry_proc_cleanup(struct binfmt_entry *e) { +#ifdef CONFIG_PROC_FS remove_proc_entry(e->proc_name, bm_dir); +#endif } /* @@ -459,6 +462,7 @@ static void entry_proc_cleanup(struct binfmt_entry *e) */ static int entry_proc_setup(struct binfmt_entry *e) { +#ifdef CONFIG_PROC_FS if (!(e->proc_dir = create_proc_entry(e->proc_name, S_IFREG | S_IRUGO | S_IWUSR, bm_dir))) return -ENOMEM; @@ -466,7 +470,7 @@ static int entry_proc_setup(struct binfmt_entry *e) e->proc_dir->data = (void *) (e->id); e->proc_dir->read_proc = proc_read_status; e->proc_dir->write_proc = proc_write_status; - +#endif return 0; } @@ -490,8 +494,9 @@ static void bm_modcount(struct inode *inode, int fill) int __init init_misc_binfmt(void) { - struct proc_dir_entry *status = NULL, *reg; int error = -ENOMEM; +#ifdef CONFIG_PROC_FS + struct proc_dir_entry *status = NULL, *reg; bm_dir = create_proc_entry("sys/fs/binfmt_misc", S_IFDIR, NULL); if (!bm_dir) @@ -511,6 +516,7 @@ int __init init_misc_binfmt(void) if (!reg) goto cleanup_status; reg->write_proc = proc_write_register; +#endif /* CONFIG_PROC_FS */ error = register_binfmt(&misc_format); out: diff --git a/fs/buffer.c b/fs/buffer.c index a013b3542094..db2ecc42d767 100644 --- a/fs/buffer.c +++ b/fs/buffer.c @@ -1836,7 +1836,8 @@ asmlinkage int sync_old_buffers(void) if (buffer_locked(bh) || !buffer_dirty(bh)) continue; ndirty++; - if(bh->b_flushtime > jiffies) continue; + if(time_before(jiffies, bh->b_flushtime)) + continue; nwritten++; next->b_count++; bh->b_count++; diff --git a/fs/devices.c b/fs/devices.c index db5cca48be76..2ff69850a1b5 100644 --- a/fs/devices.c +++ b/fs/devices.c @@ -210,11 +210,11 @@ int check_disk_change(kdev_t dev) return 0; printk(KERN_DEBUG "VFS: Disk change detected on device %s\n", - kdevname(dev)); + bdevname(dev)); sb = get_super(dev); if (sb && invalidate_inodes(sb)) - printk("VFS: busy inodes on changed media..\n"); + printk("VFS: busy inodes on changed media.\n"); invalidate_buffers(dev); @@ -338,8 +338,7 @@ struct inode_operations chrdev_inode_operations = { }; /* - * Print device name (in decimal, hexadecimal or symbolic) - - * at present hexadecimal only. + * Print device name (in decimal, hexadecimal or symbolic) * Note: returns pointer to static data! */ char * kdevname(kdev_t dev) @@ -348,3 +347,26 @@ char * kdevname(kdev_t dev) sprintf(buffer, "%02x:%02x", MAJOR(dev), MINOR(dev)); return buffer; } + +char * bdevname(kdev_t dev) +{ + static char buffer[32]; + const char * name = blkdevs[MAJOR(dev)].name; + + if (!name) + name = "unknown-block"; + + sprintf(buffer, "%s(%d,%d)", name, MAJOR(dev), MINOR(dev)); + return buffer; +} + +char * cdevname(kdev_t dev) +{ + static char buffer[32]; + const char * name = chrdevs[MAJOR(dev)].name; + + if (!name) + name = "unknown-char"; + sprintf(buffer, "%s(%d,%d)", name, MAJOR(dev), MINOR(dev)); + return buffer; +} diff --git a/fs/fat/file.c b/fs/fat/file.c index 52e36caea576..0ff5f187f76b 100644 --- a/fs/fat/file.c +++ b/fs/fat/file.c @@ -375,6 +375,12 @@ ssize_t fat_file_write( *ppos = inode->i_size; if (count == 0) return 0; + if (*ppos + count > 0x7FFFFFFFLL) { + count = 0x7FFFFFFFLL-*ppos; + if (!count) + return -EFBIG; + } + error = carry = 0; for (start = buf; count || carry; count -= size) { while (!(sector = fat_smap(inode,*ppos >> SECTOR_BITS))) diff --git a/fs/file_table.c b/fs/file_table.c index 200b6049bc30..cbc33634aa4e 100644 --- a/fs/file_table.c +++ b/fs/file_table.c @@ -20,7 +20,7 @@ int max_files = NR_FILE;/* tunable */ /* Free list management, if you are here you must have f_count == 0 */ static struct file * free_filps = NULL; -void insert_file_free(struct file *file) +static void insert_file_free(struct file *file) { if((file->f_next = free_filps) != NULL) free_filps->f_pprev = &file->f_next; @@ -40,6 +40,15 @@ static inline void put_inuse(struct file *file) file->f_pprev = &inuse_filps; } +/* It does not matter which list it is on. */ +static inline void remove_filp(struct file *file) +{ + if(file->f_next) + file->f_next->f_pprev = file->f_pprev; + *file->f_pprev = file->f_next; +} + + void __init file_table_init(void) { filp_cache = kmem_cache_create("filp", sizeof(struct file), @@ -116,3 +125,25 @@ int init_private_file(struct file *filp, struct dentry *dentry, int mode) else return 0; } + +void fput(struct file *file) +{ + int count = file->f_count-1; + + if (!count) { + locks_remove_flock(file); + __fput(file); + file->f_count = 0; + remove_filp(file); + insert_file_free(file); + } else + file->f_count = count; +} + +void put_filp(struct file *file) +{ + if(--file->f_count == 0) { + remove_filp(file); + insert_file_free(file); + } +} diff --git a/fs/hfs/ChangeLog b/fs/hfs/ChangeLog index 0bd14f24cc08..c0b077f474cd 100644 --- a/fs/hfs/ChangeLog +++ b/fs/hfs/ChangeLog @@ -1,3 +1,24 @@ +1998-12-20 a sun + + * bdelete.c (del_root): assign bthLNode and bthFNode only if the + root node becomes a leaf node. Disk First Aid no longer + complains. Norton Utilities, of course, has decided that it + doesn't like the root node number. bleah. i think that it might be + due to Norton Utilities not expecting the root node to have moved. + +1998-12-16 a sun + + * sysdep.c (hfs_revalidate_dentry): fix inode dates when there's a + timezone change. + +1998-12-15 root + + * extent.c (new_extent): expand block size variables to handle + u32. + + * mdb.c (hfs_mdb_get): AlBlkSiz shouldn't be capped at 65535. we + should be able to handle much larger volumes now. + 1998-11-21 a sun * hfs_sysdep.h, hfs_fs.h: added hfs_from_utc/to_utc to deal with diff --git a/fs/hfs/bdelete.c b/fs/hfs/bdelete.c index 0e47c273791f..c968c74b7050 100644 --- a/fs/hfs/bdelete.c +++ b/fs/hfs/bdelete.c @@ -135,11 +135,16 @@ static int del_root(struct hfs_bnode_ref *root) tree->bthRoot = child.bn->node; tree->root = child.bn; + + /* re-assign bthFNode and bthLNode if the new root is + a leaf node. */ + if (child.bn->ndType == ndLeafNode) { + tree->bthFNode = node; + tree->bthLNode = node; + } hfs_bnode_relse(&child); tree->bthRoot = node; - tree->bthFNode = node; - tree->bthLNode = node; --tree->bthDepth; tree->dirt = 1; if (!tree->bthDepth) { diff --git a/fs/hfs/extent.c b/fs/hfs/extent.c index 1fc749f344eb..3c92e7defa54 100644 --- a/fs/hfs/extent.c +++ b/fs/hfs/extent.c @@ -354,7 +354,7 @@ static void delete_extent(struct hfs_fork *fork, struct hfs_extent *ext) * hfs_u16 ablock: the number of allocation blocks in 'fork'. * hfs_u16 start: first allocation block to add to 'fork'. * hfs_u16 len: the number of allocation blocks to add to 'fork'. - * hfs_u16 ablksz: number of sectors in an allocation block. + * hfs_u32 ablksz: number of sectors in an allocation block. * Output Variable(s): * NONE * Returns: @@ -471,7 +471,7 @@ static void shrink_fork(struct hfs_fork *fork, int ablocks) struct hfs_mdb *mdb = fork->entry->mdb; struct hfs_extent *ext; int i, error, next, count; - hfs_u16 ablksz = mdb->alloc_blksz; + hfs_u32 ablksz = mdb->alloc_blksz; next = (fork->psize / ablksz) - 1; ext = find_ext(fork, next); @@ -530,7 +530,7 @@ static void grow_fork(struct hfs_fork *fork, int ablocks) struct hfs_extent *ext; int i, start, err; hfs_u16 need, len=0; - hfs_u16 ablksz = mdb->alloc_blksz; + hfs_u32 ablksz = mdb->alloc_blksz; hfs_u32 blocks, clumpablks; blocks = fork->psize; @@ -681,8 +681,7 @@ int hfs_ext_compare(const struct hfs_ext_key *key1, void hfs_extent_adj(struct hfs_fork *fork) { if (fork) { - hfs_u32 blks, ablocks; - hfs_u16 ablksz; + hfs_u32 blks, ablocks, ablksz; if (fork->lsize > HFS_FORK_MAX) { fork->lsize = HFS_FORK_MAX; diff --git a/fs/hfs/hfs.h b/fs/hfs/hfs.h index 06138ab2de58..824e02be5e63 100644 --- a/fs/hfs/hfs.h +++ b/fs/hfs/hfs.h @@ -252,7 +252,7 @@ struct hfs_mdb { hfs_u16 free_ablocks; /* The number of unused allocation blocks in the filesystem */ - hfs_u16 alloc_blksz; /* The number of + hfs_u32 alloc_blksz; /* The number of 512-byte blocks per "allocation block" */ hfs_u16 attrib; /* Attribute word */ diff --git a/fs/hfs/inode.c b/fs/hfs/inode.c index 4d997baa87f0..d960b3da017a 100644 --- a/fs/hfs/inode.c +++ b/fs/hfs/inode.c @@ -260,6 +260,7 @@ struct inode *hfs_iget(struct hfs_cat_entry *entry, ino_t type, memset(HFS_I(inode), 0, sizeof(struct hfs_inode_info)); HFS_I(inode)->magic = HFS_INO_MAGIC; HFS_I(inode)->entry = entry; + HFS_I(inode)->tz_secondswest = hfs_to_utc(0); hsb->s_ifill(inode, type); if (!hsb->s_afpd && (entry->type == HFS_CDR_FIL) && diff --git a/fs/hfs/mdb.c b/fs/hfs/mdb.c index c7267373199b..61070b1d7504 100644 --- a/fs/hfs/mdb.c +++ b/fs/hfs/mdb.c @@ -118,7 +118,7 @@ struct hfs_mdb *hfs_mdb_get(hfs_sysmdb sys_mdb, int readonly, mdb->buf = buf; bs = hfs_get_hl(raw->drAlBlkSiz); - if (!bs || bs > HFS_USHRT_MAX || (bs & (HFS_SECTOR_SIZE-1))) { + if (!bs || (bs & (HFS_SECTOR_SIZE-1))) { hfs_warn("hfs_fs: bad allocation block size %d != 512\n", bs); hfs_buffer_put(buf); HFS_DELETE(mdb); diff --git a/fs/hfs/sysdep.c b/fs/hfs/sysdep.c index c1fb812de069..0524808f7af8 100644 --- a/fs/hfs/sysdep.c +++ b/fs/hfs/sysdep.c @@ -18,12 +18,13 @@ #include #include +static int hfs_revalidate_dentry(struct dentry *); static int hfs_hash_dentry(struct dentry *, struct qstr *); static int hfs_compare_dentry(struct dentry *, struct qstr *, struct qstr *); static void hfs_dentry_iput(struct dentry *, struct inode *); struct dentry_operations hfs_dentry_operations = { - NULL, /* d_validate(struct dentry *) */ + hfs_revalidate_dentry, /* d_revalidate(struct dentry *) */ hfs_hash_dentry, /* d_hash */ hfs_compare_dentry, /* d_compare */ NULL, /* d_delete(struct dentry *) */ @@ -87,3 +88,19 @@ static void hfs_dentry_iput(struct dentry *dentry, struct inode *inode) entry->sys_entry[HFS_ITYPE_TO_INT(HFS_ITYPE(inode->i_ino))] = NULL; iput(inode); } + +static int hfs_revalidate_dentry(struct dentry *dentry) +{ + struct inode *inode = dentry->d_inode; + int diff; + + /* fix up inode on a timezone change */ + if (inode && + (diff = (hfs_to_utc(0) - HFS_I(inode)->tz_secondswest))) { + inode->i_ctime += diff; + inode->i_atime += diff; + inode->i_mtime += diff; + HFS_I(inode)->tz_secondswest += diff; + } + return 1; +} diff --git a/fs/lockd/host.c b/fs/lockd/host.c index 027c230a8423..d4ab7fcc1b2c 100644 --- a/fs/lockd/host.c +++ b/fs/lockd/host.c @@ -92,7 +92,7 @@ nlm_lookup_host(struct svc_client *clnt, struct sockaddr_in *sin, /* Lock hash table */ down(&nlm_host_sema); - if (next_gc < jiffies) + if (time_after(jiffies, next_gc)) nlm_gc_hosts(); for (hp = &nlm_hosts[hash]; (host = *hp); hp = &host->h_next) { @@ -173,7 +173,7 @@ nlm_bind_host(struct nlm_host *host) /* If we've already created an RPC client, check whether * RPC rebind is required */ if ((clnt = host->h_rpcclnt) != NULL) { - if (host->h_nextrebind < jiffies) { + if (time_after(jiffies, host->h_nextrebind)) { clnt->cl_port = 0; host->h_nextrebind = jiffies + NLM_HOST_REBIND; dprintk("lockd: next rebind in %ld jiffies\n", @@ -219,7 +219,7 @@ void nlm_rebind_host(struct nlm_host *host) { dprintk("lockd: rebind host %s\n", host->h_name); - if (host->h_rpcclnt && host->h_nextrebind < jiffies) { + if (host->h_rpcclnt && time_after(jiffies, host->h_nextrebind)) { host->h_rpcclnt->cl_port = 0; host->h_nextrebind = jiffies + NLM_HOST_REBIND; } @@ -298,7 +298,7 @@ nlm_gc_hosts(void) q = &nlm_hosts[i]; while ((host = *q) != NULL) { if (host->h_count || host->h_inuse - || host->h_expires >= jiffies) { + || time_before_eq(jiffies, host->h_expires)) { q = &host->h_next; continue; } diff --git a/fs/lockd/svc.c b/fs/lockd/svc.c index 49cb39c4d46c..2eac8d025317 100644 --- a/fs/lockd/svc.c +++ b/fs/lockd/svc.c @@ -136,7 +136,7 @@ lockd(struct svc_rqst *rqstp) */ if (!nlmsvc_grace_period) { timeout = nlmsvc_retry_blocked(); - } else if (nlmsvc_grace_period < jiffies) + } else if (time_after(jiffies, nlmsvc_grace_period)) nlmsvc_grace_period = 0; /* diff --git a/fs/locks.c b/fs/locks.c index 022206bbb1b0..38982227dc87 100644 --- a/fs/locks.c +++ b/fs/locks.c @@ -154,10 +154,10 @@ static inline struct file_lock *locks_alloc_lock(struct file_lock *fl) static inline void locks_free_lock(struct file_lock *fl) { if (waitqueue_active(&fl->fl_wait)) - panic("Aarggh: attempting to free lock with active wait queue - shoot Andy"); + panic("Attempting to free lock with active wait queue"); if (fl->fl_nextblock != NULL || fl->fl_prevblock != NULL) - panic("Aarggh: attempting to free lock with active block list - shoot Andy"); + panic("Attempting to free lock with active block list"); kfree(fl); return; diff --git a/fs/namei.c b/fs/namei.c index 7f0908387100..2063c54c044f 100644 --- a/fs/namei.c +++ b/fs/namei.c @@ -95,18 +95,6 @@ * [10-Sep-98 Alan Modra] Another symlink change. */ -static inline char * get_page(void) -{ - char * res; - res = (char*)__get_free_page(GFP_KERNEL); - return res; -} - -inline void putname(char * name) -{ - free_page((unsigned long) name); -} - /* In order to reduce some races, while at the same time doing additional * checking and hopefully speeding things up, we copy filenames to the * kernel data space before using them.. @@ -139,7 +127,7 @@ char * getname(const char * filename) char *tmp, *result; result = ERR_PTR(-ENOMEM); - tmp = get_page(); + tmp = __getname(); if (tmp) { int retval = do_getname(filename, tmp); diff --git a/fs/ncpfs/inode.c b/fs/ncpfs/inode.c index 99488fca1450..4a0459cdf19e 100644 --- a/fs/ncpfs/inode.c +++ b/fs/ncpfs/inode.c @@ -382,7 +382,12 @@ out_free_server: out_no_server: printk(KERN_ERR "ncp_read_super: could not alloc ncp_server\n"); out_unlock: - put_filp(ncp_filp); + /* 23/12/1998 Marcin Dalecki : + * + * The previously used put_filp(ncp_filp); was bogous, since + * it doesn't proper unlocking. + */ + fput(ncp_filp); unlock_super(sb); goto out; diff --git a/fs/nfs/dir.c b/fs/nfs/dir.c index fd3a72e2c6f3..329605a12057 100644 --- a/fs/nfs/dir.c +++ b/fs/nfs/dir.c @@ -571,11 +571,6 @@ show_dentry(&inode->i_dentry); error = 0; } } -#ifdef NFS_PARANOIA -if (error) -printk("nfs_lookup: %s/%s failed, error=%d\n", -dentry->d_parent->d_name.name, dentry->d_name.name, error); -#endif out: return error; } diff --git a/fs/nfsd/nfsfh.c b/fs/nfsd/nfsfh.c index 8c3d91f64e8c..a8bf3a3a59c1 100644 --- a/fs/nfsd/nfsfh.c +++ b/fs/nfsd/nfsfh.c @@ -1001,7 +1001,7 @@ out: * Perform any needed housekeeping ... * N.B. move this into one of the daemons ... */ - if (jiffies >= nfsd_next_expire) { + if (time_after_eq(jiffies, nfsd_next_expire)) { expire_old(NFSD_FILE_CACHE, 5*HZ); expire_old(NFSD_DIR_CACHE , 60*HZ); nfsd_next_expire = jiffies + 5*HZ; diff --git a/fs/open.c b/fs/open.c index 05d8f9ea4350..e6564f15e6fd 100644 --- a/fs/open.c +++ b/fs/open.c @@ -6,14 +6,11 @@ #include #include -#include -#include #include #include #include #include -#include asmlinkage int sys_statfs(const char * path, struct statfs * buf) { @@ -671,18 +668,6 @@ out: return ERR_PTR(error); } -/* should probably go into sys_open() */ -static int do_open(const char * filename, int flags, int mode, int fd) -{ - struct file * f; - - f = filp_open(filename, flags, mode); - if (IS_ERR(f)) - return PTR_ERR(f); - fd_install(fd, f); - return 0; -} - /* * Find an empty file descriptor entry, and mark it busy. */ @@ -727,24 +712,25 @@ asmlinkage int sys_open(const char * filename, int flags, int mode) char * tmp; int fd, error; - lock_kernel(); - fd = get_unused_fd(); - if (fd < 0) - goto out; - tmp = getname(filename); - error = PTR_ERR(tmp); - if (IS_ERR(tmp)) - goto out_fail; - error = do_open(tmp, flags, mode, fd); - putname(tmp); - if (error) - goto out_fail; + fd = PTR_ERR(tmp); + if (!IS_ERR(tmp)) { + lock_kernel(); + fd = get_unused_fd(); + if (fd >= 0) { + struct file * f = filp_open(tmp, flags, mode); + error = PTR_ERR(f); + if (IS_ERR(f)) + goto out_error; + fd_install(fd, f); + } out: - unlock_kernel(); + unlock_kernel(); + putname(tmp); + } return fd; -out_fail: +out_error: put_unused_fd(fd); fd = error; goto out; diff --git a/fs/read_write.c b/fs/read_write.c index 00fa17ed6514..7b9bf0bf7593 100644 --- a/fs/read_write.c +++ b/fs/read_write.c @@ -215,7 +215,8 @@ static ssize_t do_readv_writev(int type, struct file *file, tot_len += iov[i].iov_len; inode = file->f_dentry->d_inode; - ret = locks_verify_area((type == VERIFY_READ + /* VERIFY_WRITE actually means a read, as we write to user space */ + ret = locks_verify_area((type == VERIFY_WRITE ? FLOCK_VERIFY_READ : FLOCK_VERIFY_WRITE), inode, file, file->f_pos, tot_len); if (ret) goto out; diff --git a/fs/smbfs/inode.c b/fs/smbfs/inode.c index e850b7f82b4f..1a278911ab55 100644 --- a/fs/smbfs/inode.c +++ b/fs/smbfs/inode.c @@ -260,7 +260,7 @@ smb_revalidate_inode(struct dentry *dentry) /* * Check whether we've recently refreshed the inode. */ - if (jiffies < inode->u.smbfs_i.oldmtime + HZ/10) + if (time_before(jiffies, inode->u.smbfs_i.oldmtime + HZ/10)) { #ifdef SMBFS_DEBUG_VERBOSE printk("smb_revalidate_inode: up-to-date, jiffies=%lu, oldtime=%lu\n", diff --git a/include/asm-alpha/machvec.h b/include/asm-alpha/machvec.h index 17d50c777690..035ffa4e2a94 100644 --- a/include/asm-alpha/machvec.h +++ b/include/asm-alpha/machvec.h @@ -4,6 +4,12 @@ #include #include +/* + * This file gets pulled in by asm/io.h from user space. We don't + * want most of this escaping. + */ + +#ifdef __KERNEL__ /* The following structure vectors all of the I/O and IRQ manipulation from the generic kernel to the hardware specific backend. */ @@ -122,4 +128,5 @@ extern int alpha_use_srm_setup; #endif #endif /* GENERIC */ +#endif #endif /* __ALPHA_MACHVEC_H */ diff --git a/include/asm-alpha/pgtable.h b/include/asm-alpha/pgtable.h index 47432c051ab7..639d7b420190 100644 --- a/include/asm-alpha/pgtable.h +++ b/include/asm-alpha/pgtable.h @@ -14,6 +14,7 @@ #include /* For TASK_SIZE */ #include #include +#include /* For the task lock */ /* Caches aren't brain-dead on the Alpha. */ diff --git a/include/asm-alpha/softirq.h b/include/asm-alpha/softirq.h index b47281a3b90e..66aed19eba88 100644 --- a/include/asm-alpha/softirq.h +++ b/include/asm-alpha/softirq.h @@ -27,7 +27,7 @@ static inline void clear_active_bhs(unsigned long x) extern inline void init_bh(int nr, void (*routine)(void)) { bh_base[nr] = routine; - bh_mask_count[nr] = 0; + atomic_set(&bh_mask_count[nr], 0); bh_mask |= 1 << nr; } @@ -116,12 +116,12 @@ extern inline void end_bh_atomic(void) extern inline void disable_bh(int nr) { bh_mask &= ~(1 << nr); - bh_mask_count[nr]++; + atomic_inc(&bh_mask_count[nr]); } extern inline void enable_bh(int nr) { - if (!--bh_mask_count[nr]) + if (atomic_dec_and_test(&bh_mask_count[nr])) bh_mask |= 1 << nr; } diff --git a/include/asm-alpha/spinlock.h b/include/asm-alpha/spinlock.h index 63837b1953ca..28baf0b7ad61 100644 --- a/include/asm-alpha/spinlock.h +++ b/include/asm-alpha/spinlock.h @@ -88,12 +88,12 @@ typedef struct { } spinlock_t; #if DEBUG_SPINLOCK -#define SPIN_LOCK_UNLOCKED {0, 1, 0, 0, 0, 0} +#define SPIN_LOCK_UNLOCKED (spinlock_t) {0, 1, 0, 0, 0, 0} #define spin_lock_init(x) \ ((x)->lock = 0, (x)->target_ipl = 0, (x)->debug_state = 1, \ (x)->previous = 0, (x)->task = 0) #else -#define SPIN_LOCK_UNLOCKED { 0 } +#define SPIN_LOCK_UNLOCKED (spinlock_t) { 0 } #define spin_lock_init(x) ((x)->lock = 0) #endif @@ -163,7 +163,7 @@ static inline void spin_lock(spinlock_t * lock) typedef struct { volatile int write_lock:1, read_counter:31; } rwlock_t; -#define RW_LOCK_UNLOCKED { 0, 0 } +#define RW_LOCK_UNLOCKED (rwlock_t) { 0, 0 } #if DEBUG_RWLOCK extern void write_lock(rwlock_t * lock); diff --git a/include/asm-i386/bitops.h b/include/asm-i386/bitops.h index 00dd9dcc847e..09f25dc78d1a 100644 --- a/include/asm-i386/bitops.h +++ b/include/asm-i386/bitops.h @@ -127,6 +127,7 @@ extern __inline__ int __test_bit(int nr, volatile void * addr) */ extern __inline__ int find_first_zero_bit(void * addr, unsigned size) { + int d0, d1, d2; int res; if (!size) @@ -142,9 +143,8 @@ extern __inline__ int find_first_zero_bit(void * addr, unsigned size) "1:\tsubl %%ebx,%%edi\n\t" "shll $3,%%edi\n\t" "addl %%edi,%%edx" - :"=d" (res) - :"c" ((size + 31) >> 5), "D" (addr), "b" (addr) - :"ax", "cx", "di"); + :"=d" (res), "=&c" (d0), "=&D" (d1), "=&a" (d2) + :"1" ((size + 31) >> 5), "2" (addr), "b" (addr)); return res; } diff --git a/include/asm-i386/checksum.h b/include/asm-i386/checksum.h index 8ec5f9c8d71f..addaea876b28 100644 --- a/include/asm-i386/checksum.h +++ b/include/asm-i386/checksum.h @@ -14,7 +14,7 @@ * * it's best to have buff aligned on a 32-bit boundary */ -unsigned int csum_partial(const unsigned char * buff, int len, unsigned int sum); +asmlinkage unsigned int csum_partial(const unsigned char * buff, int len, unsigned int sum); /* * the same as csum_partial, but copies from src while it @@ -24,8 +24,8 @@ unsigned int csum_partial(const unsigned char * buff, int len, unsigned int sum) * better 64-bit) boundary */ -unsigned int csum_partial_copy_generic( const char *src, char *dst, int len, int sum, - int *src_err_ptr, int *dst_err_ptr); +asmlinkage unsigned int csum_partial_copy_generic( const char *src, char *dst, int len, int sum, + int *src_err_ptr, int *dst_err_ptr); /* * Note: when you get a NULL pointer exception here this means someone diff --git a/include/asm-i386/posix_types.h b/include/asm-i386/posix_types.h index 6413683c20cc..0a794e306c1e 100644 --- a/include/asm-i386/posix_types.h +++ b/include/asm-i386/posix_types.h @@ -59,10 +59,14 @@ typedef struct { #undef __FD_ZERO #define __FD_ZERO(fdsetp) \ - __asm__ __volatile__("cld ; rep ; stosl" \ - :"=m" (*(__kernel_fd_set *) (fdsetp)) \ - :"a" (0), "c" (__FDSET_LONGS), \ - "D" ((__kernel_fd_set *) (fdsetp)) :"cx","di") +do { \ + int __d0, __d1; \ + __asm__ __volatile__("cld ; rep ; stosl" \ + :"=m" (*(__kernel_fd_set *) (fdsetp)), \ + "=&c" (__d0), "=&D" (__d1) \ + :"a" (0), "1" (__FDSET_LONGS), \ + "2" ((__kernel_fd_set *) (fdsetp)) : "memory"); \ +} while (0) #endif /* defined(__KERNEL__) || !defined(__GLIBC__) || (__GLIBC__ < 2) */ diff --git a/include/asm-i386/smplock.h b/include/asm-i386/smplock.h index 3bb933e4277a..73c9cf9271f5 100644 --- a/include/asm-i386/smplock.h +++ b/include/asm-i386/smplock.h @@ -51,7 +51,7 @@ extern __inline__ void unlock_kernel(void) { __asm__ __volatile__( "decl %1\n\t" - "jns 9f\n" + "jns 9f\n\t" spin_unlock_string "\n9:" :"=m" (__dummy_lock(&kernel_flag)), diff --git a/include/asm-i386/system.h b/include/asm-i386/system.h index 65012f648da4..9e01b26174d4 100644 --- a/include/asm-i386/system.h +++ b/include/asm-i386/system.h @@ -35,30 +35,30 @@ extern void FASTCALL(__switch_to(struct task_struct *prev, struct task_struct *n "a" (prev), "d" (next)); \ } while (0) -#define _set_base(addr,base) \ -__asm__("movw %%dx,%0\n\t" \ +#define _set_base(addr,base) do { unsigned long __pr; \ +__asm__ __volatile__ ("movw %%dx,%1\n\t" \ "rorl $16,%%edx\n\t" \ - "movb %%dl,%1\n\t" \ - "movb %%dh,%2" \ - : /* no output */ \ + "movb %%dl,%2\n\t" \ + "movb %%dh,%3" \ + :"=&d" (__pr) \ :"m" (*((addr)+2)), \ "m" (*((addr)+4)), \ "m" (*((addr)+7)), \ - "d" (base) \ - :"dx") + "0" (base) \ + ); } while(0) -#define _set_limit(addr,limit) \ -__asm__("movw %%dx,%0\n\t" \ +#define _set_limit(addr,limit) do { unsigned long __lr; \ +__asm__ __volatile__ ("movw %%dx,%1\n\t" \ "rorl $16,%%edx\n\t" \ - "movb %1,%%dh\n\t" \ + "movb %2,%%dh\n\t" \ "andb $0xf0,%%dh\n\t" \ "orb %%dh,%%dl\n\t" \ - "movb %%dl,%1" \ - : /* no output */ \ + "movb %%dl,%2" \ + :"=&d" (__lr) \ :"m" (*(addr)), \ "m" (*((addr)+6)), \ - "d" (limit) \ - :"dx") + "0" (limit) \ + ); } while(0) #define set_base(ldt,base) _set_base( ((char *)&(ldt)) , (base) ) #define set_limit(ldt,limit) _set_limit( ((char *)&(ldt)) , ((limit)-1)>>12 ) diff --git a/include/asm-i386/uaccess.h b/include/asm-i386/uaccess.h index dcc56f31c166..5cfa0512fe09 100644 --- a/include/asm-i386/uaccess.h +++ b/include/asm-i386/uaccess.h @@ -250,13 +250,15 @@ do { \ /* Generic arbitrary sized copy. */ #define __copy_user(to,from,size) \ +do { \ + int __d0, __d1; \ __asm__ __volatile__( \ "0: rep; movsl\n" \ - " movl %1,%0\n" \ + " movl %3,%0\n" \ "1: rep; movsb\n" \ "2:\n" \ ".section .fixup,\"ax\"\n" \ - "3: lea 0(%1,%0,4),%0\n" \ + "3: lea 0(%3,%0,4),%0\n" \ " jmp 2b\n" \ ".previous\n" \ ".section __ex_table,\"a\"\n" \ @@ -264,18 +266,21 @@ do { \ " .long 0b,3b\n" \ " .long 1b,2b\n" \ ".previous" \ - : "=&c"(size) \ - : "r"(size & 3), "0"(size / 4), "D"(to), "S"(from) \ - : "di", "si", "memory") + : "=&c"(size), "=&D" (__d0), "=&S" (__d1) \ + : "r"(size & 3), "0"(size / 4), "1"(to), "2"(from) \ + : "memory"); \ +} while (0) #define __copy_user_zeroing(to,from,size) \ +do { \ + int __d0, __d1; \ __asm__ __volatile__( \ "0: rep; movsl\n" \ - " movl %1,%0\n" \ + " movl %3,%0\n" \ "1: rep; movsb\n" \ "2:\n" \ ".section .fixup,\"ax\"\n" \ - "3: lea 0(%1,%0,4),%0\n" \ + "3: lea 0(%3,%0,4),%0\n" \ "4: pushl %0\n" \ " pushl %%eax\n" \ " xorl %%eax,%%eax\n" \ @@ -289,9 +294,10 @@ do { \ " .long 0b,3b\n" \ " .long 1b,4b\n" \ ".previous" \ - : "=&c"(size) \ - : "r"(size & 3), "0"(size / 4), "D"(to), "S"(from) \ - : "di", "si", "memory"); + : "=&c"(size), "=&D" (__d0), "=&S" (__d1) \ + : "r"(size & 3), "0"(size / 4), "1"(to), "2"(from) \ + : "memory"); \ +} while (0) /* We let the __ versions of copy_from/to_user inline, because they're often * used in fast paths and have only a small space overhead. @@ -314,6 +320,7 @@ __generic_copy_to_user_nocheck(void *to, const void *from, unsigned long n) /* Optimize just a little bit when we know the size of the move. */ #define __constant_copy_user(to, from, size) \ do { \ + int __d0, __d1; \ switch (size & 3) { \ default: \ __asm__ __volatile__( \ @@ -327,9 +334,9 @@ do { \ " .align 4\n" \ " .long 0b,2b\n" \ ".previous" \ - : "=c"(size) \ - : "S"(from), "D"(to), "0"(size/4) \ - : "di", "si", "memory"); \ + : "=c"(size), "=&S" (__d0), "=&D" (__d1)\ + : "1"(from), "2"(to), "0"(size/4) \ + : "memory"); \ break; \ case 1: \ __asm__ __volatile__( \ @@ -346,9 +353,9 @@ do { \ " .long 0b,3b\n" \ " .long 1b,4b\n" \ ".previous" \ - : "=c"(size) \ - : "S"(from), "D"(to), "0"(size/4) \ - : "di", "si", "memory"); \ + : "=c"(size), "=&S" (__d0), "=&D" (__d1)\ + : "1"(from), "2"(to), "0"(size/4) \ + : "memory"); \ break; \ case 2: \ __asm__ __volatile__( \ @@ -365,9 +372,9 @@ do { \ " .long 0b,3b\n" \ " .long 1b,4b\n" \ ".previous" \ - : "=c"(size) \ - : "S"(from), "D"(to), "0"(size/4) \ - : "di", "si", "memory"); \ + : "=c"(size), "=&S" (__d0), "=&D" (__d1)\ + : "1"(from), "2"(to), "0"(size/4) \ + : "memory"); \ break; \ case 3: \ __asm__ __volatile__( \ @@ -387,9 +394,9 @@ do { \ " .long 1b,5b\n" \ " .long 2b,6b\n" \ ".previous" \ - : "=c"(size) \ - : "S"(from), "D"(to), "0"(size/4) \ - : "di", "si", "memory"); \ + : "=c"(size), "=&S" (__d0), "=&D" (__d1)\ + : "1"(from), "2"(to), "0"(size/4) \ + : "memory"); \ break; \ } \ } while (0) @@ -397,6 +404,7 @@ do { \ /* Optimize just a little bit when we know the size of the move. */ #define __constant_copy_user_zeroing(to, from, size) \ do { \ + int __d0, __d1; \ switch (size & 3) { \ default: \ __asm__ __volatile__( \ @@ -416,9 +424,9 @@ do { \ " .align 4\n" \ " .long 0b,2b\n" \ ".previous" \ - : "=c"(size) \ - : "S"(from), "D"(to), "0"(size/4) \ - : "di", "si", "memory"); \ + : "=c"(size), "=&S" (__d0), "=&D" (__d1)\ + : "1"(from), "2"(to), "0"(size/4) \ + : "memory"); \ break; \ case 1: \ __asm__ __volatile__( \ @@ -448,9 +456,9 @@ do { \ " .long 0b,3b\n" \ " .long 1b,4b\n" \ ".previous" \ - : "=c"(size) \ - : "S"(from), "D"(to), "0"(size/4) \ - : "di", "si", "memory"); \ + : "=c"(size), "=&S" (__d0), "=&D" (__d1)\ + : "1"(from), "2"(to), "0"(size/4) \ + : "memory"); \ break; \ case 2: \ __asm__ __volatile__( \ @@ -480,9 +488,9 @@ do { \ " .long 0b,3b\n" \ " .long 1b,4b\n" \ ".previous" \ - : "=c"(size) \ - : "S"(from), "D"(to), "0"(size/4) \ - : "di", "si", "memory"); \ + : "=c"(size), "=&S" (__d0), "=&D" (__d1)\ + : "1"(from), "2"(to), "0"(size/4) \ + : "memory"); \ break; \ case 3: \ __asm__ __volatile__( \ @@ -522,9 +530,9 @@ do { \ " .long 1b,5b\n" \ " .long 2b,6b\n" \ ".previous" \ - : "=c"(size) \ - : "S"(from), "D"(to), "0"(size/4) \ - : "di", "si", "memory"); \ + : "=c"(size), "=&S" (__d0), "=&D" (__d1)\ + : "1"(from), "2"(to), "0"(size/4) \ + : "memory"); \ break; \ } \ } while (0) diff --git a/include/asm-ppc/softirq.h b/include/asm-ppc/softirq.h index 739b22580326..e2064f07d2b4 100644 --- a/include/asm-ppc/softirq.h +++ b/include/asm-ppc/softirq.h @@ -12,7 +12,7 @@ extern unsigned int local_bh_count[NR_CPUS]; extern inline void init_bh(int nr, void (*routine)(void)) { bh_base[nr] = routine; - bh_mask_count[nr] = 0; + atomic_set(&bh_mask_count[nr], 0); bh_mask |= 1 << nr; } @@ -96,13 +96,13 @@ extern inline void end_bh_atomic(void) extern inline void disable_bh(int nr) { bh_mask &= ~(1 << nr); - bh_mask_count[nr]++; + atomic_inc(&bh_mask_count[nr]); synchronize_bh(); } extern inline void enable_bh(int nr) { - if (!--bh_mask_count[nr]) + if (atomic_dec_and_test(&bh_mask_count[nr])) bh_mask |= 1 << nr; } diff --git a/include/linux/atalk.h b/include/linux/atalk.h index 5641129d7efb..e9d209791d10 100644 --- a/include/linux/atalk.h +++ b/include/linux/atalk.h @@ -10,7 +10,7 @@ #define ATPORT_FIRST 1 #define ATPORT_RESERVED 128 -#define ATPORT_LAST 255 +#define ATPORT_LAST 254 /* 254 is only legal on localtalk */ #define ATADDR_ANYNET (__u16)0 #define ATADDR_ANYNODE (__u8)0 #define ATADDR_ANYPORT (__u8)0 diff --git a/include/linux/file.h b/include/linux/file.h index 0884fad2ffe2..8fd72b507ecf 100644 --- a/include/linux/file.h +++ b/include/linux/file.h @@ -6,7 +6,6 @@ #define __LINUX_FILE_H extern void __fput(struct file *); -extern void insert_file_free(struct file *file); /* * Check whether the specified task has the fd open. Since the task @@ -50,34 +49,23 @@ extern inline void fd_install(unsigned int fd, struct file *file) current->files->fd[fd] = file; } -/* It does not matter which list it is on. */ -extern inline void remove_filp(struct file *file) -{ - if(file->f_next) - file->f_next->f_pprev = file->f_pprev; - *file->f_pprev = file->f_next; -} - -extern inline void fput(struct file *file) -{ - int count = file->f_count-1; - - if (!count) { - locks_remove_flock(file); - __fput(file); - file->f_count = 0; - remove_filp(file); - insert_file_free(file); - } else - file->f_count = count; -} - -extern inline void put_filp(struct file *file) -{ - if(--file->f_count == 0) { - remove_filp(file); - insert_file_free(file); - } -} +/* + * 23/12/1998 Marcin Dalecki : + * + * Since those functions where calling other functions, it was compleatly + * bogous to make them all "extern inline". + * + * The removal of this pseudo optimization saved me scandaleous: + * + * 3756 (i386 arch) + * + * precious bytes from my kernel, even without counting all the code compiled + * as module! + * + * I suspect there are many other similiar "optimizations" across the + * kernel... + */ +extern void fput(struct file *file); +extern void put_filp(struct file *file); #endif diff --git a/include/linux/fs.h b/include/linux/fs.h index 0139168ca809..9a1684a0e269 100644 --- a/include/linux/fs.h +++ b/include/linux/fs.h @@ -466,7 +466,7 @@ struct file_lock { } fl_u; }; -extern struct file_lock *file_lock_table; +extern struct file_lock *file_lock_table; #include @@ -692,7 +692,8 @@ extern int close_fp(struct file *, fl_owner_t id); extern struct file *filp_open(const char *, int, int); extern char * getname(const char * filename); -extern void putname(char * name); +#define __getname() ((char *) __get_free_page(GFP_KERNEL)) +#define putname(name) free_page((unsigned long)(name)) extern void kill_fasync(struct fasync_struct *fa, int sig); extern int register_blkdev(unsigned int, const char *, struct file_operations *); @@ -702,11 +703,16 @@ extern int blkdev_release (struct inode * inode); extern struct file_operations def_blk_fops; extern struct inode_operations blkdev_inode_operations; +/* fs/devices.c */ extern int register_chrdev(unsigned int, const char *, struct file_operations *); extern int unregister_chrdev(unsigned int major, const char * name); extern int chrdev_open(struct inode * inode, struct file * filp); extern struct file_operations def_chr_fops; extern struct inode_operations chrdev_inode_operations; +extern char * bdevname(kdev_t dev); +extern char * cdevname(kdev_t dev); +extern char * kdevname(kdev_t dev); + extern void init_fifo(struct inode * inode); extern struct inode_operations fifo_inode_operations; @@ -815,8 +821,6 @@ extern struct buffer_head * get_hash_table(kdev_t, int, int); extern struct buffer_head * getblk(kdev_t, int, int); extern struct buffer_head * find_buffer(kdev_t dev, int block, int size); extern void ll_rw_block(int, int, struct buffer_head * bh[]); -extern void ll_rw_page(int, kdev_t, unsigned long, char *); -extern void ll_rw_swap_file(int, kdev_t, unsigned int *, int, char *); extern int is_read_only(kdev_t); extern void __brelse(struct buffer_head *); extern inline void brelse(struct buffer_head *buf) diff --git a/include/linux/genhd.h b/include/linux/genhd.h index fe89b7e7a99e..96469a0bdb63 100644 --- a/include/linux/genhd.h +++ b/include/linux/genhd.h @@ -108,12 +108,19 @@ struct solaris_x86_vtoc { #ifdef CONFIG_BSD_DISKLABEL /* * BSD disklabel support by Yossi Gottlieb + * updated by Marc Espie */ -#define BSD_PARTITION 0xa5 /* Partition ID */ +#define FREEBSD_PARTITION 0xa5 /* FreeBSD Partition ID */ +#define OPENBSD_PARTITION 0xa6 /* OpenBSD Partition ID */ +#define NETBSD_PARTITION 0xa9 /* NetBSD Partition ID */ +#define BSDI_PARTITION 0xb7 /* BSDI Partition ID */ + +/* check against BSD src/sys/sys/disklabel.h for consistency */ #define BSD_DISKMAGIC (0x82564557UL) /* The disk magic number */ #define BSD_MAXPARTITIONS 8 +#define OPENBSD_MAXPARTITIONS 16 #define BSD_FS_UNUSED 0 /* disklabel unused partition entry ID */ struct bsd_disklabel { __u32 d_magic; /* the magic number */ @@ -160,6 +167,62 @@ struct bsd_disklabel { #endif /* CONFIG_BSD_DISKLABEL */ +#ifdef CONFIG_UNIXWARE_DISKLABEL +/* + * Unixware slices support by Andrzej Krzysztofowicz + * and Krzysztof G. Baranowski + */ + +#define UNIXWARE_PARTITION 0x63 /* Partition ID, same as */ + /* GNU_HURD and SCO Unix */ +#define UNIXWARE_DISKMAGIC (0xCA5E600DUL) /* The disk magic number */ +#define UNIXWARE_DISKMAGIC2 (0x600DDEEEUL) /* The slice table magic nr */ +#define UNIXWARE_NUMSLICE 16 +#define UNIXWARE_FS_UNUSED 0 /* Unused slice entry ID */ + +struct unixware_slice { + __u16 s_label; /* label */ + __u16 s_flags; /* permission flags */ + __u32 start_sect; /* starting sector */ + __u32 nr_sects; /* number of sectors in slice */ +}; + +struct unixware_disklabel { + __u32 d_type; /* drive type */ + __u32 d_magic; /* the magic number */ + __u32 d_version; /* version number */ + char d_serial[12]; /* serial number of the device */ + __u32 d_ncylinders; /* # of data cylinders per device */ + __u32 d_ntracks; /* # of tracks per cylinder */ + __u32 d_nsectors; /* # of data sectors per track */ + __u32 d_secsize; /* # of bytes per sector */ + __u32 d_part_start; /* # of first sector of this partition */ + __u32 d_unknown1[12]; /* ? */ + __u32 d_alt_tbl; /* byte offset of alternate table */ + __u32 d_alt_len; /* byte length of alternate table */ + __u32 d_phys_cyl; /* # of physical cylinders per device */ + __u32 d_phys_trk; /* # of physical tracks per cylinder */ + __u32 d_phys_sec; /* # of physical sectors per track */ + __u32 d_phys_bytes; /* # of physical bytes per sector */ + __u32 d_unknown2; /* ? */ + __u32 d_unknown3; /* ? */ + __u32 d_pad[8]; /* pad */ + + struct unixware_vtoc { + __u32 v_magic; /* the magic number */ + __u32 v_version; /* version number */ + char v_name[8]; /* volume name */ + __u16 v_nslices; /* # of slices */ + __u16 v_unknown1; /* ? */ + __u32 v_reserved[10]; /* reserved */ + struct unixware_slice + v_slice[UNIXWARE_NUMSLICE]; /* slice headers */ + } vtoc; + +}; /* 408 */ + +#endif /* CONFIG_UNIXWARE_DISKLABEL */ + extern struct gendisk *gendisk_head; /* linked list of disks */ /* diff --git a/include/linux/hfs_fs_i.h b/include/linux/hfs_fs_i.h index 453896882741..03585a08644a 100644 --- a/include/linux/hfs_fs_i.h +++ b/include/linux/hfs_fs_i.h @@ -33,6 +33,9 @@ struct hfs_inode_info { const struct hfs_hdr_layout *default_layout; struct hfs_hdr_layout *layout; + /* to deal with localtime ugliness */ + int tz_secondswest; + /* for dentry cleanup */ void (*d_drop_op)(struct dentry *, const ino_t); }; diff --git a/include/linux/ipc.h b/include/linux/ipc.h index 9349f0f4970a..851ff4cef5ee 100644 --- a/include/linux/ipc.h +++ b/include/linux/ipc.h @@ -21,6 +21,11 @@ struct ipc_perm #define IPC_EXCL 00002000 /* fail if key exists */ #define IPC_NOWAIT 00004000 /* return error on wait */ +/* these fields are used by the DIPC package so the kernel as standard + should avoid using them if possible */ + +#define IPC_DIPC 00010000 /* make it distributed */ +#define IPC_OWN 00020000 /* this machine is the DIPC owner */ /* * Control commands used with semctl, msgctl and shmctl diff --git a/include/linux/ipx.h b/include/linux/ipx.h index c6846779b7ad..8b9d6bb127ae 100644 --- a/include/linux/ipx.h +++ b/include/linux/ipx.h @@ -76,6 +76,7 @@ struct ipx_route_def #define SIOCAIPXITFCRT (SIOCPROTOPRIVATE) #define SIOCAIPXPRISLT (SIOCPROTOPRIVATE+1) #define SIOCIPXCFGDATA (SIOCPROTOPRIVATE+2) +#define SIOCIPXNCPCONN (SIOCPROTOPRIVATE+3) #ifdef __KERNEL__ #include diff --git a/include/linux/module.h b/include/linux/module.h index ad3d10baf6cb..94cce874f618 100644 --- a/include/linux/module.h +++ b/include/linux/module.h @@ -20,6 +20,7 @@ # endif #endif /* __GENKSYMS__ */ +#include /* Don't need to bring in all of uaccess.h just for this decl. */ struct exception_table_entry; @@ -54,7 +55,12 @@ struct module const char *name; unsigned long size; - long usecount; + union + { + atomic_t usecount; + long pad; + } uc; /* Needs to keep its size - so says rth */ + unsigned long flags; /* AUTOCLEAN et al */ unsigned nsyms; @@ -80,10 +86,10 @@ struct module struct module_info { - unsigned long addr; - unsigned long size; - unsigned long flags; - long usecount; + unsigned long addr; + unsigned long size; + unsigned long flags; + long usecount; }; /* Bits of module.flags. */ @@ -114,17 +120,17 @@ struct module_info /* Backwards compatibility definition. */ -#define GET_USE_COUNT(module) ((module)->usecount) +#define GET_USE_COUNT(module) (atomic_read(&(module)->uc.usecount)) /* Poke the use count of a module. */ #define __MOD_INC_USE_COUNT(mod) \ - ((mod)->usecount++, (mod)->flags |= MOD_VISITED|MOD_USED_ONCE) + (atomic_inc(&(mod)->uc.usecount), (mod)->flags |= MOD_VISITED|MOD_USED_ONCE) #define __MOD_DEC_USE_COUNT(mod) \ - ((mod)->usecount--, (mod)->flags |= MOD_VISITED) + (atomic_dec(&(mod)->uc.usecount), (mod)->flags |= MOD_VISITED) #define __MOD_IN_USE(mod) \ (mod_member_present((mod), can_unload) && (mod)->can_unload \ - ? (mod)->can_unload() : (mod)->usecount) + ? (mod)->can_unload() : atomic_read(&(mod)->uc.usecount)) /* Indirect stringification. */ diff --git a/include/linux/msdos_fs_sb.h b/include/linux/msdos_fs_sb.h index 4985eef157f0..4497eeedbe70 100644 --- a/include/linux/msdos_fs_sb.h +++ b/include/linux/msdos_fs_sb.h @@ -35,9 +35,11 @@ struct vfat_unicode { struct msdos_sb_info { unsigned short cluster_size; /* sectors/cluster */ unsigned char fats,fat_bits; /* number of FATs, FAT bits (12 or 16) */ - unsigned short fat_start,fat_length; /* FAT start & length (sec.) */ - unsigned short dir_start,dir_entries; /* root dir start & entries */ - unsigned short data_start; /* first data sector */ + unsigned short fat_start; + unsigned long fat_length; /* FAT start & length (sec.) */ + unsigned long dir_start; + unsigned short dir_entries; /* root dir start & entries */ + unsigned long data_start; /* first data sector */ unsigned long clusters; /* number of clusters */ unsigned long root_cluster; /* first cluster of the root directory */ unsigned long fsinfo_offset; /* FAT32 fsinfo offset from start of disk */ diff --git a/include/linux/sem.h b/include/linux/sem.h index a5b3134bfaf6..3fb2a48f6822 100644 --- a/include/linux/sem.h +++ b/include/linux/sem.h @@ -92,6 +92,7 @@ struct sem_queue { struct semid_ds * sma; /* semaphore array for operations */ struct sembuf * sops; /* array of pending operations */ int nsops; /* number of operations */ + int alter; /* operation will alter semaphore */ }; /* Each task has a list of undo requests. They are executed automatically diff --git a/include/linux/swap.h b/include/linux/swap.h index 9257ca698e68..4b7a5ca699dc 100644 --- a/include/linux/swap.h +++ b/include/linux/swap.h @@ -87,6 +87,7 @@ extern int try_to_free_pages(unsigned int gfp_mask, int count); /* linux/mm/page_io.c */ extern void rw_swap_page(int, unsigned long, char *, int); extern void rw_swap_page_nocache(int, unsigned long, char *); +extern void rw_swap_page_nolock(int, unsigned long, char *, int); extern void swap_after_unlock_page (unsigned long entry); /* linux/mm/page_alloc.c */ diff --git a/include/linux/videodev.h b/include/linux/videodev.h index ce043b96cf68..bbf9d8351f21 100644 --- a/include/linux/videodev.h +++ b/include/linux/videodev.h @@ -261,6 +261,8 @@ struct video_unit #define VID_HARDWARE_PERMEDIA2 14 /* Reserved for Permedia2 */ #define VID_HARDWARE_RIVA128 15 /* Reserved for RIVA 128 */ #define VID_HARDWARE_PLANB 16 /* PowerMac motherboard video-in */ +#define VID_HARDWARE_BROADWAY 17 /* Broadway project */ +#define VID_HARDWARE_GEMTEK 18 /* * Initialiser list diff --git a/include/net/sock.h b/include/net/sock.h index a9cc39260216..03e4b7fea831 100644 --- a/include/net/sock.h +++ b/include/net/sock.h @@ -128,6 +128,11 @@ struct ipx_opt { unsigned char node[IPX_NODE_LEN]; #endif unsigned short type; +/* + * To handle special ncp connection-handling sockets for mars_nwe, + * the connection number must be stored in the socket. + */ + unsigned short ipx_ncp_conn; }; #endif diff --git a/include/video/fbcon.h b/include/video/fbcon.h index 5502b2381133..4fe4eb7eb9ec 100644 --- a/include/video/fbcon.h +++ b/include/video/fbcon.h @@ -441,6 +441,7 @@ static __inline__ void *mymemset(void *s, size_t count) static __inline__ void fast_memmove(void *d, const void *s, size_t count) { + int d0, d1, d2, d3; if (d < s) { __asm__ __volatile__ ( "cld\n\t" @@ -452,9 +453,9 @@ __asm__ __volatile__ ( "movsw\n" "2:\trep\n\t" "movsl" - : /* no output */ - :"c"(count),"D"((long)d),"S"((long)s) - :"cx","di","si","memory"); + : "=&c" (d0), "=&D" (d1), "=&S" (d2) + :"0"(count),"1"((long)d),"2"((long)s) + :"memory"); } else { __asm__ __volatile__ ( "std\n\t" @@ -475,9 +476,9 @@ __asm__ __volatile__ ( "2:\trep\n\t" "movsl\n\t" "cld" - : /* no output */ - :"c"(count),"D"(count-4+(long)d),"S"(count-4+(long)s) - :"ax","cx","di","si","memory"); + : "=&c" (d0), "=&D" (d1), "=&S" (d2), "=&a" (d3) + :"0"(count),"1"(count-4+(long)d),"2"(count-4+(long)s) + :"memory"); } } diff --git a/ipc/sem.c b/ipc/sem.c index 199a08ff7e9a..8478ead6b07d 100644 --- a/ipc/sem.c +++ b/ipc/sem.c @@ -29,6 +29,25 @@ * see a clean way to get the old behavior with the new design. * The POSIX standard and SVID should be consulted to determine * what behavior is mandated. + * + * Further notes on refinement (Christoph Rohland, December 1998): + * - The POSIX standard says, that the undo adjustments simply should + * redo. So the current implementation is o.K. + * - The previous code had two flaws: + * 1) It actively gave the semaphore to the next waiting process + * sleeping on the semaphore. Since this process did not have the + * cpu this led to many unnecessary context switches and bad + * performance. Now we only check which process should be able to + * get the semaphore and if this process wants to reduce some + * semaphore value we simply wake it up without doing the + * operation. So it has to try to get it later. Thus e.g. the + * running process may reaquire the semaphore during the current + * time slice. If it only waits for zero or increases the semaphore, + * we do the operation in advance and wake it up. + * 2) It did not wake up all zero waiting processes. We try to do + * better but only get the semops right which only wait for zero or + * increase. If there are decrement operations in the operations + * array we do the same as before. */ #include @@ -158,12 +177,26 @@ out: /* Manage the doubly linked list sma->sem_pending as a FIFO: * insert new queue elements at the tail sma->sem_pending_last. */ -static inline void insert_into_queue (struct semid_ds * sma, struct sem_queue * q) +static inline void append_to_queue (struct semid_ds * sma, + struct sem_queue * q) { *(q->prev = sma->sem_pending_last) = q; *(sma->sem_pending_last = &q->next) = NULL; } -static inline void remove_from_queue (struct semid_ds * sma, struct sem_queue * q) + +static inline void prepend_to_queue (struct semid_ds * sma, + struct sem_queue * q) +{ + q->next = sma->sem_pending; + *(q->prev = &sma->sem_pending) = q; + if (q->next) + q->next->prev = &q->next; + else /* sma->sem_pending_last == &sma->sem_pending */ + sma->sem_pending_last = &q->next; +} + +static inline void remove_from_queue (struct semid_ds * sma, + struct sem_queue * q) { *(q->prev) = q->next; if (q->next) @@ -173,112 +206,100 @@ static inline void remove_from_queue (struct semid_ds * sma, struct sem_queue * q->prev = NULL; /* mark as removed */ } -/* Determine whether a sequence of semaphore operations would succeed +/* + * Determine whether a sequence of semaphore operations would succeed * all at once. Return 0 if yes, 1 if need to sleep, else return error code. */ -static int try_semop (struct semid_ds * sma, struct sembuf * sops, int nsops) -{ - int result = 0; - int i = 0; - - while (i < nsops) { - struct sembuf * sop = &sops[i]; - struct sem * curr = &sma->sem_base[sop->sem_num]; - if (sop->sem_op + curr->semval > SEMVMX) { - result = -ERANGE; - break; - } - if (!sop->sem_op && curr->semval) { - if (sop->sem_flg & IPC_NOWAIT) - result = -EAGAIN; - else - result = 1; - break; - } - i++; - curr->semval += sop->sem_op; - if (curr->semval < 0) { - if (sop->sem_flg & IPC_NOWAIT) - result = -EAGAIN; - else - result = 1; - break; - } - } - while (--i >= 0) { - struct sembuf * sop = &sops[i]; - struct sem * curr = &sma->sem_base[sop->sem_num]; - curr->semval -= sop->sem_op; - } - return result; -} -/* Actually perform a sequence of semaphore operations. Atomically. */ -/* This assumes that try_semop() already returned 0. */ -static int do_semop (struct semid_ds * sma, struct sembuf * sops, int nsops, - struct sem_undo * un, int pid) +static int try_atomic_semop (struct semid_ds * sma, struct sembuf * sops, + int nsops, struct sem_undo *un, int pid, + int do_undo) { - int i; + int result, sem_op; + struct sembuf *sop; + struct sem * curr; - for (i = 0; i < nsops; i++) { - struct sembuf * sop = &sops[i]; - struct sem * curr = &sma->sem_base[sop->sem_num]; - if (sop->sem_op + curr->semval > SEMVMX) { - printk("do_semop: race\n"); - break; - } - if (!sop->sem_op) { - if (curr->semval) { - printk("do_semop: race\n"); - break; - } - } else { - curr->semval += sop->sem_op; - if (curr->semval < 0) { - printk("do_semop: race\n"); - break; - } - if (sop->sem_flg & SEM_UNDO) - un->semadj[sop->sem_num] -= sop->sem_op; - } - curr->sempid = pid; + for (sop = sops; sop < sops + nsops; sop++) { + curr = sma->sem_base + sop->sem_num; + sem_op = sop->sem_op; + + if (!sem_op && curr->semval) + goto would_block; + + curr->sempid = (curr->sempid << 16) | pid; + curr->semval += sem_op; + if (sop->sem_flg & SEM_UNDO) + un->semadj[sop->sem_num] -= sem_op; + + if (curr->semval < 0) + goto would_block; + if (curr->semval > SEMVMX) + goto out_of_range; } - sma->sem_otime = CURRENT_TIME; - /* Previous implementation returned the last semaphore's semval. - * This is wrong because we may not have checked read permission, - * only write permission. - */ + if (do_undo) + { + sop--; + result = 0; + goto undo; + } + + sma->sem_otime = CURRENT_TIME; return 0; + +out_of_range: + result = -ERANGE; + goto undo; + +would_block: + if (sop->sem_flg & IPC_NOWAIT) + result = -EAGAIN; + else + result = 1; + +undo: + while (sop >= sops) { + curr = sma->sem_base + sop->sem_num; + curr->semval -= sop->sem_op; + curr->sempid >>= 16; + + if (sop->sem_flg & SEM_UNDO) + un->semadj[sop->sem_num] += sop->sem_op; + sop--; + } + + return result; } /* Go through the pending queue for the indicated semaphore - * looking for tasks that can be completed. Keep cycling through - * the queue until a pass is made in which no process is woken up. + * looking for tasks that can be completed. */ static void update_queue (struct semid_ds * sma) { - int wokeup, error; + int error; struct sem_queue * q; - do { - wokeup = 0; - for (q = sma->sem_pending; q; q = q->next) { - error = try_semop(sma, q->sops, q->nsops); - /* Does q->sleeper still need to sleep? */ - if (error > 0) - continue; - /* Perform the operations the sleeper was waiting for */ - if (!error) - error = do_semop(sma, q->sops, q->nsops, q->undo, q->pid); - q->status = error; - /* Remove it from the queue */ - remove_from_queue(sma,q); - /* Wake it up */ - wake_up_interruptible(&q->sleeper); /* doesn't sleep! */ - wokeup++; - } - } while (wokeup); + for (q = sma->sem_pending; q; q = q->next) { + + if (q->status == 1) + return; /* wait for other process */ + + error = try_atomic_semop(sma, q->sops, q->nsops, + q->undo, q->pid, q->alter); + + /* Does q->sleeper still need to sleep? */ + if (error <= 0) { + /* Found one, wake it up */ + wake_up_interruptible(&q->sleeper); + if (error == 0 && q->alter) { + /* if q-> alter let it self try */ + q->status = 1; + return; + } + q->status = error; + remove_from_queue(sma,q); + } + } } /* The following counts are associated to each semaphore: @@ -460,7 +481,7 @@ asmlinkage int sys_semctl (int semid, int semnum, int cmd, union semun arg) goto out; switch (cmd) { case GETVAL : err = curr->semval; goto out; - case GETPID : err = curr->sempid; goto out; + case GETPID : err = curr->sempid & 0xffff; goto out; case GETNCNT: err = count_semncnt(sma,semnum); goto out; case GETZCNT: err = count_semzcnt(sma,semnum); goto out; case GETALL: @@ -582,11 +603,12 @@ out: asmlinkage int sys_semop (int semid, struct sembuf *tsops, unsigned nsops) { - int i, id, size, error = -EINVAL; + int id, size, error = -EINVAL; struct semid_ds *sma; struct sembuf sops[SEMOPM], *sop; struct sem_undo *un; - int undos = 0, alter = 0; + int undos = 0, decrease = 0, alter = 0; + struct sem_queue queue; lock_kernel(); if (nsops < 1 || semid < 0) @@ -595,8 +617,6 @@ asmlinkage int sys_semop (int semid, struct sembuf *tsops, unsigned nsops) if (nsops > SEMOPM) goto out; error = -EFAULT; - if (!tsops) - goto out; if (copy_from_user (sops, tsops, nsops * sizeof(*tsops))) goto out; id = (unsigned int) semid % SEMMNI; @@ -606,22 +626,23 @@ asmlinkage int sys_semop (int semid, struct sembuf *tsops, unsigned nsops) error = -EIDRM; if (sma->sem_perm.seq != (unsigned int) semid / SEMMNI) goto out; - for (i = 0; i < nsops; i++) { - sop = &sops[i]; + error = -EFBIG; + for (sop = sops; sop < sops + nsops; sop++) { if (sop->sem_num >= sma->sem_nsems) goto out; if (sop->sem_flg & SEM_UNDO) undos++; - if (sop->sem_op) - alter++; + if (sop->sem_op < 0) + decrease = 1; + if (sop->sem_op > 0) + alter = 1; } + alter |= decrease; + error = -EACCES; if (ipcperms(&sma->sem_perm, alter ? S_IWUGO : S_IRUGO)) goto out; - error = try_semop(sma, sops, nsops); - if (error < 0) - goto out; if (undos) { /* Make sure we have an undo structure * for this process and this semaphore set. @@ -646,40 +667,59 @@ asmlinkage int sys_semop (int semid, struct sembuf *tsops, unsigned nsops) } } else un = NULL; - if (error == 0) { - /* the operations go through immediately */ - error = do_semop(sma, sops, nsops, un, current->pid); - /* maybe some queued-up processes were waiting for this */ - update_queue(sma); - goto out; - } else { - /* We need to sleep on this operation, so we put the current - * task into the pending queue and go to sleep. - */ - struct sem_queue queue; - - queue.sma = sma; - queue.sops = sops; - queue.nsops = nsops; - queue.undo = un; - queue.pid = current->pid; - queue.status = 0; - insert_into_queue(sma,&queue); - queue.sleeper = NULL; - current->semsleeping = &queue; - interruptible_sleep_on(&queue.sleeper); - current->semsleeping = NULL; - /* When we wake up, either the operation is finished, - * or some kind of error happened. - */ - if (!queue.prev) { - /* operation is finished, update_queue() removed us */ - error = queue.status; - } else { - remove_from_queue(sma,&queue); - error = -EINTR; - } - } + + error = try_atomic_semop (sma, sops, nsops, un, current->pid, 0); + if (error <= 0) + goto update; + + /* We need to sleep on this operation, so we put the current + * task into the pending queue and go to sleep. + */ + + queue.sma = sma; + queue.sops = sops; + queue.nsops = nsops; + queue.undo = un; + queue.pid = current->pid; + queue.alter = decrease; + current->semsleeping = &queue; + if (alter) + append_to_queue(sma ,&queue); + else + prepend_to_queue(sma ,&queue); + + for (;;) { + queue.status = -EINTR; + queue.sleeper = NULL; + interruptible_sleep_on(&queue.sleeper); + + /* + * If queue.status == 1 we where woken up and + * have to retry else we simply return. + * If an interrupt occured we have to clean up the + * queue + * + */ + if (queue.status == 1) + { + error = try_atomic_semop (sma, sops, nsops, un, + current->pid,0); + if (error <= 0) + break; + } else { + error = queue.status;; + if (queue.prev) /* got Interrupt */ + break; + /* Everything done by update_queue */ + current->semsleeping = NULL; + goto out; + } + } + current->semsleeping = NULL; + remove_from_queue(sma,&queue); +update: + if (alter) + update_queue (sma); out: unlock_kernel(); return error; diff --git a/kernel/ksyms.c b/kernel/ksyms.c index 9e3dedb90ba7..2c1b2312a91d 100644 --- a/kernel/ksyms.c +++ b/kernel/ksyms.c @@ -109,7 +109,6 @@ EXPORT_SYMBOL(vmtruncate); EXPORT_SYMBOL(update_atime); EXPORT_SYMBOL(get_super); EXPORT_SYMBOL(getname); -EXPORT_SYMBOL(putname); EXPORT_SYMBOL(__fput); EXPORT_SYMBOL(iget); EXPORT_SYMBOL(iput); @@ -129,7 +128,7 @@ EXPORT_SYMBOL(d_path); EXPORT_SYMBOL(__mark_inode_dirty); EXPORT_SYMBOL(get_empty_filp); EXPORT_SYMBOL(init_private_file); -EXPORT_SYMBOL(insert_file_free); +EXPORT_SYMBOL(fput); EXPORT_SYMBOL(check_disk_change); EXPORT_SYMBOL(invalidate_buffers); EXPORT_SYMBOL(invalidate_inodes); @@ -161,7 +160,6 @@ EXPORT_SYMBOL(posix_lock_file); EXPORT_SYMBOL(posix_test_lock); EXPORT_SYMBOL(posix_block_lock); EXPORT_SYMBOL(posix_unblock_lock); -EXPORT_SYMBOL(locks_remove_flock); EXPORT_SYMBOL(dput); EXPORT_SYMBOL(get_cached_page); EXPORT_SYMBOL(put_cached_page); diff --git a/kernel/module.c b/kernel/module.c index 59884d8e2a62..c5591db7f777 100644 --- a/kernel/module.c +++ b/kernel/module.c @@ -5,6 +5,7 @@ #include #include #include +#include /* * Originally by Anonymous (as far as I know...) @@ -30,7 +31,7 @@ static struct module kernel_module = NULL, /* next */ "", /* name */ 0, /* size */ - 1, /* usecount */ + {ATOMIC_INIT(1)}, /* usecount */ MOD_RUNNING, /* flags */ 0, /* nsyms -- to filled in in init_modules */ 0, /* ndeps */ @@ -56,7 +57,7 @@ static void free_module(struct module *, int tag_freed); * Called at boot time */ -void init_modules(void) +__initfunc(void init_modules(void)) { kernel_module.nsyms = __stop___ksymtab - __start___ksymtab; @@ -328,13 +329,13 @@ sys_init_module(const char *name_user, struct module *mod_user) put_mod_name(name); /* Initialize the module. */ - mod->usecount = 1; + atomic_set(&mod->uc.usecount,1); if (mod->init && mod->init() != 0) { - mod->usecount = 0; + atomic_set(&mod->uc.usecount,0); error = -EBUSY; goto err0; } - mod->usecount--; + atomic_dec(&mod->uc.usecount); /* And set it running. */ mod->flags |= MOD_RUNNING; @@ -614,7 +615,7 @@ qm_info(struct module *mod, char *buf, size_t bufsize, size_t *ret) info.size = mod->size; info.flags = mod->flags; info.usecount = (mod_member_present(mod, can_unload) - && mod->can_unload ? -1 : mod->usecount); + && mod->can_unload ? -1 : atomic_read(&mod->uc.usecount)); if (copy_to_user(buf, &info, sizeof(struct module_info))) return -EFAULT; @@ -853,7 +854,7 @@ int get_module_list(char *p) len = sprintf(tmpstr, "%4ld", (mod_member_present(mod, can_unload) && mod->can_unload - ? -1 : mod->usecount)); + ? -1L : (long)atomic_read(&mod->uc.usecount))); safe_copy_str(tmpstr, len); } diff --git a/kernel/sched.c b/kernel/sched.c index c8c297180888..bd3746995d33 100644 --- a/kernel/sched.c +++ b/kernel/sched.c @@ -7,6 +7,11 @@ * 1996-12-23 Modified by Dave Grothe to fix bugs in semaphores and * make semaphores SMP safe * 1997-01-28 Modified by Finn Arne Gangstad to make timers scale better. + * 1998-11-19 Implemented schedule_timeout() and related stuff + * by Andrea Arcangeli + * 1998-12-24 Fixed a xtime SMP race (we need the xtime_lock rw spinlock to + * serialize accesses to xtime/lost_ticks). + * Copyright (C) 1998 Andrea Arcangeli */ /* @@ -149,6 +154,7 @@ static inline void add_to_runqueue(struct task_struct * p) init_task.next_run = p; p->next_run = next; next->prev_run = p; + nr_running++; } static inline void del_from_runqueue(struct task_struct * p) @@ -227,7 +233,6 @@ void wake_up_process(struct task_struct * p) if (!p->next_run) { add_to_runqueue(p); reschedule_idle(p); - nr_running++; } spin_unlock_irqrestore(&runqueue_lock, flags); } @@ -437,23 +442,6 @@ signed long schedule_timeout(signed long timeout) struct timer_list timer; unsigned long expire; - /* - * PARANOID. - */ - if (current->state == TASK_UNINTERRUPTIBLE) - { - printk(KERN_WARNING "schedule_timeout: task not interrutible " - "from %p\n", __builtin_return_address(0)); - /* - * We don' t want to interrupt a not interruptible task - * risking to cause corruption. Better a a deadlock ;-). - */ - timeout = MAX_SCHEDULE_TIMEOUT; - } - - /* - * Here we start for real. - */ switch (timeout) { case MAX_SCHEDULE_TIMEOUT: @@ -594,10 +582,12 @@ asmlinkage void schedule(void) #ifdef __SMP__ next->has_cpu = 1; - next->processor = this_cpu; #endif if (prev != next) { +#ifdef __SMP__ + next->processor = this_cpu; +#endif kstat.context_swtch++; get_mmu_context(next); switch_to(prev,next); @@ -1189,13 +1179,21 @@ static void update_process_times(unsigned long ticks, unsigned long system) volatile unsigned long lost_ticks = 0; static unsigned long lost_ticks_system = 0; +/* + * This spinlock protect us from races in SMP while playing with xtime. -arca + */ +rwlock_t xtime_lock = RW_LOCK_UNLOCKED; + static inline void update_times(void) { unsigned long ticks; - unsigned long flags; - save_flags(flags); - cli(); + /* + * update_times() is run from the raw timer_bh handler so we + * just know that the irqs are locally enabled and so we don't + * need to save/restore the flags of the local CPU here. -arca + */ + write_lock_irq(&xtime_lock); ticks = lost_ticks; lost_ticks = 0; @@ -1206,12 +1204,12 @@ static inline void update_times(void) calc_load(ticks); update_wall_time(ticks); - restore_flags(flags); + write_unlock_irq(&xtime_lock); update_process_times(ticks, system); } else - restore_flags(flags); + write_unlock_irq(&xtime_lock); } static void timer_bh(void) diff --git a/mm/page_io.c b/mm/page_io.c index f23fd80891b9..7564d2ee1174 100644 --- a/mm/page_io.c +++ b/mm/page_io.c @@ -7,6 +7,7 @@ * Asynchronous swapping added 30.12.95. Stephen Tweedie * Removed race in async swapping. 14.4.1996. Bruno Haible * Add swap of shared pages through the page cache. 20.2.1998. Stephen Tweedie + * Always use brw_page, life becomes simpler. 12 May 1998 Eric Biederman */ #include @@ -15,8 +16,6 @@ #include #include -#include -#include /* for copy_to/from_user */ #include static struct wait_queue * lock_queue = NULL; @@ -24,8 +23,6 @@ static struct wait_queue * lock_queue = NULL; /* * Reads or writes a swap page. * wait=1: start I/O and wait for completion. wait=0: start asynchronous I/O. - * All IO to swap files (as opposed to swap partitions) is done - * synchronously. * * Important prevention of race condition: the caller *must* atomically * create a unique swap cache entry for this swap page before calling @@ -38,21 +35,22 @@ static struct wait_queue * lock_queue = NULL; * that shared pages stay shared while being swapped. */ -void rw_swap_page(int rw, unsigned long entry, char * buf, int wait) +static void rw_swap_page_base(int rw, unsigned long entry, struct page *page, int wait) { unsigned long type, offset; struct swap_info_struct * p; - struct page *page = mem_map + MAP_NR(buf); + int zones[PAGE_SIZE/512]; + int zones_used; + kdev_t dev; + int block_size; #ifdef DEBUG_SWAP printk ("DebugVM: %s_swap_page entry %08lx, page %p (count %d), %s\n", (rw == READ) ? "read" : "write", - entry, buf, atomic_read(&page->count), + entry, (char *) page_address(page), atomic_read(&page->count), wait ? "wait" : "nowait"); #endif - if (page->inode && page->inode != &swapper_inode) - panic ("Tried to swap a non-swapper page"); type = SWP_TYPE(entry); if (type >= nr_swapfiles) { printk("Internal error: bad swap-device\n"); @@ -85,13 +83,27 @@ void rw_swap_page(int rw, unsigned long entry, char * buf, int wait) printk(KERN_ERR "VM: swap page is unlocked\n"); return; } - - /* Make sure we are the only process doing I/O with this swap page. */ - while (test_and_set_bit(offset,p->swap_lockmap)) { - run_task_queue(&tq_disk); - sleep_on(&lock_queue); + + if (PageSwapCache(page)) { + /* Make sure we are the only process doing I/O with this swap page. */ + while (test_and_set_bit(offset,p->swap_lockmap)) { + run_task_queue(&tq_disk); + sleep_on(&lock_queue); + } + + /* + * Make sure that we have a swap cache association for this + * page. We need this to find which swap page to unlock once + * the swap IO has completed to the physical page. If the page + * is not already in the cache, just overload the offset entry + * as if it were: we are not allowed to manipulate the inode + * hashing for locked pages. + */ + if (page->offset != entry) { + printk ("swap entry mismatch"); + return; + } } - if (rw == READ) { clear_bit(PG_uptodate, &page->flags); kstat.pswpin++; @@ -99,54 +111,25 @@ void rw_swap_page(int rw, unsigned long entry, char * buf, int wait) kstat.pswpout++; atomic_inc(&page->count); - /* - * Make sure that we have a swap cache association for this - * page. We need this to find which swap page to unlock once - * the swap IO has completed to the physical page. If the page - * is not already in the cache, just overload the offset entry - * as if it were: we are not allowed to manipulate the inode - * hashing for locked pages. - */ - if (!PageSwapCache(page)) { - printk(KERN_ERR "VM: swap page is not in swap cache\n"); - return; - } - if (page->offset != entry) { - printk (KERN_ERR "VM: swap entry mismatch\n"); - return; - } - if (p->swap_device) { - if (!wait) { - set_bit(PG_free_after, &page->flags); - set_bit(PG_decr_after, &page->flags); - set_bit(PG_swap_unlock_after, &page->flags); - atomic_inc(&nr_async_pages); - } - ll_rw_page(rw,p->swap_device,offset,buf); - /* - * NOTE! We don't decrement the page count if we - * don't wait - that will happen asynchronously - * when the IO completes. - */ - if (!wait) - return; - wait_on_page(page); + zones[0] = offset; + zones_used = 1; + dev = p->swap_device; + block_size = PAGE_SIZE; } else if (p->swap_file) { struct inode *swapf = p->swap_file->d_inode; - unsigned int zones[PAGE_SIZE/512]; int i; if (swapf->i_op->bmap == NULL && swapf->i_op->smap != NULL){ /* - With MS-DOS, we use msdos_smap which return + With MS-DOS, we use msdos_smap which returns a sector number (not a cluster or block number). It is a patch to enable the UMSDOS project. Other people are working on better solution. It sounds like ll_rw_swap_file defined - it operation size (sector size) based on - PAGE_SIZE and the number of block to read. + its operation size (sector size) based on + PAGE_SIZE and the number of blocks to read. So using bmap or smap should work even if smap will require more blocks. */ @@ -159,39 +142,72 @@ void rw_swap_page(int rw, unsigned long entry, char * buf, int wait) return; } } + block_size = 512; }else{ int j; unsigned int block = offset << (PAGE_SHIFT - swapf->i_sb->s_blocksize_bits); - for (i=0, j=0; j< PAGE_SIZE ; i++, j +=swapf->i_sb->s_blocksize) + block_size = swapf->i_sb->s_blocksize; + for (i=0, j=0; j< PAGE_SIZE ; i++, j += block_size) if (!(zones[i] = bmap(swapf,block++))) { printk("rw_swap_page: bad swap file\n"); return; } + zones_used = i; + dev = swapf->i_dev; } - ll_rw_swap_file(rw,swapf->i_dev, zones, i,buf); - /* Unlike ll_rw_page, ll_rw_swap_file won't unlock the - page for us. */ - clear_bit(PG_locked, &page->flags); - wake_up(&page->wait); - } else + } else { printk(KERN_ERR "rw_swap_page: no swap file or device\n"); + /* Do some cleaning up so if this ever happens we can hopefully + * trigger controlled shutdown. + */ + if (PageSwapCache(page)) { + if (!test_and_clear_bit(offset,p->swap_lockmap)) + printk("swap_after_unlock_page: lock already cleared\n"); + wake_up(&lock_queue); + } + atomic_dec(&page->count); + return; + } + if (!wait) { + set_bit(PG_decr_after, &page->flags); + atomic_inc(&nr_async_pages); + } + if (PageSwapCache(page)) { + /* only lock/unlock swap cache pages! */ + set_bit(PG_swap_unlock_after, &page->flags); + } + set_bit(PG_free_after, &page->flags); + /* block_size == PAGE_SIZE/zones_used */ + brw_page(rw, page, dev, zones, block_size, 0); + + /* Note! For consistency we do all of the logic, + * decrementing the page count, and unlocking the page in the + * swap lock map - in the IO completion handler. + */ + if (!wait) + return; + wait_on_page(page); /* This shouldn't happen, but check to be sure. */ - if (atomic_read(&page->count) == 1) + if (atomic_read(&page->count) == 0) printk(KERN_ERR "rw_swap_page: page unused while waiting!\n"); - atomic_dec(&page->count); - if (offset && !test_and_clear_bit(offset,p->swap_lockmap)) - printk(KERN_ERR "rw_swap_page: lock already cleared\n"); - wake_up(&lock_queue); + #ifdef DEBUG_SWAP printk ("DebugVM: %s_swap_page finished on page %p (count %d)\n", (rw == READ) ? "read" : "write", - buf, atomic_read(&page->count)); + (char *) page_adddress(page), + atomic_read(&page->count)); #endif } +/* Note: We could remove this totally asynchronous function, + * and improve swap performance, and remove the need for the swap lock map, + * by not removing pages from the swap cache until after I/O has been + * processed and letting remove_from_page_cache decrement the swap count + * just before it removes the page from the page cache. + */ /* This is run when asynchronous page I/O has completed. */ void swap_after_unlock_page (unsigned long entry) { @@ -214,6 +230,35 @@ void swap_after_unlock_page (unsigned long entry) wake_up(&lock_queue); } +/* A simple wrapper so the base function doesn't need to enforce + * that all swap pages go through the swap cache! + */ +void rw_swap_page(int rw, unsigned long entry, char *buf, int wait) +{ + struct page *page = mem_map + MAP_NR(buf); + + if (page->inode && page->inode != &swapper_inode) + panic ("Tried to swap a non-swapper page"); + + /* + * Make sure that we have a swap cache association for this + * page. We need this to find which swap page to unlock once + * the swap IO has completed to the physical page. If the page + * is not already in the cache, just overload the offset entry + * as if it were: we are not allowed to manipulate the inode + * hashing for locked pages. + */ + if (!PageSwapCache(page)) { + printk("VM: swap page is not in swap cache\n"); + return; + } + if (page->offset != entry) { + printk ("swap entry mismatch"); + return; + } + rw_swap_page_base(rw, entry, page, wait); +} + /* * Setting up a new swap file needs a simple wrapper just to read the * swap signature. SysV shared memory also needs a simple wrapper. @@ -242,33 +287,23 @@ void rw_swap_page_nocache(int rw, unsigned long entry, char *buffer) clear_bit(PG_swap_cache, &page->flags); } - - /* - * Swap partitions are now read via brw_page. ll_rw_page is an - * asynchronous function now --- we must call wait_on_page afterwards - * if synchronous IO is required. + * shmfs needs a version that doesn't put the page in the page cache! + * The swap lock map insists that pages be in the page cache! + * Therefore we can't use it. Later when we can remove the need for the + * lock map and we can reduce the number of functions exported. */ -void ll_rw_page(int rw, kdev_t dev, unsigned long offset, char * buffer) +void rw_swap_page_nolock(int rw, unsigned long entry, char *buffer, int wait) { - int block = offset; - struct page *page; - - switch (rw) { - case READ: - break; - case WRITE: - if (is_read_only(dev)) { - printk("Can't page to read-only device %s\n", - kdevname(dev)); - return; - } - break; - default: - panic("ll_rw_page: bad block dev cmd, must be R/W"); + struct page *page = mem_map + MAP_NR((unsigned long) buffer); + + if (!PageLocked(page)) { + printk("VM: rw_swap_page_nolock: page not locked!\n"); + return; + } + if (PageSwapCache(page)) { + printk ("VM: rw_swap_page_nolock: page in swap cache!\n"); + return; } - page = mem_map + MAP_NR(buffer); - if (!PageLocked(page)) - panic ("ll_rw_page: page not already locked"); - brw_page(rw, page, dev, &block, PAGE_SIZE, 0); + rw_swap_page_base(rw, entry, page, wait); } diff --git a/net/appletalk/aarp.c b/net/appletalk/aarp.c index 74540951f4b3..6d59b2338407 100644 --- a/net/appletalk/aarp.c +++ b/net/appletalk/aarp.c @@ -294,7 +294,7 @@ static void aarp_expire_timer(struct aarp_entry **n) while((*n)!=NULL) { /* Expired ? */ - if((*n)->expires_at < jiffies) + if(time_after(jiffies, (*n)->expires_at)) { t= *n; *n=(*n)->next; diff --git a/net/appletalk/ddp.c b/net/appletalk/ddp.c index c47f83263492..ebb381b52251 100644 --- a/net/appletalk/ddp.c +++ b/net/appletalk/ddp.c @@ -31,12 +31,19 @@ * AppleTalk drivers, cleaned it. * Rob Newberry : Added proxy AARP and AARP proc fs, * moved probing to AARP module. + * Adrian Sun/ + * Michael Zuelsdorff : fix for net.0 packets. don't + * allow illegal ether/tokentalk + * port assignment. we lose a + * valid localtalk port as a + * result. + * * * This program is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License * as published by the Free Software Foundation; either version * 2 of the License, or (at your option) any later version. - * + * */ #include @@ -141,7 +148,7 @@ static struct sock *atalk_search_socket(struct sockaddr_at *to, struct atalk_ifa continue; } - if(to->sat_addr.s_net == 0 + if(to->sat_addr.s_net == ATADDR_ANYNET && to->sat_addr.s_node == ATADDR_BCAST && s->protinfo.af_at.src_net == atif->address.s_net) { @@ -156,7 +163,14 @@ static struct sock *atalk_search_socket(struct sockaddr_at *to, struct atalk_ifa break; } - /* XXXX.0 */ + /* XXXX.0 -- we got a request for this router. make sure + * that the node is appropriately set. */ + if (to->sat_addr.s_node == ATADDR_ANYNODE && + to->sat_addr.s_net != ATADDR_ANYNET && + atif->address.s_node == s->protinfo.af_at.src_node) { + to->sat_addr.s_node = atif->address.s_node; + break; + } } return (s); @@ -502,6 +516,12 @@ static struct atalk_iface *atalk_find_interface(int net, int node) && iface->address.s_net==net && !(iface->status & ATIF_PROBE)) return (iface); + + /* XXXX.0 -- net.0 returns the iface associated with net */ + if ((node==ATADDR_ANYNODE) && (net != ATADDR_ANYNET) && + (ntohs(iface->nets.nr_firstnet) <= ntohs(net)) && + (ntohs(net) <= ntohs(iface->nets.nr_lastnet))) + return (iface); } return (NULL); diff --git a/net/bridge/br.c b/net/bridge/br.c index b648ec4a8624..e86b8a54dac3 100644 --- a/net/bridge/br.c +++ b/net/bridge/br.c @@ -1539,7 +1539,7 @@ static inline int mcast_quench(struct fdb *f) f->mcast_timer = jiffies; else { if(f->mcast_count > max_mcast_per_period) { - if(jiffies > (f->mcast_timer + mcast_hold_time)) + if(time_after(jiffies, f->mcast_timer + mcast_hold_time)) f->mcast_count = 0; else return 1; } diff --git a/net/ipv6/af_inet6.c b/net/ipv6/af_inet6.c index b40c35d00c3d..1ced6e3c04ed 100644 --- a/net/ipv6/af_inet6.c +++ b/net/ipv6/af_inet6.c @@ -477,7 +477,7 @@ int ipv6_unload(void) { if (!unloadable) return 1; /* We keep internally 3 raw sockets */ - return __this_module.usecount - 3; + return atomic_read(&(__this_module.uc.usecount)) - 3; } #endif diff --git a/net/ipx/af_ipx.c b/net/ipx/af_ipx.c index 5990b69a3cc4..443daba5aaf9 100644 --- a/net/ipx/af_ipx.c +++ b/net/ipx/af_ipx.c @@ -50,6 +50,9 @@ * Revision 0.39: SPX interfaces * Revision 0.40: Tiny SIOCGSTAMP fix (chris@cybernet.co.nz) * Revision 0.41: 802.2TR removed (p.norton@computer.org) + * Fixed connecting to primary net, + * Automatic binding on send & receive, + * Martijn van Oosterhout * * Protect the module by a MOD_INC_USE_COUNT/MOD_DEC_USE_COUNT * pair. Also, now usage count is managed this way @@ -450,7 +453,57 @@ static int ipxitf_demux_socket(ipx_interface *intrfc, struct sk_buff *skb, int c struct sock *sock1 = NULL, *sock2 = NULL; struct sk_buff *skb1 = NULL, *skb2 = NULL; - sock1 = ipxitf_find_socket(intrfc, ipx->ipx_dest.sock); + if (intrfc == ipx_primary_net && ntohs(ipx->ipx_dest.sock) == 0x451) + { + /* + * The packet's target is a NCP connection handler. We want to + * hand it to the correct socket directly within the kernel, + * so that the mars_nwe packet distribution process + * does not have to do it. Here we only care about NCP and + * BURST packets. + * You might call this a hack, but believe me, you do not + * want a complete NCP layer in the kernel, and this is + * VERY fast as well. + */ + int connection = 0; + + if (*((char*)(ipx+1)) == 0x22 && *((char*)(ipx+1)+1) == 0x22) + { + /* + * The packet is a NCP request + */ + connection = ( ((int) *((char*)(ipx+1)+5)) << 8 ) + | (int) *((char*)(ipx+1)+3); + } + else if (*((char*)(ipx+1))== 0x77 && *((char*)(ipx+1)+1) == 0x77) + { + /* + * The packet is a BURST packet + */ + connection = ( ((int) *((char*)(ipx+1)+9)) << 8 ) + | (int) *((char*)(ipx+1)+8); + } + + if (connection) + { + /* + * Now we have to look for a special NCP connection handling + * socket. Only these sockets have ipx_ncp_conn != 0, set + * by SIOCIPXNCPCONN. + */ + for (sock1=intrfc->if_sklist; + (sock1 != NULL) && + (sock1->protinfo.af_ipx.ipx_ncp_conn != connection); + sock1=sock1->next); + } + } + if (sock1 == NULL) + { + /* No special socket found, forward the packet the + * normal way. + */ + sock1 = ipxitf_find_socket(intrfc, ipx->ipx_dest.sock); + } /* * We need to check if there is a primary net and if @@ -1822,7 +1875,7 @@ static int ipx_bind(struct socket *sock, struct sockaddr *uaddr, int addr_len) } /* protect IPX system stuff like routing/sap */ - if(ntohs(addr->sipx_port) < IPX_MIN_EPHEMERAL_SOCKET && !suser()) + if(ntohs(addr->sipx_port) < IPX_MIN_EPHEMERAL_SOCKET && !capable(CAP_NET_ADMIN)) return (-EACCES); sk->protinfo.af_ipx.port = addr->sipx_port; @@ -1930,7 +1983,8 @@ static int ipx_connect(struct socket *sock, struct sockaddr *uaddr, return (ret); } - if(ipxrtr_lookup(addr->sipx_network) == NULL) + /* We can either connect to primary network or somewhere we can route to */ + if( !(addr->sipx_network == 0 && ipx_primary_net != NULL) && ipxrtr_lookup(addr->sipx_network) == NULL) return (-ENETUNREACH); sk->protinfo.af_ipx.dest_addr.net = addr->sipx_network; @@ -2061,8 +2115,9 @@ static int ipx_sendmsg(struct socket *sock, struct msghdr *msg, int len, int retval; int flags = msg->msg_flags; - if(sk->zapped) - return (-EIO); /* Socket not bound */ + /* Socket gets bound below anyway */ +/* if(sk->zapped) + return (-EIO); */ /* Socket not bound */ if(flags & ~MSG_DONTWAIT) return (-EINVAL); @@ -2120,6 +2175,26 @@ static int ipx_recvmsg(struct socket *sock, struct msghdr *msg, int size, struct sk_buff *skb; int copied, err; + /* put the autobinding in */ + if(sk->protinfo.af_ipx.port == 0) + { + struct sockaddr_ipx uaddr; + int ret; + + uaddr.sipx_port = 0; + uaddr.sipx_network = 0; + +#ifdef CONFIG_IPX_INTERN + memcpy(uaddr.sipx_node, sk->protinfo.af_ipx.intrfc->if_node, + IPX_NODE_LEN); +#endif /* CONFIG_IPX_INTERN */ + + ret = ipx_bind(sock, (struct sockaddr *)&uaddr, + sizeof(struct sockaddr_ipx)); + if(ret != 0) + return (ret); + } + if(sk->zapped) return (-ENOTCONN); @@ -2191,14 +2266,14 @@ static int ipx_ioctl(struct socket *sock,unsigned int cmd, unsigned long arg) case SIOCADDRT: case SIOCDELRT: - if(!suser()) + if(!capable(CAP_NET_ADMIN)) return (-EPERM); return (ipxrtr_ioctl(cmd,(void *)arg)); case SIOCSIFADDR: case SIOCAIPXITFCRT: case SIOCAIPXPRISLT: - if(!suser()) + if(!capable(CAP_NET_ADMIN)) return (-EPERM); case SIOCGIFADDR: @@ -2207,6 +2282,18 @@ static int ipx_ioctl(struct socket *sock,unsigned int cmd, unsigned long arg) case SIOCIPXCFGDATA: return (ipxcfg_get_config_data((void *)arg)); + case SIOCIPXNCPCONN: + { + int err; + /* + * This socket wants to take care of the NCP connection + * handed to us in arg. + */ + if (!capable(CAP_NET_ADMIN)) + return(-EPERM); + return get_user(sk->protinfo.af_ipx.ipx_ncp_conn, (const unsigned short *)(arg)); + } + case SIOCGSTAMP: { int ret = -EINVAL; diff --git a/net/sched/sch_api.c b/net/sched/sch_api.c index f2fb9e36f944..0e314653ea17 100644 --- a/net/sched/sch_api.c +++ b/net/sched/sch_api.c @@ -898,7 +898,7 @@ __initfunc(int psched_calibrate_clock(void)) stop = jiffies + HZ/10; PSCHED_GET_TIME(stamp); do_gettimeofday(&tv); - while (jiffies < stop) + while (time_before(jiffies, stop)) barrier(); PSCHED_GET_TIME(stamp1); do_gettimeofday(&tv1); diff --git a/net/sunrpc/auth.c b/net/sunrpc/auth.c index 2ac1f7b7f2b8..0a907a8f199a 100644 --- a/net/sunrpc/auth.c +++ b/net/sunrpc/auth.c @@ -117,7 +117,7 @@ rpcauth_gc_credcache(struct rpc_auth *auth) printk("RPC: rpcauth_gc_credcache looping!\n"); break; } - if (!cred->cr_count && cred->cr_expire < jiffies) { + if (!cred->cr_count && time_after(jiffies, cred->cr_expire)) { *q = cred->cr_next; cred->cr_next = free; free = cred; @@ -160,7 +160,7 @@ rpcauth_lookup_credcache(struct rpc_task *task) nr = RPC_DO_ROOTOVERRIDE(task)? 0 : (current->uid % RPC_CREDCACHE_NR); - if (auth->au_nextgc < jiffies) + if (time_after(jiffies, auth->au_nextgc)) rpcauth_gc_credcache(auth); q = &auth->au_credcache[nr]; diff --git a/net/sunrpc/xprt.c b/net/sunrpc/xprt.c index 851f4d9523a9..827a8d42ee38 100644 --- a/net/sunrpc/xprt.c +++ b/net/sunrpc/xprt.c @@ -293,7 +293,7 @@ xprt_adjust_cwnd(struct rpc_xprt *xprt, int result) if (xprt->nocong) return; if (result >= 0) { - if (xprt->cong < cwnd || jiffies < xprt->congtime) + if (xprt->cong < cwnd || time_before(jiffies, xprt->congtime)) return; /* The (cwnd >> 1) term makes sure * the result gets rounded properly. */ @@ -543,7 +543,7 @@ xprt_complete_rqst(struct rpc_xprt *xprt, struct rpc_rqst *req, int copied) pkt_cnt++; pkt_len += req->rq_slen + copied; pkt_rtt += jiffies - req->rq_xtime; - if (nextstat < jiffies) { + if (time_after(jiffies, nextstat)) { printk("RPC: %lu %ld cwnd\n", jiffies, xprt->cwnd); printk("RPC: %ld %ld %ld %ld stat\n", jiffies, pkt_cnt, pkt_len, pkt_rtt); diff --git a/scripts/Menuconfig b/scripts/Menuconfig index d8ca35755eb0..47515f69c735 100644 --- a/scripts/Menuconfig +++ b/scripts/Menuconfig @@ -47,6 +47,16 @@ # # 090398 Axel Boldt (boldt@math.ucsb.edu) - allow for empty lines in help # texts. +# +# 12 Dec 1998, Michael Elizabeth Chastain (mec@shout.net) +# Remove a /tmp security hole in get_def (also makes it faster). +# Give uninitialized variables canonical values rather than null value. +# Change a lot of places to call set_x_info uniformly. +# Take out message about preparing version (old sound driver cruft). +# +# 13 Dec 1998, Riley H Williams (rhw@bigfoot.com) +# When an error occurs, actually display the error message as well as +# our comments thereon. # @@ -65,20 +75,24 @@ single_menu_mode= # set -h +o posix -# -# Converts "# xxx is not..." to xxx=n -# -parse_config () { - sed -e 's/# \(.*\) is not.*/\1=n/' -} + +# Given a configuration variable, set the global variable $x to its value, +# and the global variable $info to the string " (NEW)" if this is a new +# variable. # -# Parses the defconfig file to set the default for a new parameter. -# -function get_def () { - parse_config < arch/$ARCH/defconfig | grep "^$1=" > /tmp/conf.$$ - . /tmp/conf.$$ - rm /tmp/conf.$$ +# This function looks for: (1) the current value, or (2) the default value +# from the arch-dependent defconfig file, or (3) a default passed by the caller. + +function set_x_info () { + eval x=\$$1 + if [ -z "$x" ]; then + eval `sed -n -e 's/# \(.*\) is not set.*/\1=n/' -e "/^$1=/p" arch/$ARCH/defconfig` + eval x=\${$1:-"$2"} + eval $1=$x + eval INFO_$1="' (NEW)'" + fi + eval info="\$INFO_$1" } # @@ -92,19 +106,6 @@ function get_def () { # load_functions () { -# -# Macro for setting the x and info varibles. get's default from defconfig -# file if it's a new parameter. -# -function set_x () { - eval x=\$$1 - if [ -z "$x" ]; then - get_def "$1" - eval x=\${$1:-'n'} INFO_$1="' (NEW)'" - fi - eval info="\$INFO_$1" -} - # # Additional comments # @@ -125,7 +126,7 @@ function define_bool () { # which calls our local bool function. # function bool () { - set_x "$2" + set_x_info "$2" "n" case $x in y|m) flag="*" ;; @@ -148,7 +149,7 @@ function tristate () { then bool "$1" "$2" else - set_x "$2" + set_x_info "$2" "n" case $x in y) flag="*" ;; @@ -193,9 +194,9 @@ function dep_tristate () { # Add a menu item which will call our local int function. # function int () { - eval $2=\${$2:-"$3"} x=\$$2 + set_x_info "$2" "$3" - echo -ne "'$2' '($x) $1' " >>MCmenu + echo -ne "'$2' '($x) $1$info' " >>MCmenu echo -e "function $2 () { l_int '$1' '$2' '$3' '$x' ;}" >>MCradiolists } @@ -204,9 +205,10 @@ function int () { # Add a menu item which will call our local hex function. # function hex () { - eval $2=\${$2:-"$3"} x=\${$2##*[x,X]} + set_x_info "$2" "$3" + x=${x##*[x,X]} - echo -ne "'$2' '($x) $1' " >>MCmenu + echo -ne "'$2' '($x) $1$info' " >>MCmenu echo -e "function $2 () { l_hex '$1' '$2' '$3' '$x' ;}" >>MCradiolists } @@ -215,9 +217,9 @@ function hex () { # Add a menu item which will call our local string function. # function string () { - eval $2=\${$2:-"$3"} x=\$$2 + set_x_info "$2" "$3" - echo -ne "'$2' ' $1: \"$x\"' " >>MCmenu + echo -ne "'$2' ' $1: \"$x\"$info' " >>MCmenu echo -e "function $2 () { l_string '$1' '$2' '$3' '$x' ;}" >>MCradiolists } @@ -370,7 +372,7 @@ function l_bool () { # Same as bool() except options are (Module/No) # function mod_bool () { - set_x "$2" + set_x_info "$2" "n" case $x in y|m) flag='M' ;; @@ -722,14 +724,20 @@ function activate_menu () { do comment_ctr=0 #So comment lines get unique tags - $1 "$default" #Create the lxdialog menu & functions + $1 "$default" 2> MCerror #Create the lxdialog menu & functions if [ "$?" != "0" ] then clear cat < /' MCerror + cat <. You may also send a problem report to . @@ -741,6 +749,7 @@ EOM cleanup exit 1 fi + rm -f MCerror . ./MCradiolists #Source the menu's functions @@ -778,6 +787,7 @@ EOM stty sane clear cat <>$CONFIG echo "#define $2 ($x)" >>$CONFIG_H } function hex () { - eval x=\${$2:-"$3"} + set_x_info "$2" "$3" echo "$2=$x" >>$CONFIG echo "#define $2 0x${x##*[x,X]}" >>$CONFIG_H } function string () { - eval x=\${$2:-"$3"} + set_x_info "$2" "$3" echo "$2=\"$x\"" >>$CONFIG echo "#define $2 \"$x\"" >>$CONFIG_H } @@ -1250,10 +1240,8 @@ fi # Fresh new log. >.menuconfig.log -echo -n "Preparing configuration scripts: version" - # Load the functions used by the config.in files. -echo -n ", functions" +echo -n "Preparing scripts: functions" load_functions if [ ! -e $CONFIG_IN ] -- 2.39.5