diff -u --recursive --new-file v2.3.19/linux/Documentation/Configure.help linux/Documentation/Configure.help --- v2.3.19/linux/Documentation/Configure.help Fri Sep 10 23:57:27 1999 +++ linux/Documentation/Configure.help Thu Oct 7 21:32:14 1999 @@ -5,29 +5,35 @@ # # Translations of this file available on the WWW: # -# - Japanese, by Tetsuyasu YAMADA (tetsu@cauchy.nslab.ntt.co.jp), at -# http://jf.gee.kyoto-u.ac.jp/JF/JF-ftp/euc/Configure.help.euc +# - Japanese, maintained by the JF Project (JF@linux.or.jp), at +# http://www.linux.or.jp/JF/JFdocs/Configure.help/ # - Russian, by kaf@linux.nevod.perm.su, at # http://nevod.perm.su/service/linux/doc/kernel/Configure.help -# - French, by David Bourgin (dbourgin@wsc.com), at -# http://www.linux-kheops.com/traduc/kernels/ +# - French, by Tane Pierre (tanep@bigfoot.com), at +# http://www.kernelfr.org # - Spanish, by Carlos Perelló Marín (fperllo@ehome.encis.es), at # http://visar.csustan.edu/~carlos/ # - Italian, by Alessandro Rubini (rubini@linux.it), at # ftp://ftp-pavia1.linux.it/pub/linux/Configure.help # - Polish, by Cezar Cichocki (cezar@cs.net.pl), at # http://www.cs.net.pl/~cezar/Kernel -# - German, by Jörg Strebel (jstrebel@suse.de) and Karl Eichwalder -# (ke@suse.de), at http://www.suse.de/~ke/kernel/Configure.de.help.gz +# - German, by SuSE, at http://www.suse.de/~ke/kernel . This patch +# includes infrastructure to support different languages as well. +# +# To access a document on the WWW, you need to have a direct Internet +# connection and a browser program such as netscape or lynx. If you +# only have email access, you can still use FTP and WWW servers: send +# an email to mail-server@rtfm.mit.edu with the text +# send usenet/news.answers/internet-services/access-via-email +# in the body of the message. # # 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 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 -# Documentation/Changes. Make sure to read the toplevel kernel README -# file as well. +# at http://metalab.unc.edu/mdw/linux.html#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 Documentation/Changes. Make sure to read the +# toplevel kernel README file as well. # # Format of this file: descriptionvariablehelp text. If # the question being documented is of type "choice", we list only the @@ -104,9 +110,7 @@ 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). + SMP-FAQ on the WWW at http://www.irisa.fr/prive/mentre/smp-faq/ . If you don't know what to do here, say N. @@ -126,39 +130,38 @@ is broken. Try "man bootparam" or see the documentation 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://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. + available from http://metalab.unc.edu/mdw/linux.html#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 the Linux math coprocessor emulation can be found in arch/i386/math-emu/README. If you are not sure, say Y; apart from resulting in a 45 KB bigger kernel, it won't hurt. - + Timer and CPU usage LEDs CONFIG_LEDS - If you define this option, the LEDs on your machine will be used + If you say Y here, the LEDs on your machine will be used to provide useful information about your current system status. - If you are compiling a kernel for a NetWinder or EBSA-285, you - will be able to select which LEDs are active using the options - below. If you are compiling a kernel for the EBSA-110 however, - the red LED will simply flash regularly to indicate that the - system is still functional. It is still safe to say yes here if - you have a CATS system, but the driver will do nothing. + If you are compiling a kernel for a NetWinder or EBSA-285, you will + be able to select which LEDs are active using the options below. If + you are compiling a kernel for the EBSA-110 however, the red LED + will simply flash regularly to indicate that the system is still + functional. It is safe to say Y here if you have a CATS system, but + the driver will do nothing. Timer LED CONFIG_LEDS_TIMER - If you say yes here, one of the system LEDs (the green one on the + If you say Y here, one of the system LEDs (the green one on the NetWinder or the amber one on the EBSA285) will flash regularly to indicate that the system is still operational. This is mainly useful to kernel hackers who are debugging unstable kernels. CPU usage LED CONFIG_LEDS_CPU - If you say yes here, the red LED will be used to give a good real + If you say Y here, the red LED will be used to give a good real time indication of CPU usage, by lighting whenever the idle task is not currently executing. @@ -170,8 +173,16 @@ Big memory support CONFIG_BIGMEM - This option is required if you want to utilize physical memory which - is not covered by the kernel virtual address space (> 1GB). + Linux can use up to 2 Gigabytes (= 2^31 bytes) of physical memory. + If you are compiling a kernel which will never run on a machine with + more than 1 Gigabyte, answer N here. Otherwise, say Y. + + The actual amount of physical memory should be specified using a + kernel command line option such as "mem=256M". (Try "man bootparam" + or see the documentation 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 from + http://metalab.unc.edu/mdw/linux.html#howto .) Normal PC floppy disk support CONFIG_BLK_DEV_FD @@ -238,16 +249,16 @@ on a remote file server. If you want to do this, you will first have to acquire and install a kernel patch from ftp://ftp.replay.com/pub/crypto/linux/all or - ftp://verden.pvv.org/pub/linux/kerneli/v2.1/, and then you need to + ftp://verden.pvv.org/pub/linux/kerneli/v2.1/ , and then you need to say Y to this option. Note that alternative ways to use encrypted filesystems are provided - by the cfs package, which can be gotten via FTP (user: anonymous) - from ftp://ftp.replay.com/pub/crypto/disk/, and the newer tcfs - package, available at http://tcfs.dia.unisa.it/. You do not need to - say Y here if you want to use one of these. However, using cfs - requires saying Y to "NFS filesystem support" below while using tcfs - requires applying a kernel patch. + by the cfs package, which can be gotten from + ftp://ftp.replay.com/pub/crypto/disk/ , and the newer tcfs package, + available at http://tcfs.dia.unisa.it/ . You do not need to say Y + here if you want to use one of these. However, using cfs requires + saying Y to "NFS filesystem support" below while using tcfs requires + applying a kernel patch. To use the loop device, you need the losetup utility and a recent version of the mount program, both contained in the util-linux @@ -295,8 +306,8 @@ CONFIG_BLK_DEV_IDE If you say Y here, you will use the full-featured IDE driver to control up to eight IDE interfaces, each being able to serve a - "master" and a "slave" device, for a total of up to sixteen (16) - IDE disk/cdrom/tape/floppy drives. People with SCSI-only systems + "master" and a "slave" device, for a total of up to sixteen IDE + disk/cdrom/tape/floppy drives. People with SCSI-only systems can say N here. Useful information about large (>540 MB) IDE disks, multiple @@ -304,12 +315,11 @@ detected, sound card IDE ports, module support, and other topics, is 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + available from http://metalab.unc.edu/mdw/linux.html#howto . To fine-tune IDE drive/interface parameters for improved performance, look for the hdparm package at - ftp://metalab.unc.edu/pub/Linux/kernel/patches/diskdrives/ + ftp://metalab.unc.edu/pub/Linux/kernel/patches/diskdrives/ . 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), @@ -337,8 +347,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + Disk-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . People with SCSI-only systems can say N here. @@ -377,7 +387,7 @@ Use multi-mode by default CONFIG_IDEDISK_MULTI_MODE - If you get this error, try to enable this option. + If you get this error, try to say Y here: hda: set_multmode: status=0x51 { DriveReady SeekComplete Error } hda: set_multmode: error=0x04 { DriveStatusError } @@ -398,12 +408,12 @@ CDROM drive, you can say N to all other CDROM options, but be sure to say Y or M to "ISO 9660 CDROM filesystem support". - Read the CDROM-HOWTO, available via FTP (user: anonymous) in - ftp://metalab.unc.edu/pub/Linux/docs/HOWTO and the file + Read the CDROM-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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://metalab.unc.edu/pub/Linux/system/Linux-boot/lilo. + ftp://metalab.unc.edu/pub/Linux/system/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), @@ -413,11 +423,11 @@ Include CD-Changer Reporting CONFIG_IDECD_SLOTS If you have an IDE/ATAPI multi-slot cd-changer and you want - to report which slots have disk-present, say Y. If you say Y - and there is not a multi-slot cdrom present, this code is skipped. + to report which slots have a disk present, say Y. If you say Y + and there is no multi-slot cdrom present, this code is skipped. - This could be the bases of multi-disk access based on multi-mounts. - This is still pie-in-the-sky. + This code could be the basis of multi-disk access based on + multi-mounts, but this is still pie-in-the-sky. If unsure, say N. @@ -497,8 +507,8 @@ to enable the CMD640 bugfix/support: "ide0=cmd640_vlb". (Try "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://metalab.unc.edu/pub/Linux/docs/HOWTO.) + the SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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 @@ -543,172 +553,211 @@ enabled automatically. By default, DMA is not enabled automatically 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://metalab.unc.edu/pub/Linux/system/hardware/. + the latest version of the hdparm utility from + 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. It is safe to say Y to this question. -Use DMA by default when available -CONFIG_IDEDMA_PCI_AUTO - Prior to kernel version 2.1.112, Linux used to automatically use - DMA for IDE drives and chipsets which support it. Due to concerns - about a couple of cases where buggy hardware may have caused damage, - the default is now to NOT use DMA automatically. To revert to the - previous behaviour, say Y to this question. - - If you suspect your hardware is at all flakey, say N here. - Do NOT email the IDE kernel people regarding this issue! - - It is normally safe to answer Y to this question unless your - motherboard uses a VIA VP2 chipset, in which case you should say N. - Good-Bad DMA Model-Firmware (EXPERIMENTAL) IDEDMA_NEW_DRIVE_LISTINGS - This test compares both the model and firmware revision for buggy drives - that claim to (U)DMA capable. This is a blanket on/off test with no speed - limit options. Straight GNU GCC 2.7.3/2.8.X compilers are known to be safe; - whereas, many versions of EGCS have a problem and miscompile. + If you say Y here, the model and firmware revision of your drive + will be compared against a blacklist of buggy drives that claim to + be (U)DMA capable but aren't. This is a blanket on/off test with no + speed limit options. + + Straight GNU GCC 2.7.3/2.8.X compilers are known to be safe; + whereas, many versions of EGCS have a problem and miscompile if you + say Y here. If in doubt, say N. +Winbond SL82c105 support +CONFIG_BLK_DEV_SL82C105 + If you have a Winbond SL82c105 IDE controller, say Y here to enable + special configuration for this chip. This is common on various CHRP + motherboards, but could be used elsewhere. If in doubt, say Y. + Boot off-board chipsets first support CONFIG_BLK_DEV_OFFBOARD Normally, IDE controllers built into the motherboard (on-board controllers) are assigned to ide0 and ide1 while those on add-in PCI cards (off-board controllers) are relegated to ide2 and ide3. - Answering Y here will reverse the situation, with off-board - controllers on ide0/1 and on-board controllers on ide2/3. This can - improve the usability of some boot managers such as LILO when - booting from a drive on an off-board controller. + Answering Y here will allow you to reverse the situation, with + off-board controllers on ide0/1 and on-board controllers on ide2/3. + This can improve the usability of some boot managers such as LILO + when booting from a drive on an off-board controller. + + If you say Y here, and you actually want to reverse the device scan + order as explained above, you also need to issue the kernel command + line option "pci=reverse". (Try "man bootparam" or see the + documentation 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 from + http://metalab.unc.edu/mdw/linux.html#howto .) - Requires that all onboard ide controllers be disabled or calling - "pci=reverse" to invert the device scan order. - - Note that, if you say Y here, the order of the hd* devices will be + Note that, if you do this, the order of the hd* devices will be rearranged which may require modification of fstab and other files. If in doubt, say N. -AEC6210 chipset support -CONFIG_BLK_DEV_AEC6210 - This driver adds up to 4 more eide devices sharing a single interrupt. - This add-on card is a bootable PCI UDMA controller. In order to get this - card to initialize correctly in some cases, you should include this driver. - - This prefers CONFIG_IDEDMA_PCI_AUTO to be enabled, regardless. +Use DMA by default when available +CONFIG_IDEDMA_PCI_AUTO + Prior to kernel version 2.1.112, Linux used to automatically use + DMA for IDE drives and chipsets which support it. Due to concerns + about a couple of cases where buggy hardware may have caused damage, + the default is now to NOT use DMA automatically. To revert to the + previous behaviour, say Y to this question. - Please read the comments at the top of drivers/block/aec6210.c + If you suspect your hardware is at all flakey, say N here. + Do NOT email the IDE kernel people regarding this issue! -ALI M15x3 chipset support (EXPERIMENTAL) -CONFIG_BLK_DEV_ALI15X3 - This driver ensures (U)DMA support for ALI 1533, 1543 and 1543C - onboard chipsets. It also tests for Simplex mode and enables - normal dual channel support. + It is normally safe to answer Y to this question unless your + motherboard uses a VIA VP2 chipset, in which case you should say N. - This requires CONFIG_IDEDMA_PCI_AUTO to be enabled. +Other IDE chipset support +CONFIG_IDE_CHIPSETS + Say Y here if you want to include enhanced support for various IDE + interface chipsets used on motherboards and add-on cards. You can + then pick your particular IDE chip from among the following options. + This enhanced support may be necessary for Linux to be able to + access the 3rd/4th drives in some systems. It may also enable + setting of higher speed I/O rates to improve system performance with + these chipsets. Most of these also require special kernel boot + parameters to actually turn on the support at runtime; you can find + a list of these in the file Documentation/ide.txt. + + People with SCSI-only systems can say N here. - Please read the comments at the top of drivers/block/alim15x3.c +Generic 4 drives/port support +CONFIG_BLK_DEV_4DRIVES + Certain older chipsets, including the Tekram 690CD, use a single set + of I/O ports at 0x1f0 to control up to four drives, instead of the + customary two drives per port. Support for this can be enabled at + runtime using the "ide0=four" kernel boot parameter if you say Y + here. - If unsure, say N. +DTC-2278 support +CONFIG_BLK_DEV_DTC2278 + This driver is enabled at runtime using the "ide0=dtc2278" kernel + boot parameter. It enables support for the secondary IDE interface + of the DTC-2278 card, and permits faster I/O speeds to be set as + well. See the Documentation/ide.txt and drivers/block/dtc2278.c + files for more info. -CMD646 chipset support (EXPERIMENTAL) -CONFIG_BLK_DEV_CMD646 - Say Y here if you have an IDE controller like this. +Holtek HT6560B support +CONFIG_BLK_DEV_HT6560B + This driver is enabled at runtime using the "ide0=ht6560b" kernel + boot parameter. It enables support for the secondary IDE interface + of the Holtek card, and permits faster I/O speeds to be set as well. + See the Documentation/ide.txt and drivers/block/ht6560b.c files for + more info. -CY82C693 chipset support (EXPERIMENTAL) -CONFIG_BLK_DEV_CY82C693 +PROMISE DC4030 support (EXPERIMENTAL) +CONFIG_BLK_DEV_PDC4030 + This driver provides support for the secondary IDE interface and + cache of Promise IDE chipsets, e.g. DC4030 and DC5030. This driver + is known to incur timeouts/retries during heavy I/O to drives + attached to the secondary interface. CDROM and TAPE devices are not + supported yet. This driver is enabled at runtime using the + "ide0=dc4030" kernel boot parameter. See the Documentation/ide.txt + and drivers/block/pdc4030.c files for more info. - This driver adds detection and support for the CY82C693 chipset - used on Digital's PC-Alpha 164SX boards. +PS/2 ESDI hard disk support +CONFIG_BLK_DEV_PS2 + Say Y here if you have a PS/2 machine with a MCA bus and an ESDI + hard disk. + + 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), + say M here and read Documentation/modules.txt. The module will be + called ps2esdi.o. - This requires CONFIG_IDEDMA_PCI_AUTO to be enabled. +Tekram TRM290 chipset support (EXPERIMENTAL) +CONFIG_BLK_DEV_TRM290 + This driver adds support for bus master DMA transfers + using the Tekram TRM290 PCI IDE chip. Volunteers are + needed for further tweaking and development. + Please read the comments at the top of drivers/block/trm290.c. - Please read the comments at the top of drivers/block/cy82c693.c +OPTi 82C621 enhanced support (EXPERIMENTAL) +CONFIG_BLK_DEV_OPTI621 + This is a driver for the OPTi 82C621 EIDE controller. + Please read the comments at the top of drivers/block/opti621.c. -HPT34X chipset support -CONFIG_BLK_DEV_HPT34X - This driver adds up to 4 more EIDE devices sharing a single - interrupt. The HPT343 chipset in its current form is a non-bootable or - HPT345/HPT363 chipset is bootable (needs BIOS FIX) PCI UDMA controllers. - This driver requires dynamic tuning of the chipset during the ide-probe - at boot. It is reported to support DVD II drives, by the manufacturer. +NS87415 support (EXPERIMENTAL) +CONFIG_BLK_DEV_NS87415 + This driver adds detection and support for the NS87415 chip + (used in SPARC64, among others). - Please read the comments at the top of drivers/block/hpt34x.c + Please read the comments at the top of drivers/block/ns87415.c. -HPT34X DMA support (DANGEROUS) -CONFIG_BLK_DEV_HPT34X_DMA - This requires CONFIG_IDEDMA_PCI_AUTO to be enabled. +CY82C693 chipset support (EXPERIMENTAL) +CONFIG_BLK_DEV_CY82C693 + This driver adds detection and support for the CY82C693 chipset + used on Digital's PC-Alpha 164SX boards. - Please read the comments at the top of drivers/block/hpt34x.c + If you say Y here, you need to say Y to "Use DMA by default + when available" as well. -HPT366 chipset support -CONFIG_BLK_DEV_HPT366 - This is an Ultra DMA chipset for ATA-66. - This driver adds up to 4 more EIDE devices sharing a single - interrupt. The HPT366 chipset in its current form is a non-bootable. - This driver requires dynamic tuning of the chipset during the ide-probe - at boot. It is reported to support DVD II drives, by the manufacturer. +VIA82C586 chipset support (EXPERIMENTAL) +CONFIG_BLK_DEV_VIA82C586 + Saying Y here adds initial timing settings for VIA (U)DMA onboard + IDE controllers that are ATA3 compliant. May work with ATA4 systems, + but not tested to date. To use some features of this chipset, you + will have to issue a kernel command line as described in the file + drivers/block/via82c586.c. Furthermore, if you also say Y to "/proc + filesystem support" and set DISPLAY_APOLLO_TIMINGS in via82c586.c, + you will be able to read information about the IDE controller from + the virtual file /proc/ide/via. - Please read the comments at the top of drivers/block/hpt366.c + If you say Y here, you also need to say Y to "Use DMA by default + when available", above. -Intel PIIXn chipsets support -CONFIG_BLK_DEV_PIIX - This driver adds PIO mode setting and tuning for all PIIX IDE - controllers by Intel. Since the BIOS can sometimes improperly tune - PIO 0-4 mode settings, this allows dynamic tuning of the chipset - via the standard end-user tool 'hdparm'. + If unsure, say N. - Please read the comments at the top of drivers/block/piix.c +CMD646 chipset support (EXPERIMENTAL) +CONFIG_BLK_DEV_CMD646 + Say Y here if you have an IDE controller which uses this chipset. - If unsure, say N. +ALI M15x3 chipset support (EXPERIMENTAL) +CONFIG_BLK_DEV_ALI15X3 + This driver ensures (U)DMA support for ALI 1533, 1543 and 1543C + onboard chipsets. It also tests for Simplex mode and enables + normal dual channel support. -PIIXn Tuning support (EXPERIMENTAL) -CONFIG_BLK_DEV_PIIX_TUNING - This driver extension adds DMA mode setting and tuning for all PIIX IDE - controllers by Intel. Since the BIOS can sometimes improperly setup - the device/adapter combination and speed limits, It has become a necessity - to back/forward speed devices as needed. + If you say Y here, you also need to say Y to "Use DMA by default + when available", above. - Case 430HX/440FX PIIX3 need speed limits to reduce UDMA to DMA mode 2 - if the BIOS can to perform this task at INIT. + Please read the comments at the top of drivers/block/alim15x3.c If unsure, say N. -NS87415 support (EXPERIMENTAL) -CONFIG_BLK_DEV_NS87415 - This driver adds detection and support for the NS87415 chip - (used in SPARC64, among others). +PROMISE PDC20246/PDC20262 support +CONFIG_BLK_DEV_PDC202XX + Promise Ultra33 or PDC20246 - Please read the comments at the top of drivers/block/ns87415.c. + This driver adds up to 4 more EIDE devices sharing a single + interrupt. This add-on card is a bootable PCI UDMA controller. Since + multiple cards can be installed and there are BIOS ROM problems that + happen if the BIOS revisions of all installed cards (three-max) do + not match, the driver attempts to do dynamic tuning of the chipset at + boot-time for max-speed. Ultra33 BIOS 1.25 or newer is required for + more than one card. This card may require that you say Y to "Special + UDMA Feature (EXPERIMENTAL)". -OPTi 82C621 enhanced support (EXPERIMENTAL) -CONFIG_BLK_DEV_OPTI621 - This is a driver for the OPTi 82C621 EIDE controller. - Please read the comments at the top of drivers/block/opti621.c. + Promise Ultra66 or PDC20262 -PROMISE PDC20246/PDC20262 support -CONFIG_BLK_DEV_PDC202XX - Promise Ultra33 or PDC20246. - This driver adds up to 4 more eide devices sharing a single interrupt. - This add-on card is a bootable PCI UDMA controller. - Since multiple cards can be installed and there are BIOS ROM problems - that happen if the BIOS revisions of all installed cards (three-max) - do not match. Should you be unable to make new BIOS chips with a burner, - the driver attempts to dynamic tuning of the chipset at boot-time - for max-speed. Ultra33 BIOS 1.25 or new required for more than one card. - This card may require "PDC202XX Special UDMA Feature (EXPERIMENTAL)". - - Promise Ultra66 or PDC20262. - This driver adds up to 4 more eide devices sharing a single interrupt. - This add-on card is a bootable PCI UDMA ATA-66 controller. - The driver attempts to dynamic tuning of the chipset at boot-time - for max-speed. Note tested limits are UDMA-2. - Ultra66 BIOS 1.11 or newer required. + This driver adds up to 4 more EIDE devices sharing a single + interrupt. This add-on card is a bootable PCI UDMA ATA-66 + controller. The driver attempts to dynamic tuning of the chipset at + boot-time for max-speed. Note tested limits are UDMA-2. Ultra66 BIOS + 1.11 or newer required. - This requires CONFIG_IDEDMA_PCI_AUTO to be enabled. + If you say Y here, you need to say Y to "Use DMA by default when + available" as well. Please read the comments at the top of drivers/block/pdc202xx.c @@ -716,9 +765,9 @@ Special UDMA Feature (EXPERIMENTAL) PDC202XX_FORCE_BURST_BIT - For PDC20246 and PDC20262 Ultra DMA chipsets. - Designed originally for PDC20246/Ultra33 that has BIOS setup failures - when using 3 or more cards. + For PDC20246 and PDC20262 Ultra DMA chipsets. Designed originally + for PDC20246/Ultra33 that has BIOS setup failures when using 3 or + more cards. Please read the comments at the top of drivers/block/pdc202xx.c @@ -726,132 +775,69 @@ Special Mode Feature (DANGEROUS) PDC202XX_FORCE_MASTER_MODE - For PDC20246 and PDC20262 Ultra DMA chipsets. - This is reserved for possible Hardware RAID 0,1 for the FastTrak Series. + For PDC20246 and PDC20262 Ultra DMA chipsets. This is reserved for + possible Hardware RAID 0,1 for the FastTrak Series. Say N. -SiS5513 chipset support -CONFIG_BLK_DEV_SIS5513 - This driver ensures (U)DMA support for SIS5513 chipset based mainboards. - SiS620/530 UDMA mode 4, SiS5600/5597 UDMA mode 2, all other DMA mode 2 - limited chipsets are unsupported to date. - - This requires CONFIG_IDEDMA_PCI_AUTO to be enabled. - - Please read the comments at the top of drivers/block/sis5513.c - -Winbond SL82c105 support -CONFIG_BLK_DEV_SL82C105 - If you have a Winbond SL82c105 IDE controller, say Y here to enable - special configuration for this chip. This is common on various CHRP - motherboards, but could be used elsewhere. If in doubt, say Y. +AEC6210 chipset support +CONFIG_BLK_DEV_AEC6210 + This driver adds up to 4 more EIDE devices sharing a single + interrupt. This add-on card is a bootable PCI UDMA controller. In + order to get this card to initialize correctly in some cases, you + should say Y here, and preferably also to "Use DMA by default when + available". -Tekram TRM290 chipset support (EXPERIMENTAL) -CONFIG_BLK_DEV_TRM290 - This driver adds support for bus master DMA transfers - using the Tekram TRM290 PCI IDE chip. Volunteers are - needed for further tweaking and development. - Please read the comments at the top of drivers/block/trm290.c. + Please read the comments at the top of drivers/block/aec6210.c -VIA82C586 chipset support (EXPERIMENTAL) -CONFIG_BLK_DEV_VIA82C586 - This allows you to to configure your chipset for a better use while - running (U)DMA: it will allow you to enable efficiently the second - channel dma usage, as it is may not be set by BIOS. It allows you to - run a kernel command line at boot time in order to set fifo config. - If no command line is provided, it will try to set fifo configuration - at its best. It will allow you to get a proc/ide/via display - (while running a "cat") provided you enabled "proc" support and - set DISPLAY_APOLLO_TIMINGS in via82c586.c +HPT366 chipset support +CONFIG_BLK_DEV_HPT366 + This is an Ultra DMA chipset for ATA-66. + + This driver adds up to 4 more EIDE devices sharing a single + interrupt. The HPT366 chipset in its current form is a non-bootable. + This driver requires dynamic tuning of the chipset during the + ide-probe at boot. It is reported to support DVD II drives, by the + manufacturer. + +Intel PIIXn chipsets support +CONFIG_BLK_DEV_PIIX + This driver adds PIO mode setting and tuning for all PIIX IDE + controllers by Intel. Since the BIOS can sometimes improperly tune + PIO 0-4 mode settings, this allows dynamic tuning of the chipset + via the standard end-user tool 'hdparm'. - This requires CONFIG_IDEDMA_PCI_AUTO to be enabled. + Please read the comments at the top of drivers/block/piix.c If unsure, say N. -Support for PowerMac IDE devices (must also enable IDE) -CONFIG_BLK_DEV_IDE_PMAC - No help for CONFIG_BLK_DEV_IDE_PMAC - -PowerMac IDE DMA support -CONFIG_BLK_DEV_IDEDMA_PMAC - No help for CONFIG_BLK_DEV_IDEDMA_PMAC - -Use DMA by default -CONFIG_IDEDMA_PMAC_AUTO - No help for CONFIG_IDEDMA_PMAC_AUTO - -ICS IDE interface support -CONFIG_BLK_DEV_IDE_ICSIDE - No help for CONFIG_BLK_DEV_IDE_ICSIDE - -ICS DMA support -CONFIG_BLK_DEV_IDEDMA_ICS - No help for CONFIG_BLK_DEV_IDEDMA_ICS - -Use ICS DMA by default -CONFIG_IDEDMA_ICS_AUTO - No help for CONFIG_IDEDMA_ICS_AUTO - -RapIDE interface support -CONFIG_BLK_DEV_IDE_RAPIDE - No help for CONFIG_BLK_DEV_IDE_RAPIDE - -Other IDE chipset support -CONFIG_IDE_CHIPSETS - Say Y here if you want to include enhanced support for various IDE - interface chipsets used on motherboards and add-on cards. You can - then pick your particular IDE chip from among the following options. - This enhanced support may be necessary for Linux to be able to - access the 3rd/4th drives in some systems. It may also enable - setting of higher speed I/O rates to improve system performance with - these chipsets. Most of these also require special kernel boot - parameters to actually turn on the support at runtime; you can find - a list of these in the file Documentation/ide.txt. - - People with SCSI-only systems can say N here. +PIIXn Tuning support (EXPERIMENTAL) +CONFIG_BLK_DEV_PIIX_TUNING + This driver extension adds DMA mode setting and tuning for all PIIX + IDE controllers by Intel. Since the BIOS can sometimes improperly + set up the device/adapter combination and speed limits, it has + become a necessity to back/forward speed devices as needed. -Generic 4 drives/port support -CONFIG_BLK_DEV_4DRIVES - Certain older chipsets, including the Tekram 690CD, use a single set - of I/O ports at 0x1f0 to control up to four drives, instead of the - customary two drives per port. Support for this can be enabled at - runtime using the "ide0=four" kernel boot parameter if you say Y - here. + Case 430HX/440FX PIIX3 need speed limits to reduce UDMA to DMA mode + 2 if the BIOS can not perform this task at initialization. -ALI M14xx support -CONFIG_BLK_DEV_ALI14XX - This driver is enabled at runtime using the "ide0=ali14xx" kernel - boot parameter. It enables support for the secondary IDE interface - of the ALI M1439/1443/1445/1487/1489 chipsets, and permits faster - I/O speeds to be set as well. See the files Documentation/ide.txt - and drivers/block/ali14xx.c for more info. + If unsure, say N. -DTC-2278 support -CONFIG_BLK_DEV_DTC2278 - This driver is enabled at runtime using the "ide0=dtc2278" kernel - boot parameter. It enables support for the secondary IDE interface - of the DTC-2278 card, and permits faster I/O speeds to be set as - well. See the Documentation/ide.txt and drivers/block/dtc2278.c - files for more info. +HPT34X chipset support +CONFIG_BLK_DEV_HPT34X + This driver adds up to 4 more EIDE devices sharing a single + interrupt. The HPT343 chipset in its current form is a non-bootable + controller; the HPT345/HPT363 chipset is a bootable (needs BIOS FIX) + PCI UDMA controllers. This driver requires dynamic tuning of the + chipset during the ide-probe at boot time. It is reported to support + DVD II drives, by the manufacturer. -Holtek HT6560B support -CONFIG_BLK_DEV_HT6560B - This driver is enabled at runtime using the "ide0=ht6560b" kernel - boot parameter. It enables support for the secondary IDE interface - of the Holtek card, and permits faster I/O speeds to be set as well. - See the Documentation/ide.txt and drivers/block/ht6560b.c files for - more info. +HPT34X DMA support (DANGEROUS) +CONFIG_BLK_DEV_HPT34X_DMA + you need to say Y to "Use DMA by default when available" if you say + Y here. -PROMISE DC4030 support (EXPERIMENTAL) -CONFIG_BLK_DEV_PDC4030 - This driver provides support for the secondary IDE interface and - cache of Promise IDE chipsets, e.g. DC4030 and DC5030. This driver - is known to incur timeouts/retries during heavy I/O to drives - attached to the secondary interface. CDROM and TAPE devices are not - supported yet. This driver is enabled at runtime using the - "ide0=dc4030" kernel boot parameter. See the Documentation/ide.txt - and drivers/block/pdc4030.c files for more info. + Please read the comments at the top of drivers/block/hpt343.c QDI QD6580 support CONFIG_BLK_DEV_QD6580 @@ -868,61 +854,92 @@ See the files Documentation/ide.txt and drivers/block/umc8672.c for more info. +ALI M14xx support +CONFIG_BLK_DEV_ALI14XX + This driver is enabled at runtime using the "ide0=ali14xx" kernel + boot parameter. It enables support for the secondary IDE interface + of the ALI M1439/1443/1445/1487/1489 chipsets, and permits faster + I/O speeds to be set as well. See the files Documentation/ide.txt + and drivers/block/ali14xx.c for more info. + Amiga builtin Gayle IDE interface support CONFIG_BLK_DEV_GAYLE This is the IDE driver for the builtin IDE interface on some Amiga - models. It supports both the `A1200 style' (used in A600 and A1200) - and `A4000 style' (used in A4000 and A4000T) of the Gayle IDE interface. - Say Y if you have such an Amiga model and want to use IDE devices - (hard disks, CD-ROM drives, etc.) that are connected to the builtin - IDE interface. - -Amiga IDE Doubler support (EXPERIMENTAL) -CONFIG_BLK_DEV_IDEDOUBLER - This driver provides support for the so called `IDE doublers' (made by - various manufacturers, e.g. Eyetech) that can be connected to the - builtin IDE interface of some Amiga models. Using such an IDE doubler, - you can connect up to four instead of two IDE devices on the Amiga's + models. It supports both the `A1200 style' (used in A600 and A1200) + and `A4000 style' (used in A4000 and A4000T) of the Gayle IDE + interface. Say Y if you have such an Amiga model and want to use IDE + devices (hard disks, CD-ROM drives, etc.) that are connected to the builtin IDE interface. - Note that the normal Amiga Gayle IDE driver may not work correctly if - you have an IDE doubler and don't enable this driver! - Say Y if you have an IDE doubler. The driver is enabled at kernel - runtime using the "ide=doubler" kernel boot parameter. + +Falcon IDE interface support +CONFIG_BLK_DEV_FALCON_IDE + This is the IDE driver for the builtin IDE interface on the Atari + Falcon. Say Y if you have a Falcon and want to use IDE devices (hard + disks, CD-ROM drives, etc.) that are connected to the builtin IDE + interface. Amiga Buddha/Catweasel IDE interface support (EXPERIMENTAL) CONFIG_BLK_DEV_BUDDHA This is the IDE driver for the IDE interfaces on the Buddha and Catweasel expansion boards. It supports up to two interfaces on the Buddha and three on the Catweasel. + Say Y if you have a Buddha or Catweasel expansion board and want to use IDE devices (hard disks, CD-ROM drives, etc.) that are connected to one of its IDE interfaces. -Falcon IDE interface support -CONFIG_BLK_DEV_FALCON_IDE - This is the IDE driver for the builtin IDE interface on the Atari Falcon. - Say Y if you have a Falcon and want to use IDE devices (hard disks, - CD-ROM drives, etc.) that are connected to the builtin IDE interface. +Amiga IDE Doubler support (EXPERIMENTAL) +CONFIG_BLK_DEV_IDEDOUBLER + This driver provides support for the so called `IDE doublers' (made + by various manufacturers, e.g. Eyetech) that can be connected to the + builtin IDE interface of some Amiga models. Using such an IDE + doubler, you can connect up to four instead of two IDE devices on + the Amiga's builtin IDE interface. + + Note that the normal Amiga Gayle IDE driver may not work correctly + if you have an IDE doubler and don't enable this driver! + + Say Y if you have an IDE doubler. The driver is enabled at kernel + runtime using the "ide=doubler" kernel boot parameter. + +Support for PowerMac IDE devices (must also enable IDE) +CONFIG_BLK_DEV_IDE_PMAC + No help for CONFIG_BLK_DEV_IDE_PMAC + +PowerMac IDE DMA support +CONFIG_BLK_DEV_IDEDMA_PMAC + No help for CONFIG_BLK_DEV_IDEDMA_PMAC + +Use DMA by default +CONFIG_IDEDMA_PMAC_AUTO + No help for CONFIG_IDEDMA_PMAC_AUTO Macintosh Quadra/Powerbook IDE interface support CONFIG_BLK_DEV_MAC_IDE - This is the IDE driver for the builtin IDE interface on the some m68k - Macintosh models. It supports both the `Quadra style' (used in Quadra/ - Centris 630 and Performa 588 models) and `Powerbook style' (used in the - Powerbook 150 and 190 models) IDE interface. - Say Y if you have such an Macintosh model and want to use IDE devices - (hard disks, CD-ROM drives, etc.) that are connected to the builtin - IDE interface. + This is the IDE driver for the builtin IDE interface on some m68k + Macintosh models. It supports both the `Quadra style' (used in + Quadra/ Centris 630 and Performa 588 models) and `Powerbook style' + (used in the Powerbook 150 and 190 models) IDE interface. -PS/2 ESDI hard disk support -CONFIG_BLK_DEV_PS2 - Say Y here if you have a PS/2 machine with a MCA bus and an ESDI - hard disk. - - 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), - say M here and read Documentation/modules.txt. The module will be - called ps2esdi.o. + Say Y if you have such an Macintosh model and want to use IDE + devices (hard disks, CD-ROM drives, etc.) that are connected to the + builtin IDE interface. + +ICS IDE interface support +CONFIG_BLK_DEV_IDE_ICSIDE + No help for CONFIG_BLK_DEV_IDE_ICSIDE + +ICS DMA support +CONFIG_BLK_DEV_IDEDMA_ICS + No help for CONFIG_BLK_DEV_IDEDMA_ICS + +Use ICS DMA by default +CONFIG_IDEDMA_ICS_AUTO + No help for CONFIG_IDEDMA_ICS_AUTO + +RapIDE interface support +CONFIG_BLK_DEV_IDE_RAPIDE + No help for CONFIG_BLK_DEV_IDE_RAPIDE XT hard disk support CONFIG_BLK_DEV_XD @@ -939,8 +956,9 @@ Mylex DAC960/DAC1100 PCI RAID Controller support CONFIG_BLK_DEV_DAC960 This driver adds support for the Mylex DAC960, AcceleRAID, and - eXtremeRAID PCI RAID controllers. See README.DAC960 for further - information about this driver. + eXtremeRAID PCI RAID controllers. See the file + Documentation/README.DAC960 for further information about this + driver. 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), @@ -1198,8 +1216,8 @@ have such a controller, you do not need to say Y here. More information about Software RAID on Linux is contained in the - Software-RAID mini-HOWTO, available via FTP (user: anonymous) from - ftp://metalab.unc.edu/pub/Linux/docs/HOWTO/mini. There you will also + Software-RAID mini-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . There you will also learn where to get the supporting user space utilities raidtools. If unsure, say N. @@ -1226,8 +1244,8 @@ the throughput rate if the partitions reside on distinct disks. Information about Software RAID on Linux is contained in the - Software-RAID mini-HOWTO, available via FTP (user: anonymous) from - ftp://metalab.unc.edu/pub/Linux/docs/HOWTO/mini. There you will also + Software-RAID mini-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . 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 @@ -1248,8 +1266,8 @@ drives. Information about Software RAID on Linux is contained in the - Software-RAID mini-HOWTO, available via FTP (user: anonymous) from - ftp://metalab.unc.edu/pub/Linux/docs/HOWTO/mini. There you will also + Software-RAID mini-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . 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 @@ -1271,8 +1289,8 @@ of the available parity distribution methods. Information about Software RAID on Linux is contained in the - Software-RAID mini-HOWTO, available via FTP (user: anonymous) from - ftp://metalab.unc.edu/pub/Linux/docs/HOWTO/mini. There you will also + Software-RAID mini-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . 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 @@ -1294,32 +1312,29 @@ This is a machine with a R4400 100 MHz CPU. To compile a Linux kernel that runs on these, say Y here. For details about Linux on the MIPS architecture, check out the Linux/MIPS FAQ on the WWW at - http://lena.fnet.fr/ (To browse the WWW, you need to - have access to a machine on the Internet that has a program like - lynx or netscape). + http://lena.fnet.fr/ . Support for Acer PICA 1 chipset CONFIG_ACER_PICA_61 This is a machine with a R4400 133/150 MHz CPU. To compile a Linux kernel that runs on these, say Y here. For details about Linux on the MIPS architecture, check out the Linux/MIPS FAQ on the WWW at - http://lena.fnet.fr/ (To browse the WWW, you need to have access to - a machine on the Internet that has a program like lynx or netscape). + http://lena.fnet.fr/ . Support for Algorithmics P4032 CONFIG_ALGOR_P4032 This is an evaluation board of the British company Algorithmics. The board uses the R4300 and a R5230 CPUs. For more information about - this board see http://www.algor.co.uk. + this board see http://www.algor.co.uk . IDE card support CONFIG_BLK_DEV_IDE_CARDS - On Acorn systems, enable this if you wish to use an IDE interface + On Acorn systems, say Y here if you wish to use an IDE interface expansion card. If you do not or are unsure, say N to this. ICS IDE interface CONFIG_BLK_DEV_IDE_ICS - On Acorn systems, enable this if you wish to use the ICS IDE + On Acorn systems, say Y here if you wish to use the ICS IDE interface card. This is not required for ICS partition support. If you are unsure, say N to this. @@ -1328,23 +1343,21 @@ This allows Linux on Acorn systems to determine its partitions in the 'non-ADFS' partition area of the hard disk - usually located after the ADFS partition. You are probably using this system, so - you should enable it. + you should say Y here. Support for Mips Magnum 4000 CONFIG_MIPS_MAGNUM_4000 This is a machine with a R4000 100 MHz CPU. To compile a Linux kernel that runs on these, say Y here. For details about Linux on the MIPS architecture, check out the Linux/MIPS FAQ on the WWW at - http://lena.fnet.fr/ (To browse the WWW, you need to have access to - a machine on the Internet that has a program like lynx or netscape). + http://lena.fnet.fr/ . Support for Olivetti M700 CONFIG_OLIVETTI_M700 This is a machine with a R4000 100 MHz CPU. To compile a Linux kernel that runs on these, say Y here. For details about Linux on the MIPS architecture, check out the Linux/MIPS FAQ on the WWW at - http://lena.fnet.fr/ (To browse the WWW, you need to have access to - a machine on the Internet that has a program like lynx or netscape). + http://lena.fnet.fr/ . CPU type CONFIG_CPU_R3000 @@ -1382,8 +1395,8 @@ of which are given in Documentation/Changes. For a general introduction to Linux networking, it is highly - recommended to read the NET-3-HOWTO, available via FTP (user: - anonymous) from ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. + recommended to read the NET-3-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . Socket filtering CONFIG_FILTER @@ -1397,22 +1410,55 @@ Network packet filtering CONFIG_NETFILTER - Netfilter is a framework for filtering and mangling packets. + Netfilter is a framework for filtering and mangling network packets + that pass through your Linux box. + + The most common use of packet filtering is to run your Linux box as + a firewall protecting a local network from the Internet. The type of + firewall provided by this kernel support is called a "packet + filter", which means that it can reject individual network packets + based on type, source, destination etc. The other kind of firewall, + a "proxy-based" one, is more secure but more intrusive and more + bothersome to set up; it inspects the network traffic much more + closely, modifies it and has knowledge about the higher level + protocols, which a packet filter lacks. Moreover, proxy-based + firewalls often require changes to the programs running on the local + clients. Proxy-based firewalls don't need support by the kernel, but + they are often combined with a packet filter, which only works if + you say Y here. + + You should also say Y here if you intend to use your Linux box as + the gateway to the Internet for a local network of machines without + globally valid IP addresses. This is called "masquerading": if one + of the computers on your local network wants to send something to + the outside, your box can "masquerade" as that computer, i.e. it + forwards the traffic to the intended outside destination, but + modifies the packets to make it look like they came from the + firewall box itself. It works both ways: if the outside host + replies, the Linux box will silently forward the traffic to the + correct local computer. This way, the computers on your local net + are completely invisible to the outside world, even though they can + reach the outside and can receive replies. It is even possible to + run globally visible servers from within a masqueraded local network + using a mechanism called portforwarding. Masquerading is also often + called NAT (Network Address Translation). + + Another use of Netfilter is in transparent proxying: if a machine on + the local network tries to connect to an outside host, your Linux + box can transparently forward the traffic to a local server, + typically a caching proxy server. + Various modules exist for netfilter which replace the previous masquerading (ipmasqadm), packet filtering (ipchains), transparent - proxying, and portforwarding mechanisms. Enabling this option - makes minor alterations to allow these modules to hook into the - packet stream. More information is available from - http://netfilter.kernelnotes.org (to browse the WWW, you need - to have access to a machine on the Internet that has a program like - lynx or netscape). - + proxying, and portforwarding mechanisms. More information is + available from http://netfilter.kernelnotes.org . + Make sure to say N to "Fast switching" below if you intend to say Y here, as Fast switching currently bypasses netfilter. - - Chances are that you should say Y here for every machine which is - run as a router and N for every regular host. If unsure, say N. - + + Chances are that you should say Y here if you compile a kernel which + will run as a router and N for regular hosts. If unsure, say N. + Network packet filtering debugging CONFIG_NETFILTER_DEBUG Say Y to make sure packets aren't leaking. @@ -1432,7 +1478,7 @@ is no need for the legitimate users to change their TCP/IP software; SYN cookies work transparently to them. For technical information about SYN cookies, check out - ftp://koobera.math.uic.edu/pub/docs/syncookies-archive. + ftp://koobera.math.uic.edu/pub/docs/syncookies-archive . If you are SYN flooded, the source address reported by the kernel is likely to have been forged by the attacker; it is only reported as @@ -1466,9 +1512,7 @@ To find out what type of Alpha system you have, you may want to check out the Linux/Alpha FAQ, accessible on the WWW from - http://www.alphalinux.org (To browse the WWW, you need to - have access to a machine on the Internet that has a program like - lynx or netscape). In summary: + http://www.alphalinux.org . In summary: Alcor/Alpha-XLT AS 600 Alpha-XL XL-233, XL-266 @@ -1511,9 +1555,7 @@ which is command line driven, and ARC, which uses menus and arrow keys. Details about the Linux/Alpha booting process are contained in the Linux/Alpha FAQ, accessible on the WWW from - http://www.alphalinux.org (To browse the WWW, you need to - have access to a machine on the Internet that has a program like - lynx or netscape). + http://www.alphalinux.org . The usual way to load Linux on an Alpha machine is to use MILO (a bootloader that lets you pass command line parameters to the @@ -1565,8 +1607,7 @@ Say Y here if you have dumb serial boards other than the four 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://metalab.unc.edu/pub/Linux/docs/HOWTO/mini), or other custom + from http://metalab.unc.edu/mdw/linux.html#howto ), 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 @@ -1619,8 +1660,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO, contains valuable + The PCI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto , contains valuable information about which PCI hardware does work under Linux and which doesn't. @@ -1660,58 +1701,139 @@ I2O support CONFIG_I2O - The Intelligent Input/Output (I2O) architecture allows - hardware drivers to be split into two parts: an operating system - specific module called the OSM and an hardware specific module - called the HDM. The OSM can talk to a whole range of HDM's, and - ideally the HDM's are not OS dependent. This allows for the same - driver to be used under different operating systems if the relevant - OSM is in place. If you say Y here, you will get a choice of OSM's - with the following questions. + The Intelligent Input/Output (I2O) architecture allows hardware + drivers to be split into two parts: an operating system specific + module called the OSM and an hardware specific module called the + HDM. The OSM can talk to a whole range of HDM's, and ideally the + HDM's are not OS dependent. This allows for the same HDM driver to + be used under different operating systems if the relevant OSM is in + place. In order for this to work, you need to have an I2O interface + adapter card in your computer. This card contains a special I/O + processor (IOP), thus allowing high speeds since the CPU does not + have to deal with I/O. + + If you say Y here, you will get a choice of interface adapter + drivers and OSM's with the following questions. This support is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). If you want to compile it as a module, say M here and read - Documentation/modules.txt. + Documentation/modules.txt. You will get modules called i2o_core.o + and i20_config.o. If unsure, say N. I2O PCI support CONFIG_I2O_PCI - Build in support for PCI bus I2O interface adapters. Currently this - is the only variety supported. + Say Y for support of PCI bus I2O interface adapters. Currently this + is the only variety supported, so you should say Y. + + This support is also available as a module called i2o_pci.o ( = code + which can be inserted in and removed from the running kernel + whenever you want). If you want to compile it as a module, say M + here and read Documentation/modules.txt. I2O Block OSM CONFIG_I2O_BLOCK - Include support for the I2O Block OSM. The Block OSM presents disk and - other structured block devices to the operating system. + Include support for the I2O Block OSM. The Block OSM presents disk + and other structured block devices to the operating system. + + This support is also available as a module called i2o_block.o ( = + code which can be inserted in and removed from the running kernel + whenever you want). If you want to compile it as a module, say M + here and read Documentation/modules.txt. I2O LAN OSM CONFIG_I2O_LAN - Include support for the LAN OSM. You will also need to include support - for token ring or fddi if you wish to use token ring or FDDI I2O cards - with this driver. + Include support for the LAN OSM. You will also need to include + support for token ring or FDDI if you wish to use token ring or FDDI + I2O cards with this driver. + + This support is also available as a module called i2o_lan.o ( = code + which can be inserted in and removed from the running kernel + whenever you want). If you want to compile it as a module, say M + here and read Documentation/modules.txt. I2O SCSI OSM CONFIG_I2O_SCSI - Allow direct scsi access to scsi devices on a SCSI or FibreChannel I2O - controller. You can use both the SCSI and Block OSM together if you wish. + Allows direct SCSI access to SCSI devices on a SCSI or FibreChannel + I2O controller. You can use both the SCSI and Block OSM together if + you wish. + + This support is also available as a module called i2o_scsi.o ( = + code which can be inserted in and removed from the running kernel + whenever you want). If you want to compile it as a module, say M + here and read Documentation/modules.txt. + +I2O /proc support +CONFIG_I2O_PROC + If you say Y here and to "/proc filesystem support", you will be + able to read I2O related information from the virtual directory + /proc/i2o. + + This support is also available as a module called i2o_proc.o ( = + code which can be inserted in and removed from the running kernel + whenever you want). If you want to compile it as a module, say M + here and read Documentation/modules.txt. + +Plug and Play support +CONFIG_PNP + Plug and Play (PnP) is a standard for peripherals which allows those + peripherals to be configured by software, e.g. assign IRQ's or other + parameters. No jumpers on the cards are needed, instead the values + are provided to the cards from the BIOS, from the operating system, + or using a user-space utility. + + Say Y here if you would like Linux to configure your Plug and Play + devices. You should then also say Y to "ISA Plug and Play support", + below. Alternatively, you can configure your PnP devices using the + user space utilities contained in the isapnptools package. + + This support is also available as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + If you want to compile it as a module, say M here and read + Documentation/modules.txt. + +ISA Plug and Play support +CONFIG_ISAPNP + Say Y here if you would like support for ISA Plug and Play devices. + + This support is also available as a module called isapnp.o ( = + code which can be inserted in and removed from the running kernel + whenever you want). If you want to compile it as a module, say M + here and read Documentation/modules.txt. + + If unsure, say Y. + +PCMCIA/Cardbus support +CONFIG_PCMCIA + Say Y here if you want to attach PCMCIA's (PC-cards) to your Linux + computer. These are credit-card size devices such as network cards, + modems or hard drives popular with laptops. + + You will also need David Hinds' pcmcia-cs package (see the file + Documentation/Changes for location). + +CardBus support +CONFIG_CARDBUS + CardBus is a bus mastering architecture for PC-cards (it allows + PC-cards to talk to the rest of the stuff inside your computer). If + unsure, say Y. System V IPC CONFIG_SYSVIPC Inter Process Communication is a suite of library functions and - system calls which let processes (running programs) synchronize - and exchange information. It is generally considered to be a good - 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://metalab.unc.edu/pub/Linux/docs/HOWTO), you'll need to say Y + system calls which let processes (running programs) synchronize and + exchange information. It is generally considered to be a good 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 from + http://metalab.unc.edu/mdw/linux.html#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://metalab.unc.edu/pub/Linux/docs/LDP/programmers-guide. + section 6.4 of the Linux Programmer's Guide, available from + http://metalab.unc.edu/mdw/linux.html#guide . Saying Y here enlarges your kernel by about 7 KB. Just say Y. @@ -1732,11 +1854,11 @@ The sysctl interface provides a means of dynamically changing certain kernel parameters and variables on the fly without requiring a recompile of the kernel or reboot of the system. The primary - interface consists of a system call, but if the /proc filesystem is - enabled, a tree of modifiable sysctl entries will be generated - beneath the /proc/sys directory. They are explained in the files in - Documentation/sysctl/. Note that enabling this option will enlarge - the kernel by at least 8 KB. + interface consists of a system call, but if you say Y to "/proc + filesystem support", a tree of modifiable sysctl entries will be + generated beneath the /proc/sys directory. They are explained in the + files in Documentation/sysctl/. Note that enabling this option will + enlarge the kernel by at least 8 KB. As it is generally a good thing, you should say Y here unless building a kernel for install/rescue disks or your system is very @@ -1755,8 +1877,8 @@ executables are distributed solely in ELF format. You definitely want to say Y here. - Information about ELF is contained in the ELF HOWTO available via - FTP (user: anonymous) at ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. + Information about ELF is contained in the ELF HOWTO available from + http://metalab.unc.edu/mdw/linux.html#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 @@ -1796,6 +1918,10 @@ Say Y here if you want to be able to execute Linux/Intel ELF binaries just like native Alpha binaries on your Alpha machine. For this to work, you need to have the emulator /usr/bin/em86 in place. + + You can get the same functionality by saying N here and saying Y to + "Kernel support for MISC binaries". + You may answer M to compile the emulation support as a module and later load the module when you want to use a Linux/Intel binary. The module will be called binfmt_em86.o. If unsure, say Y. @@ -1806,17 +1932,13 @@ formats into the kernel. You will like this especially when you use 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://metalab.unc.edu/pub/Linux/docs/HOWTO). Once you have + the Linux DOS emulator DOSEMU (read the DOSEMU-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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. - If you say Y here, you won't need "Kernel support for JAVA binaries" - (CONFIG_BINFMT_JAVA) or "Kernel support for Linux/Intel ELF - binaries" (CONFIG_BINFMT_EM86), as this is a more general solution. - - You can do other nice things, too. Read + You can do other nice things, too. Read the file Documentation/binfmt_misc.txt to learn how to use this feature, and Documentation/java.txt for information about how to include Java support. @@ -1872,8 +1994,8 @@ everyone wants that. 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://metalab.unc.edu/pub/Linux/utils/console. + their full potential in text mode. Download it from + ftp://metalab.unc.edu/pub/Linux/utils/console . Say Y. @@ -1884,13 +2006,14 @@ card's BIOS offers, but the traditional Linux utilities like SVGATextMode don't, you can say Y here and set the mode using the "vga=" option from your boot loader (lilo or loadlin) or set - "vga=ask" which brings up a video mode menu on kernel startup. Try + "vga=ask" which brings up a video mode menu on kernel startup. (Try "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://metalab.unc.edu/pub/Linux/docs/HOWTO. Read - Documentation/svga.txt for more information about the Video mode - selection support. If unsure, say N. + explained in the SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto .) + + Read the file Documentation/svga.txt for more information about the + Video mode selection support. If unsure, say N. Support for frame buffer devices (EXPERIMENTAL) CONFIG_FB @@ -1984,15 +2107,23 @@ you have a Retina Z3 or plan to get one before you next recompile the kernel. -Cirrus Logic generic driver (EXPERIMENTAL) +Cirrus Logic support (EXPERIMENTAL) CONFIG_FB_CLGEN This enables support for Cirrus Logic GD542x/543x based boards on Amiga: SD64, Piccolo, Picasso II/II+, Picasso IV, or EGS Spectrum. - If you have a PCI-based system, this enables support for these chips: - GD-543x, GD-544x, GD-5480. + + If you have a PCI-based system, this enables support for these + chips: GD-543x, GD-544x, GD-5480. + + Please read the file Documentation/fb/clgenfb.txt. + Say N unless you have such a graphics board or plan to get one before you next recompile the kernel. +Permedia2 support (experimental) +CONFIG_FB_PM2 + Say Y here if this is your graphics board. + Apollo support CONFIG_APOLLO Say Y here if you want to run Linux on an MC680x0-based Apollo @@ -2022,7 +2153,13 @@ ATI Mach64 display support CONFIG_FB_ATY This driver supports graphics boards with the ATI Mach64 chips. + Say Y if you have such a graphics board. + The driver is also available as a module ( = code which can be + inserted and removed from the running kernel whenever you want). The + module will be called atyfb.o. If you want to compile it as a + module, say M here and read Documentation/modules.txt. + PowerMac "control" frame buffer device support CONFIG_FB_CONTROL This driver supports a frame buffer for the graphics adapter in the @@ -2070,6 +2207,11 @@ This is the frame buffer device driver for VGA 16 color graphic cards. Say Y if you have such a card. + This code is also available as a module. If you want to compile it + 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 vga16fb.o. + Backward compatibility mode for Xpmac CONFIG_FB_COMPAT_XPMAC If you use the Xpmac X server (common with mklinux), you'll need to @@ -2112,7 +2254,7 @@ packed pixel and 32 bpp packed pixel. You can also use font widths different from 8. -Matrox G100/G200 support +Matrox G100/G200/G400 support CONFIG_FB_MATROX_G100 Say Y here if you have a Matrox Productiva G100, Matrox Mystique G200, Matrox Marvel G200 or Matrox Millennium G200 video card. If @@ -2285,10 +2427,17 @@ bits per pixel packed pixels on Mac. It supports variable font widths for low resolution screens. +#VGA 16-color planar support +#CONFIG_FBCON_VGA_PLANES +### +###What is this? +### + VGA characters/attributes support CONFIG_FBCON_VGA This is the low level frame buffer console driver for VGA text mode; - it is used by frame buffer device drivers that support VGA text mode. + it is used by frame buffer device drivers that support VGA text + mode. Parallel-port support CONFIG_PARPORT @@ -2301,8 +2450,7 @@ For extensive information about drivers for many devices attaching to the parallel port see http://www.torque.net/linux-pp.html on the - WWW (to browse the WWW, you need to have access to a machine on the - Internet that has a program like lynx or netscape). + WWW. It is possible to share a single parallel port among several devices and it is safe to compile all the corresponding drivers into the @@ -2340,6 +2488,11 @@ FIFO. See Documentation/parport.txt to find out how to specify which IRQ/DMA to use. +Support for PCMCIA management for PC-style ports +CONFIG_PARPORT_PC_PCMCIA + Say Y here if you need PCMCIA support for your PC-style parallel + ports. If unsure, say N. + Support foreign hardware CONFIG_PARPORT_OTHER Say Y here if you want to be able to load driver modules to support @@ -2359,7 +2512,7 @@ such as EPP and ECP, say Y here to enable advanced IEEE 1284 transfer modes. Also say Y if you want device ID information to appear in /proc/sys/dev/parport/*/autoprobe*. It is safe to say N. - + Enable loadable module support CONFIG_MODULES Kernel modules are small pieces of compiled code which can be @@ -2416,10 +2569,10 @@ daemon arpd. Arpd then answers the address resolution request either from its own cache or by asking the net. - This code is experimental. If you do say Y here, you should obtain a - copy of arpd from http://www.loran.com/~layes/arpd/index.html, and - you should also say Y to "Kernel/User network link driver", below. - If unsure, say N. + This code is experimental and also obsolete. If you want to use it, + you need to find a version of the daemon arpd on the net somewhere, + and you should also say Y to "Kernel/User network link driver", + below. If unsure, say N. TCP/IP networking CONFIG_INET @@ -2431,14 +2584,14 @@ allows you to ping yourself (great fun, that!). For an excellent introduction to Linux networking, please read the - NET-3-HOWTO, available via FTP (user: anonymous) from - ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. + NET-3-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This option is also necessary if you want to use the full power of 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; for more information, read - http://www.bart.nl/~patrickr/term-howto/Term-HOWTO.html). + http://www.bart.nl/~patrickr/term-howto/Term-HOWTO.html ). If you say Y here and also to "/proc filesystem support" and "Sysctl support" below, you can change various aspects of the behavior of @@ -2455,9 +2608,7 @@ intend to participate in the MBONE, a high bandwidth network on top of the Internet which carries audio and video broadcasts. More information about the MBONE is on the WWW at - http://www.best.com/~prince/techinfo/mbone.html (to browse the WWW, - you need to have access to a machine on the Internet that has a - program like lynx or netscape). Information about the multicast + http://www-itg.lbl.gov/mbone/ . Information about the multicast capabilities of the various network cards is contained in Documentation/networking/multicast.txt. For most people, it's safe to say N. @@ -2512,7 +2663,7 @@ If you are interested in this, please see the preliminary documentation at http://www.compendium.com.ar/policy-routing.txt and - ftp://post.tepkom.ru/pub/vol2/Linux/docs/advanced-routing.tex. You + ftp://post.tepkom.ru/pub/vol2/Linux/docs/advanced-routing.tex . You will need supporting software from ftp://ftp.inr.ac.ru/ip-routing/ If unsure, say N. @@ -2628,7 +2779,7 @@ appear on a different network than it physically is, or to use mobile-IP facilities (allowing laptops to seamlessly move between networks without changing their IP addresses; check out - http://anchor.cs.binghamton.edu/~mobileip/LJ/index.html). + http://anchor.cs.binghamton.edu/~mobileip/LJ/index.html ). Saying Y to this option will produce two modules ( = code which can be inserted in and removed from the running kernel whenever you @@ -2657,15 +2808,12 @@ CONFIG_IP_ALIAS Sometimes it is useful to give several IP addresses to a single physical network interface (serial port or Ethernet card). The most - common case is that you want to serve different WWW or ftp documents + common case is that you want to serve different WWW or FTP documents to the outside depending on which of your host names was used to connect to you. This is called "multihosting" or "virtual domains" - or "virtual hosting services" and is explained in detail on the WWW - at http://www.thesphere.com/~dlp/TwoServers/ (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 in the Virtual-Services-HOWTO, - available via FTP (user: anonymous) from - ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. + or "virtual hosting services" and is explained in the + Virtual-Services-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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 @@ -2693,9 +2841,7 @@ Multicast) version 1. This multicast routing protocol is used widely because Cisco supports it. You need special software to use it (pimd-v1). Please see http://netweb.usc.edu/pim/ for more - information about PIM (to browse the WWW, you need to have access to - a machine on the Internet that has a program like lynx or - netscape). + information about PIM. Say Y if you want to use PIM-SM v1. Note that you can say N here if you just want to use Dense Mode PIM. @@ -2717,38 +2863,6 @@ People having problems with NCSA telnet should see the file linux/Documentation/networking/ncsa-telnet. -Reverse ARP server -CONFIG_INET_RARP - If there are (usually diskless or portable) machines on your local - network that know their hardware Ethernet addresses but don't know - their IP addresses upon startup, they can send out a Reverse Address - Resolution Protocol (RARP) request to find out their own IP - addresses. Diskless Sun 3 machines use this procedure at boot time, - and diskless Linux boxes can be configured to do it as well. - - If you want your Linux box to be able to *answer* such requests, - answer Y here; you'll then have to run the program rarp ("man rarp") - on your box. - - 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://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 - its successor DHCP. See the DHCP FAQ - http://web.syr.edu/~jmwobus/comfaqs/dhcp.faq.html for details (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 RARP support 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 rarp.o. - - If you don't understand a word of the above, say N and rest in - peace. - Assume subnets are local CONFIG_INET_SNARL Say Y if you are on a subnetted network with all machines connected @@ -2822,15 +2936,14 @@ The IPv6 protocol CONFIG_IPV6 This is experimental support for the next version of the Internet - Protocol: IP version 6 (also called IPng "IP next generation"). + Protocol: IP version 6 (also called IPng "IP next generation"). Features of this new protocol include: expanded address space, authentication and privacy, and seamless interoperability with the current version of IP (IP version 4). For general information about - IPv6, see http://playground.sun.com/pub/ipng/html/ipng-main.html (to - browse the WWW, you need to have access to a machine on the Internet - that has a program like lynx or netscape); for specific information - about IPv6 under Linux read http://www.bieringer.de/linux/IPv6/ and - the file net/ipv6/README in the kernel source. + IPv6, see http://playground.sun.com/pub/ipng/html/ipng-main.html ; + for specific information about IPv6 under Linux read the HOWTO at + http://www.bieringer.de/linux/IPv6/ and the file net/ipv6/README in + the kernel source. If you want to use IPv6, please upgrade to the newest net-tools as given in Documentation/Changes. You will still be able to do regular @@ -2871,10 +2984,10 @@ This is support for the Novell networking protocol, IPX, commonly 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://metalab.unc.edu/pub/Linux/system/filesystems/) or from within - the Linux DOS emulator DOSEMU (read the DOSEMU-HOWTO, available in - ftp://metalab.unc.edu/pub/Linux/docs/HOWTO). In order to do the + Novell client ncpfs (available from + ftp://metalab.unc.edu/pub/Linux/system/filesystems/ ) or from within + the Linux DOS emulator DOSEMU (read the DOSEMU-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto ). In order to do the former, you'll also have to say Y to "NCP filesystem support", below. @@ -2885,13 +2998,12 @@ To turn your Linux box into a fully featured NetWare file server and IPX router, say Y here and fetch either lwared from 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + from ftp://ftp.gwdg.de/pub/linux/misc/ncpfs . For more information, + read the IPX-HOWTO available from + http://metalab.unc.edu/mdw/linux.html#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 - browse the WWW, you need to have access to a machine on the Internet - that has a program like lynx or netscape). + Macs is on the WWW at http://www.eats.com/linux_mac_win.html . The IPX driver would enlarge your kernel by about 5 kB. This driver is also available as a module ( = code which can be inserted in and @@ -2909,7 +3021,7 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO for details. + http://metalab.unc.edu/mdw/linux.html#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 @@ -2922,7 +3034,7 @@ 'special' sockets to sockets listening on the primary network is disabled. This might break existing applications, especially RIP/SAP daemons. A RIP/SAP daemon that works well with the full internal net - can be found on ftp://ftp.gwdg.de/pub/linux/misc/ncpfs. + can be found on ftp://ftp.gwdg.de/pub/linux/misc/ncpfs . If you don't know what you are doing, say N. @@ -2939,7 +3051,7 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO for details. + http://metalab.unc.edu/mdw/linux.html#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). @@ -2960,9 +3072,13 @@ More detailed documentation is available in the Documentation/networking/decnet.txt file. - Be sure to turn on the CONFIG_PROCFS and CONFIG_SYSCTL options - when using DECnet, since you will need sysctl support to aid in - configuration at run time. + Be sure to say Y to "/proc filesystem support" and "Sysctl support" + below when using DECnet, since you will need sysctl support to aid + in configuration at run time. + + The DECnet code is also available as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + The module is called decnet.o. DECnet SIOCFIGCONF support CONFIG_DECNET_SIOCGIFCONF @@ -2970,19 +3086,23 @@ you know what you are doing. It can break other applications which use this system call and the proper way to get the information provided by this call is to use rtnetlink. + + If unsure, say N. DECnet Router Support CONFIG_DECNET_ROUTER Add support for turning your DECnet Endnode into a level 1 or 2 - router. This is an unfinished option for developers only. If you - do turn it on, then make sure you also have rtnetlink configured - in, since thats the only current method of configuration. + router. This is an unfinished option for developers only. If you do + turn it on, then make sure that you also say Y to "Kernel/User + network link driver" and "Routing messages", since rtnetlink is the + only current method of configuration. DECnet Raw Socket Support CONFIG_DECNET_RAW Add support for the SOCK_RAW type under DECnet. Used by userland routing programs to receive routing messages from the kernel and - also as a general debugging aid to see whats going on "under the hood". + also as a general debugging aid to see what's going on "under the + hood". AppleTalk DDP CONFIG_ATALK @@ -2992,16 +3112,15 @@ netatalk package so that your Linux box can act as a print and file server for Macs as well as access AppleTalk printers. Check out http://threepio.hitchcock.org/cgi-bin/faq/netatalk/faq.pl on the WWW - for details (to browse the WWW, you need to have access to a machine - on the Internet that has a program like lynx or netscape). EtherTalk - is the name used for AppleTalk over Ethernet and the cheaper and - slower LocalTalk is AppleTalk over a proprietary Apple network using - serial links. EtherTalk and LocalTalk are fully supported by Linux. + for details. EtherTalk is the name used for AppleTalk over Ethernet + and the cheaper and slower LocalTalk is AppleTalk over a proprietary + Apple network using serial links. EtherTalk and LocalTalk are fully + supported by Linux. General information about how to connect Linux, Windows machines and - Macs is on the WWW at http://www.eats.com/linux_mac_win.html - The NET-3-HOWTO, available via FTP (user: anonymous) in - ftp://metalab.unc.edu/pub/Linux/docs/HOWTO contains valuable + Macs is on the WWW at http://www.eats.com/linux_mac_win.html The + NET-3-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto , contains valuable information as well. This driver is also available as a module ( = code which can be @@ -3088,10 +3207,8 @@ CONFIG_HAMRADIO If you want to connect your Linux box to an amateur radio, answer Y here. You want to read http://www.tapr.org/tapr/html/pkthome.html - (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://metalab.unc.edu/pub/Linux/docs/HOWTO. + and the HAM-HOWTO and the AX25-HOWTO, both available from + http://metalab.unc.edu/mdw/linux.html#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 @@ -3114,13 +3231,11 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. You might also want to + contained in the AX25-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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 - the WWW, you need to have access to a machine on the Internet that - has a program like lynx or netscape). + on the WWW at http://www.tapr.org/tapr/html/pkthome.html . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -3152,13 +3267,11 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. You also might want to + contained in the AX25-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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 - need to have access to a machine on the Internet that has a program - like lynx or netscape). + http://www.tapr.org/tapr/html/pkthome.html . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -3173,13 +3286,11 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. You also might want to + contained in the AX25-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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 - need to have access to a machine on the Internet that has a program - like lynx or netscape). + http://www.tapr.org/tapr/html/pkthome.html . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -3238,11 +3349,11 @@ traffic. Currently, this driver supports Ottawa PI/PI2 - (http://hydra.carleton.ca/info/pi2.html) and Gracilis PackeTwin - (http://www.paccomm.com/gracilis.html) boards. They are detected + (http://hydra.carleton.ca/info/pi2.html ) and Gracilis PackeTwin + (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://metalab.unc.edu/pub/Linux/docs/HOWTO/. + the AX25-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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 @@ -3258,18 +3369,15 @@ certain parameters, such as channel access timing, clock mode, and DMA channel. This is accomplished with a small utility program, dmascc_cfg, available at - http://www.nt.tuwien.ac.at/~kkudielk/Linux/. (To browse the WWW, you - need to have access to a machine on the Internet that has a program - like lynx or netscape). + http://www.nt.tuwien.ac.at/~kkudielk/Linux/ . Z8530 SCC driver for AX.25 CONFIG_SCC These cards are used to connect your Linux box to an amateur radio 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://metalab.unc.edu/pub/Linux/docs/HOWTO. Also make sure to say Y - to "Amateur Radio AX.25 Level 2" support. + this, read Documentation/networking/z8530drv.txt and the AX25-HOWTO, + available from http://metalab.unc.edu/mdw/linux.html#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 inserted in and removed from the running kernel whenever you want), @@ -3288,12 +3396,16 @@ ### Don't know what's going on here. ### # + YAM driver for AX.25 CONFIG_YAM - Support for the YAM modem on serial port. If you want to compile this - 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 YAM is a modem for packet radio which connects to the serial + port and includes some of the functions of a Terminal Node + Controller. If you have one of those, say Y here. + + If you want to compile this 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. BAYCOM picpar and par96 driver for AX.25 CONFIG_BAYCOM_PAR @@ -3301,9 +3413,8 @@ connect to a parallel interface. The driver supports the picpar and par96 designs. To configure the driver, use the sethdlc utility available in the standard ax25 utilities package. For information on - the modems, see http://www.baycom.de (to browse the WWW, you need to - have access to a machine on the Internet that has a program like - lynx or netscape) and Documentation/networking/baycom.txt. + the modems, see http://www.baycom.de and the file + Documentation/networking/baycom.txt. 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), @@ -3316,9 +3427,8 @@ connect to a parallel interface. The driver supports the EPP designs. To configure the driver, use the sethdlc utility available in the standard ax25 utilities package. For information on the - modems, see http://www.baycom.de (to browse the WWW, you need to - have access to a machine on the Internet that has a program like - lynx or netscape) and Documentation/networking/baycom.txt. + modems, see http://www.baycom.de and the file + Documentation/networking/baycom.txt. 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), @@ -3336,10 +3446,8 @@ driver and still provided in case this driver does not work with your serial interface chip. To configure the driver, use the sethdlc utility available in the standard ax25 utilities package. For - information on the modems, see http://www.baycom.de (to browse the - WWW, you need to have access to a machine on the Internet that has a - program like lynx or netscape) and - Documentation/networking/baycom.txt. + information on the modems, see http://www.baycom.de and + Documentation/networking/baycom.txt. 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), @@ -3352,12 +3460,10 @@ modems that connect to a serial interface. The driver supports the ser12 design in full duplex mode. This is the old driver. It is still provided in case your serial interface chip does not work with - the full duplex driver. This driver is depreciated. To configure - the driver, use the sethdlc utility available in the standard ax25 + the full duplex driver. This driver is depreciated. To configure the + driver, use the sethdlc utility available in the standard ax25 utilities package. For information on the modems, see - http://www.baycom.de (to browse the WWW, you need to have access to - a machine on the Internet that has a program like lynx or netscape) - and Documentation/networking/baycom.txt. + http://www.baycom.de and Documentation/networking/baycom.txt. 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), @@ -3374,10 +3480,8 @@ To configure the driver, use the sethdlc, smdiag and smmixer utilities available in the standard ax25 utilities package. For information on how to key the transmitter, see - http://www.ife.ee.ethz.ch/~sailer/pcf/ptt_circ/ptt.html (to browse - the WWW, you need to have access to a machine on the Internet that - has a program like lynx or netscape) and - Documentation/networking/soundmodem.txt. + http://www.ife.ee.ethz.ch/~sailer/pcf/ptt_circ/ptt.html and + Documentation/networking/soundmodem.txt. 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), @@ -3473,13 +3577,11 @@ if you want that) and the lower level data link layer protocol LAPB (say Y to "LAPB Data Link Driver" below if you want that). - You can read more about X.25 at http://www.sangoma.com/x25.html and - http://www.cisco.com/univercd/data/doc/software/11_0/rpcg/cx25.htm - (to browse the WWW, you need to have access to a machine on the - Internet that has a program like lynx or netscape). Information - about X.25 for Linux is contained in the files + You can read more about X.25 at http://www.sangoma.com/x25.htm and + http://www.cisco.com/univercd/data/doc/software/11_0/rpcg/cx25.htm . + Information about X.25 for Linux is contained in the files Documentation/networking/x25.txt and - Documentation/networking/x25-iface.txt. + Documentation/networking/x25-iface.txt. One connects to an X.25 network either with a dedicated network card using the X.21 protocol (not yet supported by Linux) or one can do @@ -3528,39 +3630,59 @@ other third party bridge products. In order to use this, you'll need the bridge configuration tools - available via FTP (user: anonymous) from - ftp://shadow.cabi.net/pub/Linux. Please read the Bridge mini-HOWTO - for more information. Note that if your box acts as a bridge, it - 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://metalab.unc.edu/pub/Linux/docs/HOWTO. The Bridging code is - still in test. If unsure, say N. + available from ftp://shadow.cabi.net/pub/Linux . Please read the + Bridge mini-HOWTO for more information. Note that if your box acts + as a bridge, it 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 from + http://metalab.unc.edu/mdw/linux.html#howto . + + The Bridging code is still in test. If unsure, say N. Packet socket CONFIG_PACKET The Packet protocol is used by applications which communicate directly with network devices without an intermediate network protocol implemented in the kernel, e.g. tcpdump. If you want them - to work, choose Y. This driver is also available as a module called - af_packet.o ( = code which can be inserted in and removed from the - running kernel whenever you want). If you want to compile it as a - module, say M here and read Documentation/modules.txt. If unsure, - say Y. + to work, choose Y. + + This driver is also available as a module called af_packet.o ( = + code which can be inserted in and removed from the running kernel + whenever you want). If you want to compile it as a module, say M + here and read Documentation/modules.txt; if you use modprobe or + kmod, you may also want to add "alias net-pf-17 af_packet" to + /etc/conf.modules. + + If unsure, say Y. + +Packet socket: mmapped IO +CONFIG_PACKET_MMAP + If you say Y here, the Packet protocol driver will use an IO + mechanism that results in faster communication. + + If unsure, say N. Kernel/User network link driver CONFIG_NETLINK - This driver allows for two-way communication between certain parts - of the kernel or modules and user processes; the user processes are - able to read from and write to character special files in the /dev - directory having major mode 36. So far, the kernel uses it to - publish some network related information if you say Y to "Routing - messages", below. You also need to say Y here if you want to use - arpd, a daemon that helps keep the internal ARP cache (a mapping - between IP addresses and hardware addresses on the local network) - small. The ethertap device, which lets user space programs read and - write raw Ethernet frames, also needs the network link driver. If - unsure, say Y. + This driver allows for two-way communication between the kernel and + user processes; the user processes communicate with the kernel by + reading from and writing to character special files in the /dev + directory having major mode 36. + + So far, the kernel uses this feature to publish some network related + information if you say Y to "Routing messages", below. You also need + to say Y here if you want to use arpd, a daemon that helps keep the + internal ARP cache (a mapping between IP addresses and hardware + addresses on the local network) small. The ethertap device, which + lets user space programs read and write raw Ethernet frames, also + needs the network link driver. + + This driver is also available as a module called netlink_dev.o ( = + code which can be inserted in and removed from the running kernel + whenever you want). If you want to compile it as a module, say M + here and read Documentation/modules.txt. + + If unsure, say Y. Routing messages CONFIG_RTNETLINK @@ -3577,30 +3699,38 @@ Asynchronous Transfer Mode (ATM) CONFIG_ATM - Kernel support for ATM. Note that you need a set of user-space programs - to actually make use of ATM. See Documentation/atm.txt for further - details. + ATM is a high-speed networking technology for Local Area Networks + and Wide Area Networks. It uses a fixed packet size and is + connection oriented, allowing for the negotiation of minimum + bandwidth requirements. + + In order to participate in an ATM network, your Linux box needs an + ATM networking card. If you have that, say Y here and to the driver + of your ATM card below. + + Note that you need a set of user-space programs to actually make use + of ATM. See the file Documentation/atm.txt for further details. Classical IP over ATM CONFIG_ATM_CLIP - Classical IP over ATM for PVCs and SVCs, supporting InARP and ATMARP. - Typically you will either use LAN Emulation (LANE) or Classical IP to - communicate with other IP hosts on your ATM network. + Classical IP over ATM for PVCs and SVCs, supporting InARP and + ATMARP. Typically you will either use LAN Emulation (LANE) or + Classical IP to communicate with other IP hosts on your ATM network. Do NOT send ICMP if no neighbour CONFIG_ATM_CLIP_NO_ICMP - Normally, an ICMP host unreachable message is sent if a neighbour cannot - be reached because there is no VC to it in the kernel's ATMARP table. - This may cause problems when ATMARP table entries are briefly removed - during revalidation. If this configuration option is set to "yes", - packets to such neighbours are silently discarded instead. + Normally, an "ICMP host unreachable" message is sent if a neighbour + cannot be reached because there is no VC to it in the kernel's + ATMARP table. This may cause problems when ATMARP table entries are + briefly removed during revalidation. If you say Y here, packets to + such neighbours are silently discarded instead. LAN Emulation (LANE) support CONFIG_ATM_LANE - LAN Emulation emulates services of existing LANs across an ATM network. - Besides operating as a normal ATM end station client, Linux LANE client - can also act as an proxy client bridging packets between ELAN and - Ethernet segments. You need LANE if you want to try MPOA. + LAN Emulation emulates services of existing LANs across an ATM + network. Besides operating as a normal ATM end station client, Linux + LANE client can also act as an proxy client bridging packets between + ELAN and Ethernet segments. You need LANE if you want to try MPOA. Multi-Protocol Over ATM (MPOA) support CONFIG_ATM_MPOA @@ -3611,50 +3741,52 @@ ATM over TCP CONFIG_ATM_TCP - ATM over TCP driver. Useful mainly for development and for experiments. + ATM over TCP driver. Useful mainly for development and for + experiments. If unsure, say N. Efficient Networks ENI155P CONFIG_ATM_ENI - Driver for the Efficient Networks ENI155p series and SMC ATM Power155 - 155 Mbps ATM adapters. Both, the versions with 512kB and 2MB on-board - RAM (Efficient calls them "C" and "S", respectively), and the FPGA and - the ASIC Tonga versions of the board are supported. The driver works - with MMF (-MF or ...F) and UTP-5 (-U5 or ...D) adapters. + Driver for the Efficient Networks ENI155p series and SMC ATM + Power155 155 Mbps ATM adapters. Both, the versions with 512kB and + 2MB on-board RAM (Efficient calls them "C" and "S", respectively), + and the FPGA and the ASIC Tonga versions of the board are supported. + The driver works with MMF (-MF or ...F) and UTP-5 (-U5 or ...D) + adapters. Enable extended debugging CONFIG_ATM_ENI_DEBUG - Extended debugging records various events and displays that list when - an inconsistency is detected. This mechanism is faster than generally - using printks, but still has some impact on performance. Note that - extended debugging may create certain race conditions itself. Enable - this ONLY if you suspect problems with the driver. + Extended debugging records various events and displays that list + when an inconsistency is detected. This mechanism is faster than + generally using printks, but still has some impact on performance. + Note that extended debugging may create certain race conditions + itself. Enable this ONLY if you suspect problems with the driver. Fine-tune burst settings CONFIG_ATM_ENI_TUNE_BURST - In order to obtain good throughput, the ENI NIC can transfer multiple - words of data per PCI bus access cycle. Such a multi-word transfer is - called a burst. + In order to obtain good throughput, the ENI NIC can transfer + multiple words of data per PCI bus access cycle. Such a multi-word + transfer is called a burst. The default settings for the burst sizes are suitable for most PCI - chipsets. However, in some cases, large bursts may overrun buffers in - the PCI chipset and cause data corruption. In such cases, large bursts - must be disabled and only (slower) small bursts can be used. The burst - sizes can be set independently in the send (TX) and receive (RX) - direction. + chipsets. However, in some cases, large bursts may overrun buffers + in the PCI chipset and cause data corruption. In such cases, large + bursts must be disabled and only (slower) small bursts can be used. + The burst sizes can be set independently in the send (TX) and + receive (RX) direction. Note that enabling many different burst sizes in the same direction - may increase the cost of setting up a transfer such that the resulting - throughput is lower than when using only the largest available burst - size. + may increase the cost of setting up a transfer such that the + resulting throughput is lower than when using only the largest + available burst size. Also, sometimes larger bursts lead to lower throughput, e.g. on an - Intel 440FX board, a drop from 135 Mbps to 103 Mbps was observed when - going from 8W to 16W bursts. + Intel 440FX board, a drop from 135 Mbps to 103 Mbps was observed + when going from 8W to 16W bursts. Enable 16W TX bursts (discouraged) CONFIG_ATM_ENI_BURST_TX_16W - Burst sixteed words at once in the send direction. This may work with - recent PCI chipsets, but is known to fail with older chipsets. + Burst sixteen words at once in the send direction. This may work + with recent PCI chipsets, but is known to fail with older chipsets. Enable 8W TX bursts (recommended) CONFIG_ATM_ENI_BURST_TX_8W @@ -3663,37 +3795,38 @@ Enable 4W TX bursts (optional) CONFIG_ATM_ENI_BURST_TX_4W - Burst four words at once in the send direction. You may want to try this - if you have disabled 8W bursts. Enabling 4W if 8W is also set may or may - not improve throughput. + Burst four words at once in the send direction. You may want to try + this if you have disabled 8W bursts. Enabling 4W if 8W is also set + may or may not improve throughput. Enable 2W TX bursts (optional) CONFIG_ATM_ENI_BURST_TX_2W - Burst two words at once in the send direction. You may want to try this - if you have disabled 4W and 8W bursts. Enabling 2W if 4W or 8W are also - set may or may not improve throughput. + Burst two words at once in the send direction. You may want to try + this if you have disabled 4W and 8W bursts. Enabling 2W if 4W or 8W + are also set may or may not improve throughput. Enable 16W RX bursts (discouraged) CONFIG_ATM_ENI_BURST_RX_16W - Burst sixteen words at once in the receive direction. This may work with - recent PCI chipsets, but is known to fail with older chipsets. + Burst sixteen words at once in the receive direction. This may work + with recent PCI chipsets, but is known to fail with older chipsets. Enable 8W RX bursts (discouraged) CONFIG_ATM_ENI_BURST_RX_8W - Burst eight words at once in the receive direction. This may work with - recent PCI chipsets, but is known to fail with older chipsets, such as - the Intel Neptune series. + Burst eight words at once in the receive direction. This may work + with recent PCI chipsets, but is known to fail with older chipsets, + such as the Intel Neptune series. Enable 4W RX bursts (recommended) CONFIG_ATM_ENI_BURST_RX_4W - Burst four words at once in the receive direction. This is the default - setting. Enabling 4W if 8W is also set may or may not improve throughput. + Burst four words at once in the receive direction. This is the + default setting. Enabling 4W if 8W is also set may or may not + improve throughput. Enable 2W RX bursts (optional) CONFIG_ATM_ENI_BURST_RX_2W - Burst two words at once in the receive direction. You may want to try - this if you have disabled 4W and 8W bursts. Enabling 2W if 4W or 8W are - also set may or may not improve throughput. + Burst two words at once in the receive direction. You may want to + try this if you have disabled 4W and 8W bursts. Enabling 2W if 4W or + 8W are also set may or may not improve throughput. ZeitNet ZN1221/ZN1225 CONFIG_ATM_ZATM @@ -3702,20 +3835,21 @@ Enable extended debugging CONFIG_ATM_ZATM_DEBUG - Extended debugging records various events and displays that list when - an inconsistency is detected. This mechanism is faster than generally - using printks, but still has some impact on performance. Note that - extended debugging may create certain race conditions itself. Enable - this ONLY if you suspect problems with the driver. + Extended debugging records various events and displays that list + when an inconsistency is detected. This mechanism is faster than + generally using printks, but still has some impact on performance. + Note that extended debugging may create certain race conditions + itself. Enable this ONLY if you suspect problems with the driver. Enable usec resolution timestamps CONFIG_ATM_ZATM_EXACT_TS - The uPD98401 SAR chip supports a high-resolution timer (approx. 30 MHz) - that is used for very accurate reception timestamps. Because that timer - overflows after 140 seconds, and also to avoid timer drift, time - measurements need to be periodically synchronized with the normal - system time. Enabling this feature will add some general overhead for - timer synchronization and also per-packet overhead for time conversion. + The uPD98401 SAR chip supports a high-resolution timer (approx. 30 + MHz) that is used for very accurate reception timestamps. Because + that timer overflows after 140 seconds, and also to avoid timer + drift, time measurements need to be periodically synchronized with + the normal system time. Enabling this feature will add some general + overhead for timer synchronization and also per-packet overhead for + time conversion. IDT 77201 (NICStAR) CONFIG_ATM_NICSTAR @@ -3772,8 +3906,8 @@ You also need to say Y here if you want support for the parallel port version of the 100 MB IOMEGA ZIP drive. - Please read the SCSI-HOWTO, available via FTP (user: anonymous) in - ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. The + Please read the SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . The SCSI-Programming-HOWTO contains information about how to add or remove an SCSI device from a running Linux machine without rebooting. @@ -3790,9 +3924,9 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. - This is NOT for SCSI CDROMs. + SCSI-HOWTO, the Disk-HOWTO and the Multi-Disk-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This is NOT for SCSI + CDROMs. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -3806,8 +3940,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO and + SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto , and drivers/scsi/README.st in the kernel source. This is NOT for SCSI CDROMs. @@ -3820,8 +3954,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. Also make sure to say Y + SCSI-HOWTO and the CDROM-HOWTO at + http://metalab.unc.edu/mdw/linux.html#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 @@ -3844,12 +3978,12 @@ CDROMs or tapes, say Y here. These won't be supported by the kernel 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://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://metalab.unc.edu/pub/Linux/docs/HOWTO. Please read the file + would need the program cdwrite, available 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 from + http://metalab.unc.edu/mdw/linux.html#howto . Please read the file Documentation/scsi-generic.txt for more information. If you want to compile this as a module ( = code which can be @@ -3914,10 +4048,9 @@ SCSI host adapters. It also works for the AVA-1505, but the IRQ etc. must be manually specified in this case. - It is explained in section 3.3 of the SCSI-HOWTO, available via FTP - (user: anonymous) at ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. You - might also want to read the comments at the top of - drivers/scsi/aha152x.c. + It is explained in section 3.3 of the SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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 inserted in and removed from the running kernel whenever you want). @@ -3927,11 +4060,11 @@ 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://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. + 3.4 of the SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . Note that Trantor was + 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. If you want to compile this as a module ( = code which can be inserted in and removed from the running kernel whenever you want), @@ -3941,8 +4074,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. If it doesn't work out + 3.5 of the SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . If it doesn't work out of the box, you may have to change some settings in drivers/scsi/aha1740.h. @@ -3975,9 +4108,9 @@ Information on the configuration options for this controller can be found by checking the help file for each of the available configuration options. You should read drivers/scsi/README.aic7xxx - at a minimum before contacting the maintainer with any questions. - The SCSI-HOWTO, available via FTP (user: anonymous) at - ftp://metalab.unc.edu/pub/Linux/docs/HOWTO can also be of great + at a minimum before contacting the maintainer with any questions. + The SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto , can also be of great help. If you want to compile this driver as a module ( = code which can be @@ -3987,26 +4120,37 @@ Enable or Disable Tagged Command Queueing by default CONFIG_AIC7XXX_TCQ_ON_BY_DEFAULT - This option causes the aic7xxx driver to attempt to use tagged command - queueing on any devices that claim to support it. If this is set to yes, - you can still turn off TCQ on troublesome devices with the use of the - tag_info boot parameter. See /usr/src/linux/drivers/scsi/README.aic7xxx - for more information on that and other aic7xxx setup commands. If this - option is turned off, you may still enable TCQ on known good devices by - use of the tag_info boot parameter. - - If you are unsure about your devices then it is safest to say N here. + This option causes the aic7xxx driver to attempt to use Tagged + Command Queueing (TCQ) on all devices that claim to support it. + + TCQ is a feature of SCSI-2 which improves performance: the host + adapter can send several SCSI commands to a device's queue even if + previous commands haven't finished yet. Because the device is + intelligent, it can optimize its operations (like head positioning) + based on its own request queue. Not all devices implement this + correctly. + + If you say Y here, you can still turn off TCQ on troublesome devices + with the use of the tag_info boot parameter. See the file + drivers/scsi/README.aic7xxx for more information on that and other + aic7xxx setup commands. If this option is turned off, you may still + enable TCQ on known good devices by use of the tag_info boot + parameter. + + If you are unsure about your devices then it is safest to say N + here. However, TCQ can increase performance on some hard drives by as much - as 50% or more, so I would recommend that if you say N here, that you - at least read the README.aic7xxx file so you will know how to enable - this option manually should your drives prove to be safe in regards - to TCQ. - - Conversely, certain drives are known to lock up or cause bus resets when - TCQ is enabled on them. If you have a Western Digital Enterprise SCSI - drive for instance, then don't even bother to enable TCQ on it as the - drive will become unreliable, and it will actually reduce performance. + as 50% or more, so it is recommended that if you say N here, you + should at least read the README.aic7xxx file so you will know how to + enable this option manually should your drives prove to be safe in + regards to TCQ. + + Conversely, certain drives are known to lock up or cause bus resets + when TCQ is enabled on them. If you have a Western Digital + Enterprise SCSI drive for instance, then don't even bother to enable + TCQ on it as the drive will become unreliable, and it will actually + reduce performance. Default number of TCQ commands per device CONFIG_AIC7XXX_CMDS_PER_DEVICE @@ -4018,14 +4162,14 @@ figure. If the number is too high for any particular device, the driver will automatically compensate usually after only 10 minutes of uptime. It will not hinder performance if some of your devices - eventually have their command depth reduced, but is a waste of memory - if all of your devices end up reducing this number down to a more - reasonable figure. - - NOTE: Certain very broken drives are known to lock up when given more - commands than they like to deal with. Quantum Fireball drives are the - most common in this category. For the Quantum Fireball drives I would - suggest no more than 8 commands per device. + eventually have their command depth reduced, but is a waste of + memory if all of your devices end up reducing this number down to a + more reasonable figure. + + NOTE: Certain very broken drives are known to lock up when given + more commands than they like to deal with. Quantum Fireball drives + are the most common in this category. For the Quantum Fireball + drives it is suggested to use no more than 8 commands per device. Default: 8 @@ -4069,12 +4213,12 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO, and the files + Adapters. Consult the SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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 - email to lnz@dandelion.com. + email to lnz@dandelion.com. You can also build this driver as a module ( = code which can be inserted in and removed from the running kernel whenever you want), @@ -4092,9 +4236,9 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO and the file - drivers/scsi/README.dtc3x80. + the SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto , and the file + drivers/scsi/README.dtc3x80. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -4110,8 +4254,7 @@ Note that this driver is obsolete; if you have one of the above SCSI Host Adapters, you should normally say N here and Y to "EATA ISA/EISA/PCI support", below. Please read the SCSI-HOWTO, available - via FTP (user: anonymous) at - ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. + from http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -4125,8 +4268,7 @@ host adapters could also use this driver but are discouraged from 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + available from http://metalab.unc.edu/mdw/linux.html#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), @@ -4139,11 +4281,11 @@ The source at drivers/scsi/u14-34f.c contains some information about 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://metalab.unc.edu/pub/Linux/docs/HOWTO. Note that there is also + SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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. + well. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -4174,8 +4316,8 @@ (TMC-1660/1680, TMC-1650/1670, TMC-3260, TMC-1610M/MER/MEX) and other adapters based on the Future Domain chipsets (Quantum ISA-200S, ISA-250MG; Adaptec AHA-2920A; and at least one IBM board). - It is explained in section 3.7 of the SCSI-HOWTO, available via FTP - (user: anonymous) at ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. + It is explained in section 3.7 of the SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . NOTE: Newer Adaptec AHA-2920C boards use the Adaptec AIC-7850 chip and should use the aic7xxx driver ("Adaptec AIC7xxx chipset SCSI @@ -4189,19 +4331,24 @@ Future Domain MCS-600/700 SCSI support CONFIG_SCSI_FD_MCS - This is support for Future Domain MCS 600/700 MCA SCSI adapters. Some - PS/2 computers are equipped with IBM Fast SCSI Adapter/A which is - identical to the MCS 700 and hence also supported by this driver. - This driver also supports the Reply SB16/SCSI card (the SCSI part). - It supports multiple adapters in the same system. + This is support for Future Domain MCS 600/700 MCA SCSI adapters. + Some PS/2 computers are equipped with IBM Fast SCSI Adapter/A which + is identical to the MCS 700 and hence also supported by this driver. + This driver also supports the Reply SB16/SCSI card (the SCSI part). + It supports multiple adapters in the same system. + + This driver is also available as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + The module will be called fd_mcs.o. If you want to compile it as a + module, say M here and read Documentation/modules.txt. Generic NCR5380/53c400 SCSI support 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://metalab.unc.edu/pub/Linux/docs/HOWTO. If it doesn't work - out of the box, you may have to change some settings in + section 3.8 of the SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . If it doesn't work out + of the box, you may have to change some settings in drivers/scsi/g_NCR5380.h. This driver is also available as a module ( = code which can be @@ -4228,9 +4375,9 @@ CONFIG_SCSI_NCR53C7xx This is a driver for 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://metalab.unc.edu/pub/Linux/docs/HOWTO. If it - doesn't work out of the box, you may have to change some settings in + explained in section 3.8 of the SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . If it doesn't work out + of the box, you may have to change some settings in drivers/scsi/53c7,8xx.h. Please read drivers/scsi/README.ncr53c7xx for the available boot time command line options. @@ -4279,11 +4426,11 @@ Recent versions of the 53C8XX chips are better supported by the option "SYM53C8XX SCSI support", below. - Note: there is yet another driver for the 53c8xx family of controllers - ("NCR53c7,8xx SCSI support" above). If you want to use them both, - you need to say M to both and build them as modules, but only one - may be active at a time. If you have a 53c8xx board, you probably do - not want to use the "NCR53c7,8xx SCSI support". + Note: there is yet another driver for the 53c8xx family of + controllers ("NCR53c7,8xx SCSI support" above). If you want to use + them both, you need to say M to both and build them as modules, but + only one may be active at a time. If you have a 53c8xx board, you + probably do not want to use the "NCR53c7,8xx SCSI support". Please read drivers/scsi/README.ncr53c8xx for more information. @@ -4300,14 +4447,14 @@ NCR53C8XX and this SYM53C8XX drivers either as module or linked to the kernel image. - When both drivers are linked to the kernel, the SYM53C8XX driver is - called first at initialization and you can use the 'excl=ioaddr' - driver boot option to exclude attachment of adapters by the SYM53C8XX - driver. For instance, entering 'sym53c8xx=excl:0xb400,excl=0xc000' at - lilo prompt prevents adapters at io address 0xb400 and 0xc000 from - being attached by the SYM53C8XX driver, thus allowing the NCR53C8XX - driver to attach them. The 'excl' option is also supported by the - NCR53C8XX driver. + When both drivers are linked into the kernel, the SYM53C8XX driver + is called first at initialization and you can use the 'excl=ioaddr' + driver boot option to exclude attachment of adapters by the + SYM53C8XX driver. For example, entering + 'sym53c8xx=excl:0xb400,excl=0xc000' at the lilo prompt prevents + adapters at io address 0xb400 and 0xc000 from being attached by the + SYM53C8XX driver, thus allowing the NCR53C8XX driver to attach them. + The 'excl' option is also supported by the NCR53C8XX driver. Please read drivers/scsi/README.ncr53c8xx for more information. @@ -4365,9 +4512,11 @@ CONFIG_SCSI_NCR53C8XX_DEFAULT_TAGS "Tagged command queuing" is a feature of SCSI-2 which improves performance: the host adapter can send several SCSI commands to a - device's queue even if previous commands haven't finished yet. Some - SCSI devices don't implement this properly; if you want to disable - this feature, enter 0 or 1 here (it doesn't matter which). + device's queue even if previous commands haven't finished yet. + Because the device is intelligent, it can optimize its operations + (like head positioning) based on its own request queue. Some SCSI + devices don't implement this properly; if you want to disable this + feature, enter 0 or 1 here (it doesn't matter which). The default value is 8 and should be supported by most hard disks. This value can be overridden from the boot command line using the @@ -4448,8 +4597,8 @@ 'ibmmcascsi=display' as an additional kernel parameter. Try "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://metalab.unc.edu/pub/Linux/docs/HOWTO. + the SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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), @@ -4525,9 +4674,9 @@ Initio 91XXU(W) SCSI support CONFIG_SCSI_INITIO - This is support for the Initio 91XXU(W) SCSI host adapter. - Please read the SCSI-HOWTO, available via FTP (user: anonymous) at - ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. + This is support for the Initio 91XXU(W) SCSI host adapter. Please + read the SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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), @@ -4537,8 +4686,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. If it doesn't work out + 3.10 of the SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . If it doesn't work out of the box, you may have to change some settings in drivers/scsi/pas16.h. @@ -4549,9 +4698,9 @@ Initio INI-A100U2W SCSI support CONFIG_SCSI_INIA100 - This is support for the Initio INI-A100U2W SCSI host adapter. - Please read the SCSI-HOWTO, available via FTP (user: anonymous) at - ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. + This is support for the Initio INI-A100U2W SCSI host adapter. Please + read the SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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), @@ -4561,8 +4710,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + SCSI host adapter. Please read the SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module called pci2000.o ( = code which can be inserted in and removed from the running kernel @@ -4572,8 +4721,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + SCSI host adapter. Please read the SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module called pci2220i.o ( = code which can be inserted in and removed from the running kernel @@ -4583,8 +4732,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + SCSI host adapter. Please read the SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module called psi240i.o ( = code which can be inserted in and removed from the running kernel @@ -4603,8 +4752,7 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + available from http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -4621,8 +4769,8 @@ access mode". Please read the file drivers/scsi/README.qlogicisp. You should also - read the SCSI-HOWTO, available via FTP (user: anonymous) at - ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. + read the SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -4642,9 +4790,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. If it doesn't work out - of the box, you may have to change some settings in + available from http://metalab.unc.edu/mdw/linux.html#howto . If it + doesn't work out of the box, you may have to change some settings in drivers/scsi/seagate.h. This driver is also available as a module ( = code which can be @@ -4655,8 +4802,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. If it doesn't work out + 3.11 of the SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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. @@ -4670,8 +4817,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. If it doesn't work out + SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . If it doesn't work out of the box, you may have to change some settings in drivers/scsi/ultrastor.h. @@ -4711,8 +4858,8 @@ subsystem 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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. @@ -4751,8 +4898,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + kernel source. Also read the SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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), @@ -4815,8 +4962,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO, is for you. + available from http://metalab.unc.edu/mdw/linux.html#howto , is for + you. Note that there is another driver for AM53C974 based adapters: "Tekram DC390(T) and Am53/79C974 (PCscsi) SCSI support", above. You @@ -4837,12 +4984,6 @@ say M here and read Documentation/modules.txt. The module will be called megaraid.o. -### -### What is this? -### -#Concurrent IO commands on MegaRAID -#CONFIG_MEGARAID_MULTI_IO - GDT SCSI Disk Array Controller support CONFIG_SCSI_GDTH This is a driver for all SCSI Disk Array Controllers (EISA/ISA/PCI) @@ -4870,8 +5011,8 @@ For more information about this 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://metalab.unc.edu/pub/Linux/docs/HOWTO. If you use this driver, + SCSI-HOWTO, which is available from + http://metalab.unc.edu/mdw/linux.html#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. @@ -4897,8 +5038,8 @@ For more information about this 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://metalab.unc.edu/pub/Linux/docs/HOWTO. If you use this driver, + SCSI-HOWTO, which is available from + http://metalab.unc.edu/mdw/linux.html#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. @@ -5022,31 +5163,28 @@ any other computer at all or if all your connections will be over a telephone 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://metalab.unc.edu/pub/Linux/docs/HOWTO) or dialing up a shell + the UUCP-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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 - http://www.bart.nl/~patrickr/term-howto/Term-HOWTO.html (to browse - the WWW, you need to have access to a machine on the Internet that - has a program like lynx or netscape)). + http://www.bart.nl/~patrickr/term-howto/Term-HOWTO.html ). You'll have to say Y if your computer contains a network card that 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://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 - newer replacement for SLIP) or PLIP (Parallel Line Internet Protocol - is mainly used to create a mini network by connecting the parallel - ports of two local machines) or AX.25/KISS (protocol for sending - Internet traffic over amateur radio links). + plan to use more than one network card under Linux)) 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 newer replacement for SLIP) or PLIP (Parallel Line Internet + Protocol is mainly used to create a mini network by connecting the + parallel ports of two local machines) or AX.25/KISS (protocol for + sending Internet traffic over amateur radio links). Make sure to read the NET-3-HOWTO. Eventually, you will have to read Olaf Kirch's excellent and free book "Network Administrator's - Guide", to be found in ftp://metalab.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 @@ -5055,11 +5193,11 @@ this device is consigned into oblivion) with a configurable IP address. It is most commonly used in order to make your currently 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://metalab.unc.edu/pub/Linux/docs/LDP. Since this + If you use SLIP or PPP, you might want to say Y here. Since this thing often comes in handy, the default is Y. It won't enlarge your - kernel either. What a deal. + kernel either. What a deal. Read about it in the Network + Administrator's Guide, available from + http://metalab.unc.edu/mdw/linux.html#guide . If you want to compile this as a module ( = code which can be inserted in and removed from the running kernel whenever you want), @@ -5085,16 +5223,14 @@ 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-3-HOWTO, available via FTP (user: anonymous) in - ftp://metalab.unc.edu/pub/Linux/docs/HOWTO, explains how to + NET-3-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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 some Internet connected Unix computer. Read - http://www.bart.nl/~patrickr/term-howto/Term-HOWTO.html (to browse - the WWW, you need to have access to a machine on the Internet that - has a program like lynx or netscape)). SLIP support will enlarge - your kernel by about 4 KB. If unsure, say N. + http://www.bart.nl/~patrickr/term-howto/Term-HOWTO.html ). SLIP + support will enlarge your kernel by about 4 KB. If unsure, say N. If you want to compile this as a module ( = code which can be inserted in and removed from the running kernel whenever you want), @@ -5108,13 +5244,12 @@ TCP/IP headers (not on the data itself), but it has to be supported on both ends. Ask your access provider if you are not sure and 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://metalab.unc.edu/pub/Linux/system/network/serial/) which allows + you plan to use SLiRP, the SLIP emulator (available from + 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-3-HOWTO, available via FTP - (user: anonymous) in ftp://metalab.unc.edu/pub/Linux/docs/HOWTO, - explains how to configure CSLIP. This won't enlarge your kernel. + definitely want to say Y here. The NET-3-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto , explains how to + configure CSLIP. This won't enlarge your kernel. Keepalive and linefill CONFIG_SLIP_SMART @@ -5136,23 +5271,30 @@ CONFIG_PPP PPP (Point to Point Protocol) is a newer and better SLIP. It serves the same purpose: sending Internet traffic over telephone (and other - serial) lines. Most ISPs these days support PPP rather than SLIP. + serial) lines. Ask your access provider if they support it, because + otherwise you can't use it; most internet access providers these + days support PPP rather than SLIP. 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://metalab.unc.edu/pub/Linux/docs/HOWTO. If you upgrade + at http://metalab.unc.edu/mdw/linux.html#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. - Almost always, if you answer Y or M to this question, you should - give the same answer to the next question, about PPP support for - async serial ports. + There are actually two versions of PPP: the traditional PPP for + asynchronous lines, such as regular analog phone lines, and + synchronous PPP which can be used over digital ISDN lines for + example. If you want to use PPP over phone lines or other + asynchronous serial lines, you need to say Y (or M) here and also to + the next option, "PPP support for async serial ports". For PPP over + synchronous lines, you should say Y (or M) here and to "Support + synchronous PPP", below. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). If you said Y to "Version information on all symbols" above, then you cannot compile the PPP driver into the kernel; you can then only - compile it as a module. The module will be called ppp_generic.o. If + compile it as a module. The module will be called ppp_generic.o. If you want to compile it as a module, say M here and read Documentation/modules.txt as well as Documentation/networking/net-modules.txt. @@ -5172,10 +5314,10 @@ CONFIG_PPP_DEFLATE Support for the Deflate compression method for PPP, which uses the Deflate algorithm (the same algorithm that gzip uses) to compress - each PPP packet before it is sent over the wire. The peer (the - machine at the other end of the PPP link, usually your ISP) has to - support the Deflate compression method as well for this to be - useful. + each PPP packet before it is sent over the wire. The machine at the + other end of the PPP link (usually your ISP) has to support the + Deflate compression method as well for this to be useful. Even if + they don't support it, it is safe to say Y here. This code is also available as a module (code which can be inserted into and removed from the running kernel). If you want to compile @@ -5185,15 +5327,19 @@ CONFIG_PPP_BSDCOMP Support for the BSD-Compress compression method for PPP, which uses the LZW compression method to compress each PPP packet before it is - sent over the wire. The peer (the other end of the PPP link) has to - support the BSD-Compress compression method as well for this to be - useful. The PPP Deflate compression method is preferable to - BSD-Compress, because it compresses better and is patent-free. + sent over the wire. The machine at the other end of the PPP link + (usually your ISP) has to support the BSD-Compress compression + method as well for this to be useful. Even if they don't support it, + it is safe to say Y here. + + The PPP Deflate compression method ("PPP Deflate compression", + above) is preferable to BSD-Compress, because it compresses better + and is patent-free. Note that the BSD compression code will always be compiled as a module; it is called bsd_comp.o and will show up in the directory modules once you have said "make modules". If unsure, say N. - + Wireless LAN (non-hamradio) CONFIG_NET_RADIO Support for wireless LANs and everything having to do with radio, @@ -5203,22 +5349,20 @@ interfaces. Some user-level drivers for scarab devices which don't require - special kernel support are available via FTP (user: anonymous) from - ftp://shadow.cabi.net/pub/Linux. + special kernel support are available from + ftp://shadow.cabi.net/pub/Linux . STRIP (Metricom Starmode radio IP) CONFIG_STRIP Say Y if you have a Metricom radio and intend to use Starmode Radio IP. STRIP is a radio protocol developed for the MosquitoNet project - (On the WWW at http://mosquitonet.stanford.edu/; to browse the WWW, - you need to have access to a machine on the Internet that has a - program like lynx or netscape) to send Internet traffic using - Metricom radios. Metricom radios are small, battery powered, - 100kbit/sec packet radio transceivers, about the size and weight of - a cellular telephone. (You may also have heard them called + (on the WWW at http://mosquitonet.stanford.edu/ ) to send Internet + traffic using Metricom radios. Metricom radios are small, battery + powered, 100kbit/sec packet radio transceivers, about the size and + weight of a cellular telephone. (You may also have heard them called "Metricom modems" but we avoid the term "modem" because it misleads many people into thinking that you can plug a Metricom modem into a - phone line and use it as a modem.) + phone line and use it as a modem.) You can use STRIP on any Linux machine with a serial port, although it is obviously most useful for people with laptop computers. If you @@ -5243,14 +5387,14 @@ location). 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://metalab.unc.edu/pub/Linux/docs/HOWTO. Some more specific + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . Some more specific information is contained in Documentation/networking/wavelan.txt and in the source code drivers/net/wavelan.p.h. You will also need the wireless tools package available from - ftp://ftp.inka.de/pub/comp/Linux/networking/NetTools/contrib/. - Please read the man pages contained therein. + ftp://hyper.stanford.edu/pub/pcmcia/contrib/ . Please read the man + pages contained therein. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5260,14 +5404,16 @@ Aironet Arlan 655 & IC2200 DS support CONFIG_ARLAN - Aironet makes Arlan. www.aironet.com. Uses www.Telxon.com chip, which is - used on several similar cards. Driver is tested on 655 and IC2200 series. - Look for http://www.ylenurme.ee/~elmer/655/ for latest information. - Driver is build as two modules, arlan and arlan-proc. The later is /proc - interface and not needed most of time. + Aironet makes Arlan, a class of wireless LAN adapters. These use the + www.Telxon.com chip, which is also used on several similar cards. + This driver is tested on the 655 and IC2200 series cards. Look at + http://www.ylenurme.ee/~elmer/655/ for latest information. + + The driver is built as two modules, arlan and arlan-proc. The latter + is the /proc interface and is not needed most of time. + On some computers the card ends up in non-valid state after some time. Use a ping-reset script to clear it. - LAPB over Ethernet driver CONFIG_LAPBETHER @@ -5295,6 +5441,39 @@ say M here and read Documentation/modules.txt. The module will be called x25_asy.o. If unsure, say N. +PCMCIA ethernet cards (NE2000 compatibles: DE-650, ...) +CONFIG_PCMCIA_PCNET + Say Y here if you intend to attach an NE2000 compatible PCMCIA + (PC-card) Ethernet networking card to your computer. + + This driver is also available as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + The module will be called pcnet_cs.o. If you want to compile it as a + module, say M here and read Documentation/modules.txt. If unsure, + say N. + +3Com 3c589 PCMCIA card +CONFIG_PCMCIA_3C589 + Say Y here if you intend to attach a 3Com 3c589 PCMCIA + (PC-card) Ethernet networking card to your computer. + + This driver is also available as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + The module will be called 3c589_cs.o. If you want to compile it as a + module, say M here and read Documentation/modules.txt. If unsure, + say N. + +Aviator/Raytheon 2.4MHz wireless +CONFIG_PCMCIA_RAYCS + Say Y here if you intend to attach an Aviator/Raytheon PCMCIA + (PC-card) wireless Ethernet networking card to your computer. + + This driver is also available as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + The module will be called ray_cs.o. If you want to compile it as a + module, say M here and read Documentation/modules.txt. If unsure, + say N. + PLIP (parallel port) support CONFIG_PLIP PLIP (Parallel Line Internet Protocol) is used to create a @@ -5314,17 +5493,15 @@ Documentation/networking/PLIP.txt. The cables can be up to 15m long. Mode 0 works also if one of the machines runs DOS/Windows and has some PLIP software installed, e.g. the Crynwr PLIP packet driver - (http://oak.oakland.edu/simtel.net/msdos/pktdrvr-pre.html; to browse - the WWW, you need to have access to a machine on the Internet that - has a program like lynx or netscape) and winsock or NCSA's telnet. - - If you want to use PLIP, say Y and read the PLIP mini-HOWTO, - available via FTP (user: anonymous) in - ftp://metalab.unc.edu/pub/Linux/docs/HOWTO/mini as well as the - NET-3-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. + (http://oak.oakland.edu/simtel.net/msdos/pktdrvr-pre.html ) and + winsock or NCSA's telnet. + + If you want to use PLIP, say Y and read the PLIP mini-HOWTO as well + as the NET-3-HOWTO, both available from + http://metalab.unc.edu/mdw/linux.html#howto . Note that the PLIP + protocol has been 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. If you want to compile this as a module ( = code which can be inserted in and removed from the running kernel whenever you want), @@ -5344,8 +5521,7 @@ Say Y if you want this and read Documentation/networking/eql.txt. You may also want to read section 6.2 of the NET-3-HOWTO, available - via FTP (user: anonymous) from - ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. + from http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5372,8 +5548,9 @@ This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). The module will be called ethertap.o. If you want to compile it as a - module, say M here and read Documentation/modules.txt. If you don't - know what to use this for, you don't need it. + module, say M here and read Documentation/modules.txt. + + If you don't know what to use this for, you don't need it. Sealevel Systems 4021 support CONFIG_SEALEVEL_4021 @@ -5393,11 +5570,10 @@ network, usually at the phone company) can carry several logical point-to-point connections to other computers connected to the frame relay network. For a general explanation of the protocol, check out - http://www.frforum.com/ on the WWW. (To browse the WWW, you need to - have access to a machine on the Internet that has a program like - lynx or netscape.) To use frame relay, you need supporting hardware - (called FRAD) and certain programs from the net-tools package as - explained in Documentation/networking/framerelay.txt. + http://www.frforum.com/ on the WWW. To use frame relay, you need + supporting hardware (called FRAD) and certain programs from the + net-tools package as explained in + Documentation/networking/framerelay.txt. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5473,9 +5649,8 @@ the price of an external router. If you have one of those cards and wish to use your Linux box as a WAN router, say Y here and also to the WAN driver for your card, below. You will then need the - wan-tools package which is available via FTP (user: anonymous) from - ftp://ftp.sangoma.com. Read Documentation/networking/wan-router.txt - for more information. + wan-tools package which is available from ftp://ftp.sangoma.com . + Read Documentation/networking/wan-router.txt for more information. The WAN routing support is also available as a module called wanrouter.o ( = code which can be inserted in and removed from the @@ -5487,17 +5662,18 @@ Fast switching (read help!) CONFIG_NET_FASTROUTE Saying Y here enables direct NIC-to-NIC (NIC = Network Interface - Card) data transfers, which is fast. + Card) data transfers on the local network, which is fast. - *** This option is NOT COMPATIBLE with several important *** - *** networking options: especially CONFIG_NETFILTER. *** - *** Say N here if you intend to use Linux as a firewall. *** + IMPORTANT NOTE: This option is NOT COMPATIBLE with "Network packet + filtering" (CONFIG_NETFILTER). Say N here if you say Y there. + + However, it will work with all options in the "IP: advanced router" + section (except for "IP: use TOS value as routing key" and + "IP: use FWMARK value as routing key"). - However, it will work with all options in CONFIG_IP_ADVANCED_ROUTER - section (except for CONFIG_IP_ROUTE_TOS and CONFIG_IP_ROUTE_FWMARK). At the moment, few devices support fast switching (tulip is one of - them, modified 8390 can be found at - ftp://ftp.inr.ac.ru/ip-routing/fastroute/fastroute-8390.tar.gz). + them, a modified 8390 driver can be found at + ftp://ftp.inr.ac.ru/ip-routing/fastroute/fastroute-8390.tar.gz ). If unsure, say N. @@ -5505,40 +5681,41 @@ CONFIG_NET_HW_FLOWCONTROL This option enables NIC (Network Interface Card) hardware throttling during periods of extremal congestion. At the moment only a couple - of device drivers support it (really only one -- tulip, modified - 8390 can be found at - ftp://ftp.inr.ac.ru/ip-routing/fastroute/fastroute-8390.tar.gz). - Really, this option is applicable to any machine attached to a fast enough - network, and even a 10 Mb NIC is able to kill a not very slow box, - such as a 120MHz Pentium. + of device drivers support it (really only one -- tulip, a modified + 8390 driver can be found at + ftp://ftp.inr.ac.ru/ip-routing/fastroute/fastroute-8390.tar.gz ). + + Really, this option is applicable to any machine attached to a fast + enough network, and even a 10 Mb NIC is able to kill a not very slow + box, such as a 120MHz Pentium. However, do not say Y here if you did not experience any serious problems. -CPU is too slow to handle full bandwidth -CONFIG_CPU_IS_SLOW - If you suspect that your CPU is not fast enough to handle the - full bandwidth of your network connection, try saying Y here. If - unsure, say N. - QoS and/or fair queueing CONFIG_NET_SCHED - When the kernel has several packets to send out over the network - devices, it has to make a decision which one to send first. This is - especially important if some of the network devices are real time - devices that need a certain minimum data flow rate. There are - several different algorithms for how to do this "fairly"; they are - called packet schedulers. If you want to stick to the default - scheduling algorithm, say N here. If you want to experiment with a - couple of different algorithms, say Y. You can then attach different - schedulers to different network devices. Currently, this is only - recommended for experts. + When the kernel has several packets to send out over a network + device, it has to decide which ones to send first, which ones to + delay, and which ones to drop. This is the job of the packet + scheduler, and several different algorithms for how to do this + "fairly" have been proposed. + + If you say N here, you will get the standard packet scheduler, which + is a FIFO (first come, first served). If you say Y here, you will be + able to choose from among several alternative algorithms which can + then be attached to different network devices. This is useful for + example if some of your network devices are real time devices that + need a certain minimum data flow rate, or if you need to limit the + maximum data flow rate for traffic which matches specified criteria. + This code is considered to be experimental. To administer these schedulers, you'll need the user-level utilities - from the package iproute2+tc at ftp://ftp.inr.ac.ru/ip-routing/ + from the package iproute2+tc at ftp://ftp.inr.ac.ru/ip-routing/ . + That package also contains some documentation; for more, check out + http://snafu.freedom.org/linux2.2/iproute-notes.html . If you say Y here and to "/proc filesystem" below, you will be able - to read status information about priority schedulers from the file + to read status information about packet schedulers from the file /proc/net/psched. The available schedulers are listed in the following questions; you @@ -5550,9 +5727,17 @@ scheduling algorithm for some of your network devices. This algorithm classifies the waiting packets into a tree-like hierarchy of classes; the leaves of this tree are in turn scheduled by - separate algorithms (called "disciplines" in this context) which you - can choose below from among the various queueing algorithms. See the - top of net/sched/sch_cbq.c for references about the CBQ algorithm. + separate algorithms (called "disciplines" in this context). + + See the top of net/sched/sch_cbq.c for references about the CBQ + algorithm. + + CBQ is a commonly used scheduler, so if you're unsure, you should + say Y here. Then say Y to all the queueing algorithms below that you + want to use as CBQ disciplines. Then say Y to "Packet classifier + API" and say Y to all the classifiers you want to use; a classifier + is a routine that allows you to sort your outgoing traffic into + classes based on a certain criterion. This code is also available as a module called sch_cbq.o ( = code which can be inserted in and removed from the running kernel @@ -5574,11 +5759,17 @@ whenever you want). If you want to compile it as a module, say M here and read Documentation/modules.txt. +#ATM pseudo-scheduler +#CONFIG_NET_SCH_ATM +# +# ??? +# + The simplest PRIO pseudo scheduler CONFIG_NET_SCH_PRIO Say Y here if you want to use an n-band priority queue packet "scheduler" for some of your network devices or as a leaf discipline - for the CBQ scheduling algorithm. + for the CBQ scheduling algorithm. If unsure, say Y. This code is also available as a module called sch_prio.o ( = code which can be inserted in and removed from the running kernel @@ -5590,7 +5781,7 @@ Say Y here if you want to use the Random Early Detection (RED) packet scheduling algorithm for some of your network devices (see the top of net/sched/sch_red.c for details and references about the - algorithm). + algorithm). This code is also available as a module called sch_red.o ( = code which can be inserted in and removed from the running kernel @@ -5640,7 +5831,7 @@ CONFIG_NET_QOS Say Y here if you want to include Quality Of Service scheduling features, which means that you will be able to request certain - rate-of-flow limits for your net devices. + rate-of-flow limits for your network devices. Note that the answer to this question won't directly affect the kernel: saying N will just cause this configure script to skip all @@ -5655,24 +5846,70 @@ Packet classifier API CONFIG_NET_CLS The CBQ scheduling algorithm requires that network packets which are - scheduled to be sent out over a network device be classified in some - way. If you say Y here, you will get a choice of several different - packet classifiers with the following questions. -# -# Routing tables based classifier -# CONFIG_NET_CLS_ROUTE -# -# Firewall based classifier -# CONFIG_NET_CLS_FW -# -# U32 classifier -# CONFIG_NET_CLS_U32 -# -# Special RSVP classifier -# CONFIG_NET_CLS_RSVP -# -# Special RSVP classifier for IPv6 -# CONFIG_NET_CLS_RSVP6 + scheduled to be sent out over a network device be classified + according to some criterion. If you say Y here, you will get a + choice of several different packet classifiers with the following + questions. + +Routing tables based classifier +CONFIG_NET_CLS_ROUTE + If you say Y here, you will be able to classify outgoing packets + according to the route table entry they matched. If unsure, say Y. + + This code is also available as a module called cls_route.o ( = code + which can be inserted in and removed from the running kernel + whenever you want). If you want to compile it as a module, say M + here and read Documentation/modules.txt. + +Firewall based classifier +CONFIG_NET_CLS_FW + If you say Y here, you will be able to classify outgoing packets + according to firewall criteria you specified. + + This code is also available as a module called cls_fw.o ( = code + which can be inserted in and removed from the running kernel + whenever you want). If you want to compile it as a module, say M + here and read Documentation/modules.txt. + +U32 classifier +CONFIG_NET_CLS_U32 + If you say Y here, you will be able to classify outgoing packets + according to their destination address. If unsure, say Y. + + This code is also available as a module called cls_u32.o ( = code + which can be inserted in and removed from the running kernel + whenever you want). If you want to compile it as a module, say M + here and read Documentation/modules.txt + +Special RSVP classifier +CONFIG_NET_CLS_RSVP + The Resource Reservation Protocol (RSVP) permits end systems to + request a minimum and maximum data flow rate for a connection; this + is important for real time data such as streaming sound or video. + + Say Y here if you want to be able to classify outgoing packets based + on their RSVP requests. + + This code is also available as a module called cls_rsvp.o ( = code + which can be inserted in and removed from the running kernel + whenever you want). If you want to compile it as a module, say M + here and read Documentation/modules.txt + +Special RSVP classifier for IPv6 +CONFIG_NET_CLS_RSVP6 + The Resource Reservation Protocol (RSVP) permits end systems to + request a minimum and maximum data flow rate for a connection; this + is important for real time data such as streaming sound or video. + + Say Y here if you want to be able to classify outgoing packets based + on their RSVP requests and you are using the new Internet Protocol + IPv6 as opposed to the older and more common IPv4. + + This code is also available as a module called cls_rsvp6.o ( = code + which can be inserted in and removed from the running kernel + whenever you want). If you want to compile it as a module, say M + here and read Documentation/modules.txt + # # Ingres traffic policing # CONFIG_NET_CLS_POLICE @@ -5716,6 +5953,12 @@ The module will be called cosa.o. For general information about modules read Documentation/modules.txt. +# Fibre Channel driver support +# CONFIG_NET_FC + +# Interphase 5526 Tachyon chipset based adaptor support +# CONFIG_IPHASE5526 + Red Creek Hardware VPN (EXPERIMENTAL) CONFIG_RCPCI This is a driver for hardware which provides a Virtual Private @@ -5742,16 +5985,15 @@ Sangoma WANPIPE(tm) multiprotocol cards CONFIG_VENDOR_SANGOMA - WANPIPE from Sangoma Technologies Inc. (http://www.sangoma.com; to - browse the WWW, you need to have access to a machine on the Internet - that has a program like lynx or netscape) is a family of intelligent - multiprotocol WAN adapters with data transfer rates up to T1 (1.544 - Mbps). They are also known as Synchronous Data Link Adapters (SDLA) - and designated S502E(A), S503 or S508. These cards support the X.25, - Frame Relay, and PPP protocols. If you have one or more of these - cards, say Y to this option; you may then also want to read the file - Documentation/networking/wanpipe.txt. The next questions will ask - you about the protocols you want the driver to support. + WANPIPE from Sangoma Technologies Inc. (http://www.sangoma.com ) is a + family of intelligent multiprotocol WAN adapters with data transfer + rates up to T1 (1.544 Mbps). They are also known as Synchronous Data + Link Adapters (SDLA) and designated S502E(A), S503 or S508. These + cards support the X.25, Frame Relay, and PPP protocols. If you have + one or more of these cards, say Y to this option; you may then also + want to read the file Documentation/networking/wanpipe.txt. The next + questions will ask you about the protocols you want the driver to + support. The driver will be compiled as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5793,23 +6035,22 @@ Cyclom 2X(tm) multiprotocol cards CONFIG_CYCLADES_SYNC Cyclom 2X from Cyclades Corporation (http://www.cyclades.com and - http://www.cyclades.com.br; to browse the WWW, you need to have - access to a machine on the Internet that has a program like lynx or - netscape) is an intelligent multiprotocol WAN adapter with data - transfer rates up to 512 Kbps). These cards support the X.25 and SNA - related protocols. If you have one or more of these cards, say Y to - this option. The next questions will ask you about the protocols you - want the driver to support (for now only X.25 is supported). + http://www.cyclades.com.br ) is an intelligent multiprotocol WAN + adapter with data transfer rates up to 512 Kbps. These cards support + the X.25 and SNA related protocols. If you have one or more of these + cards, say Y to this option. The next questions will ask you about + the protocols you want the driver to support (for now only X.25 is + supported). While no documentation is available at this time please grab the wanconfig tarball in http://www.conectiva.com.br/~acme/cycsyn-devel (with minor changes to make it compile with the current wanrouter include files; efforts are being made to use the original package - available at ftp://ftp.sangoma.com). + available at ftp://ftp.sangoma.com ). Feel free to contact me or the cycsyn-devel mailing list at acme@conectiva.com.br and cycsyn-devel@bazar.conectiva.com.br for - aditional details, I hope to have documentation available as soon + additional details, I hope to have documentation available as soon as possible. The driver will be compiled as a module ( = code which can be @@ -5821,6 +6062,7 @@ CONFIG_CYCLOMX_X25 Say Y to this option if you are planning to connect a Cyclom 2X card to an X.25 network. + If you say N, the X.25 support will not be included in the driver (saves about 11 KB of kernel memory). @@ -5841,9 +6083,9 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. You will - then also have to say Y to the driver for your particular NIC. + say Y here and read the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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 kernel: saying N will just cause this configure script to skip all @@ -5868,8 +6110,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + and read the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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 @@ -5879,8 +6121,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5891,9 +6133,8 @@ SMC Ultra MCA support 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + an MCA based system (PS/2), say Y and read the Ethernet-HOWTO, + available from http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5904,8 +6145,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . Important: There have been many reports that, with some motherboards mixing an SMC Ultra and an Adaptec AHA154x SCSI card (or compatible, @@ -5923,8 +6164,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5939,8 +6180,7 @@ another SMC9192/9194 based chipset. Say Y if you want it compiled into the kernel, and read the file Documentation/networking/smc9.txt and the Ethernet-HOWTO, available - via FTP (user: anonymous) in - ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. + from http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you @@ -5953,8 +6193,8 @@ This driver is for NE2000 compatible PCI cards. It will not work 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + say Y and read the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5966,8 +6206,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://metalab.unc.edu/pub/Linux/docs/HOWTO. + available from http://metalab.unc.edu/mdw/linux.html#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 @@ -5977,9 +6216,9 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. Note that this is still - experimental code. + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . Note that this is still + experimental code. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -5990,8 +6229,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -6002,8 +6241,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -6015,22 +6254,33 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + read the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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), say M here and read Documentation/modules.txt. This is recommended. The module will be called rtl8139.o. +SiS 900 PCI Fast Ethernet Adapter support +CONFIG_SIS900 + This is a driver for the Silicon Integrated System Corporation 900 + Fast Ethernet PCI network card. If you have one of those, say Y and + read the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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), + say M here and read Documentation/modules.txt. This is recommended. + The module will be called sis900.o. + Packet Engines Yellowfin Gigabit-NIC support CONFIG_YELLOWFIN Say Y here if you have a Packet Engines G-NIC PCI Gigabit Ethernet adapter. This adapter is used by the Beowulf Linux cluster project. See http://cesdis.gsfc.nasa.gov/linux/drivers/yellowfin.html for more information about this driver in particular and Beowulf in - general (to browse the WWW, you need to have access to a machine on - the Internet that has a program like lynx or netscape). + general. 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), @@ -6039,16 +6289,19 @@ General Instruments Surfboard 1000 CONFIG_NET_SB1000 - This is a driver for the General Instrument SURFboard 1000 internal cable - modem. This is an ISA card which is used by a number of cable TV companies - to provide cable modem access. It's a one-way downstream-only cable modem, - meaning that your upstream net link is provided by your regular phone modem. - - At present this driver only compiles as a module, so say M here if you - have this card. Then read Documentation/networking/README.sb1000 for - information on how to use this module, as it needs special ppp scripts for - establishing a connection. Further documentation and the necessary scripts - can be found at: + This is a driver for the General Instrument (also known as + NextLevel) SURFboard 1000 internal + cable modem. This is an ISA card which is used by a number of cable + TV companies to provide cable modem access. It's a one-way + downstream-only cable modem, meaning that your upstream net link is + provided by your regular phone modem. + + At present this driver only compiles as a module, so say M here if + you have this card. The module will be called sb1000.o. Then read + Documentation/networking/README.sb1000 for information on how to use + this module, as it needs special ppp scripts for establishing a + connection. Further documentation and the necessary scripts can be + found at: http://www.jacksonville.net/~fventuri/ http://home.adelphia.net/~siglercm/sb1000.html @@ -6084,8 +6337,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. Some LinkSys cards are + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . Some LinkSys cards are of this type. If you want to compile this driver as a module ( = code which can be @@ -6096,8 +6349,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + and read the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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 @@ -6107,8 +6360,8 @@ 3c501 support 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://metalab.unc.edu/pub/Linux/docs/HOWTO. Also, consider buying a + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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. @@ -6122,8 +6375,8 @@ 3c503 support 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -6135,8 +6388,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + say Y and read the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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), @@ -6147,8 +6400,8 @@ 3c507 support 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -6159,8 +6412,8 @@ 3c523 support 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -6171,8 +6424,8 @@ 3c527 support CONFIG_ELMC_II If you have a network (Ethernet) card of this type, say Y and read - the Ethernet-HOWTO, available via FTP (user: anonymous) in - ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -6184,8 +6437,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://metalab.unc.edu/pub/Linux/docs/HOWTO. + from http://metalab.unc.edu/mdw/linux.html#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 @@ -6201,10 +6453,10 @@ 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://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. + (Ethernet) card, say Y and read the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . More specific + information is in Documentation/networking/vortex.txt and in the + comments at the beginning of drivers/net/3c59x.c. If you want to compile this as a module ( = code which can be inserted in and removed from the running kernel whenever you want), @@ -6217,8 +6469,9 @@ bus system (that's the way the cards talks to the other components 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://metalab.unc.edu/pub/Linux/docs/HOWTO. If unsure, say Y. + available from http://metalab.unc.edu/mdw/linux.html#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 @@ -6236,9 +6489,8 @@ support" below. You might also want to have a look at the Ethernet-HOWTO, available - via FTP (user: anonymous) in - ftp://metalab.unc.edu/pub/Linux/docs/HOWTO (even though ARCnet is - not really Ethernet). + from http://metalab.unc.edu/mdw/linux.html#howto (even though ARCnet + is not really Ethernet). This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -6324,8 +6576,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -6337,8 +6589,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO as well as + Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto as well as Documentation/networking/cs89x0.txt. If you want to compile this as a module ( = code which can be @@ -6350,8 +6602,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO as well as + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto as well as drivers/net/depca.c. If you want to compile this as a module ( = code which can be @@ -6365,8 +6617,8 @@ This driver supports the DE203, DE204 and DE205 network (Ethernet) 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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), @@ -6377,14 +6629,20 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + is for you, read the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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), + say M here and read Documentation/modules.txt as well as + Documentation/networking/net-modules.txt. The module will be called + ewrk3.o. 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -6396,8 +6654,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + say Y and read the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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. @@ -6412,8 +6670,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + separate driver. Please read the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -6424,8 +6682,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. Note that the Intel + read the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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. @@ -6439,8 +6697,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -6451,8 +6709,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -6463,8 +6721,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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), @@ -6475,9 +6733,9 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. Many Ethernet cards - without a specific driver are compatible with NE2000. + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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 NE2000 support", above. If you have a NE2000 card and are running on @@ -6494,14 +6752,14 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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://metalab.unc.edu/pub/Linux/docs/HOWTO. + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -6511,24 +6769,24 @@ SKnet MCA support CONFIG_SKMC - This are Micro Channel ethernet adapters. You need to set CONFIG_MCA - to use this driver. It's both available as an in-kernel driver and - as a module ( = code which can be inserted in and removed from the - running kernel whenever you want). If you want to compile it as a module, - say M here and read Documentation/modules.txt as well as - Documentation/networking/net-modules.txt. If you plan to use more than - one network card under linux, read the Multiple-Ethernet-mini-HOWTO, - available from sunsite.unc.edu:/pub/Linux/docs/HOWTO/mini. Supported - cards are the SKnet Junior MC2 and the SKnet MC2(+). Distinguishing - both cards is done automatically. Note that using multiple boards - of different type hasn't been tested with this driver. + These are Micro Channel ethernet adapters. You need to say Y to "MCA + support" in order to use this driver. Supported cards are the SKnet + Junior MC2 and the SKnet MC2(+). The driver automatically + distinguishes between the two cards. Note that using multiple boards + of different type hasn't been tested with this driver. Say Y if you + have one of these ethernet adapters. + + This driver is also available as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + The module is called sk_mca.o. If you want to compile it as a + module, say M here and read Documentation/modules.txt as well as + Documentation/networking/net-modules.txt. EISA, VLB, PCI and on board controllers 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + available from http://metalab.unc.edu/mdw/linux.html#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 @@ -6539,8 +6797,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + answer Y here and read the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -6551,8 +6809,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -6563,8 +6821,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -6575,8 +6833,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. Note that this driver + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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 @@ -6588,8 +6846,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + read the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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), @@ -6602,8 +6860,8 @@ This is support for the DIGITAL series of PCI/EISA Ethernet cards. 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://metalab.unc.edu/pub/Linux/docs/HOWTO. More specific + Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . More specific information is contained in Documentation/networking/de4x5.txt. This driver is also available as a module ( = code which can be @@ -6620,10 +6878,9 @@ of this type. (If your card is NOT SMC EtherPower 10/100 PCI (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://metalab.unc.edu/pub/Linux/docs/HOWTO. - More specific information is contained in - Documentation/networking/tulip.txt. + will say Y here.) Do read the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . More specific + information is contained in Documentation/networking/tulip.txt. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -6636,8 +6893,8 @@ This is support for the Digi International RightSwitch series of 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://metalab.unc.edu/pub/Linux/docs/HOWTO. More specific + Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . More specific information is contained in Documentation/networking/dgrs.txt. This driver is also available as a module ( = code which can be @@ -6649,8 +6906,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + card, say Y and read the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -6661,8 +6918,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -6674,8 +6931,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . Devices currently supported by this driver are Compaq Netelligent, Compaq NetFlex and Olicom cards. Please read the file @@ -6703,8 +6960,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -6716,8 +6973,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://metalab.unc.edu/pub/Linux/docs/HOWTO. + available from http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -6735,15 +6991,27 @@ The Zenith Z-Note notebook computer has a built-in network (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://metalab.unc.edu/pub/Linux/docs/HOWTO. + by this driver. Read the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . + +Adaptec Starfire support +CONFIG_ADAPTEC_STARFIRE + If you have an Ethernet network card like this, say Y and read the + Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . + + This driver is also available as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + The module will be called starfire.o. If you want to compile it as a + module, say M here and read Documentation/modules.txt as well as + Documentation/networking/net-modules.txt. 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + one of those, say Y and read the Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . If you want to plug a network (or some other) card into the PCMCIA (or PC-card) slot of your laptop instead (PCMCIA is the standard for @@ -6752,9 +7020,7 @@ Documentation/Changes) and you can say N here. Laptop users should read the Linux Laptop home page at - http://www.cs.utexas.edu/users/kharker/linux-laptop/ (to browse the - WWW, you need to have access to a machine on the Internet that has a - program like lynx or netscape). + http://www.cs.utexas.edu/users/kharker/linux-laptop/ . Note that the answer to this question doesn't directly affect the kernel: saying N will just cause this configure script to skip all @@ -6765,20 +7031,20 @@ 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://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. + available from http://metalab.unc.edu/mdw/linux.html#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. D-Link DE600 pocket adapter support 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://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. + Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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. If you want to compile this driver as a module however ( = code which can be inserted in and removed from the running kernel @@ -6789,10 +7055,11 @@ 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://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. + Ethernet-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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. If you want to compile this driver as a module however ( = code which can be inserted in and removed from the running kernel @@ -6807,16 +7074,14 @@ connected to such a Token Ring network and want to use your Token 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://metalab.unc.edu/pub/Linux/docs/HOWTO. Most people can say N - here. + from http://metalab.unc.edu/mdw/linux.html#howto . Most people can + say N here. IBM Tropic chipset based adapter support 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + available from http://metalab.unc.edu/mdw/linux.html#howto . Warning: this driver will almost definitely fail if more than one active Token Ring card is present. @@ -6832,16 +7097,16 @@ Specifically this is all IBM PCI, PCI Wake On Lan, PCI II, PCI II Wake On Lan, and PCI 100/16/4 adapters. - If you have such an adapter, say Y and read the Token-Ring mini-HOWTO, - available via FTP (user:anonymous) from - ftp://metalab.unc/edu/pub/Linux/docs/HOWTO. + If you have such an adapter, say Y and read the Token-Ring + mini-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). - The module will will be called olympic.o. If you want to compile it as a - module, say M here and read Documentation/modules.txt. + The module will will be called olympic.o. If you want to compile it + as a module, say M here and read Documentation/modules.txt. - Also read the linux/Documentation/networking/olympic.txt or check the + Also read the file Documentation/networking/olympic.txt or check the Linux Token Ring Project site for the latest information at http://www.linuxtr.net @@ -6852,21 +7117,28 @@ (SK-4590), SysKonnect TR4/16 PCI (SK-4591) adapters. 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + read the Token-Ring mini-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . Also read the file linux/Documentation/networking/sktr.txt or check the Linux-SNA WWW site for the latest information at - http://samba.anu.edu.au/linux-sna/documents/drivers/SysKonnect/ + http://www.linux-sna.org . Traffic Shaper (EXPERIMENTAL) CONFIG_SHAPER The traffic shaper is a virtual network device that allows you to - limit the rate of outgoing data flow over some other network - device. See Documentation/networking/shaper.txt for more - information. To set up and configure shaper devices, you need the - shapecfg program, available via FTP (user: anonymous) from - ftp://shadow.cabi.net/pub/Linux in the shaper package. + limit the rate of outgoing data flow over some other network device. + The traffic that you want to slow down can then be routed through + these virtual devices. See Documentation/networking/shaper.txt for + more information. + + An alternative to this traffic shaper is the experimental + Class-Based Queueing (CBQ) scheduling support which you get if you + say Y to "QoS and/or fair queueing" above. + + To set up and configure shaper devices, you need the shapecfg + program, available from ftp://shadow.cabi.net/pub/Linux in the + shaper package. This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -6899,16 +7171,6 @@ under Linux, say Y here (you must also remember to enable the driver for your HIPPI card below). Most people will say N here. -CERN HIPPI PCI adapter support -CONFIG_CERN_HIPPI - Say Y here if this is your PCI HIPPI network card. - - This driver is also available as a module ( = code which can be - inserted in and removed from the running kernel whenever you want). - The module will be called cern_hippi.o. If you want to compile it as - a module, say M here and read Documentation/modules.txt. If unsure, - say N. - Essential RoadRunner HIPPI PCI adapter support CONFIG_ROADRUNNER Say Y here if this is your PCI HIPPI network card. @@ -6950,8 +7212,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + here, otherwise N. Read the CDROM-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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 @@ -7009,9 +7271,6 @@ (PhotoCDs). There is a new driver (next question) which can do this. If you want that one, say N here. - If the driver doesn't work out of the box, you might want to have a - look at drivers/cdrom/mcd.h. - If you say Y here, you should also say Y or M to "ISO 9660 CDROM filesystem support" below, because that's the filesystem used on CDROMs. @@ -7215,22 +7474,253 @@ The module will be called isp16.o. If you want to compile it as a module, say M here and read Documentation/modules.txt. -Quota support -CONFIG_QUOTA - If you say Y here, you will be able to set per user limits for disk - usage (also called disk quotas). Currently, it works only for the - 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://metalab.unc.edu/pub/Linux/docs/HOWTO/mini. Probably the quota - support is only useful for multi user systems. If unsure, say N. +Quota support +CONFIG_QUOTA + If you say Y here, you will be able to set per user limits for disk + usage (also called disk quotas). Currently, it works only for the + ext2 filesystem. You need additional software in order to use quota + support; for details, read the Quota mini-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . Probably the quota + support is only useful for multi user systems. If unsure, say N. + +Support for USB (EXPERIMENTAL!) +CONFIG_USB + Universal Serial Bus (USB) is a specification for a serial bus + system which offers higher speeds and more features than the + traditional PC serial port. The bus supplies power to peripherals + and allows for hot swapping. Up to 127 USB peripherals can be + connected to a single USB port in a tree structure; the USB port is + the root of the tree, the peripherals are the leafs and the inner + nodes are special USB devices called hubs. Many newer PC's have USB + ports and newer peripherals such as scanners, keyboards, mice, + modems and printers support the USB protocol and can be connected to + the PC via those ports. + + Say Y here if your computer has a USB port and you want to + experiment with USB devices. You then need to say Y to at least one + of "UHCI support" or "OHCI support" below (the type of interface + that the USB hardware in your computer provides) and then choose + from among the drivers for USB peripherals. + + This code is also available as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + The module will be called usbcore.o. If you want to compile it as a + module, say M here and read Documentation/modules.txt. + +UHCI (intel PIIX4 and others) support? +CONFIG_USB_UHCI + The Universal Host Controller Interface is a standard by Intel for + accessing the USB hardware in the PC (which is also called the USB + host controller). If your USB host controller conforms to this + standard, say Y. All recent boards with Intel PCI chipsets conform + to this standard. If unsure, say Y. + + This code is also available as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + The module will be called usb-uhci.o. If you want to compile it as a + module, say M here and read Documentation/modules.txt. + +OHCI (compaq and some others) support? +CONFIG_USB_OHCI + The Open Host Controller Interface is a standard by Compaq for + accessing the USB PC hardware (also called USB host controller). If + your USB host controller conforms to this standard, say Y. The USB + host controllers on most non-Intel architectures and on several x86 + compatibles with non-Intel chipsets conform to this standard. + + There are currently two OHCI drivers in development. You should + compile at most one. The other one is "OHCI-HCD (other OHCI opt. + Virt. Root Hub) support?", below. + + You may want to read the file drivers/usb/README.ohci. + + This code is also available as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + The module will be called usb-ohci.o. If you want to compile it as a + module, say M here and read Documentation/modules.txt. + +Enable tons of OHCI debugging output +CONFIG_USB_OHCI_DEBUG + Say Y here in order to have the OHCI code generate verbose debugging + output. + +OHCI-HCD (other OHCI opt. Virt. Root Hub) support? +CONFIG_USB_OHCI_HCD + This is an alternative driver for USB PC hardware (also called USB + host controller) which complies with Compaq's Open Host Controller + Interface. You may want to read the file + drivers/usb/README.ohci_hcd. + + There are currently two OHCI drivers in development. You should + compile at most one. The other one is "OHCI (compaq and some others) + support?", above. + + This code is also available as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + The module will be called usb-ohci-hcd.o. If you want to compile it + as a module, say M here and read Documentation/modules.txt. + +OHCI-HCD Virtual Root Hub +CONFIG_USB_OHCI_VROOTHUB + The virtual root hub support is currently unstable, so you probably + want to say N unless you are a hacker. But you aren't a hacker since + you are reading help texts. + +Enable lots of ISOC debugging output +CONFIG_USB_DEBUG_ISOC + Say Y here if you want to get lots of debugging output related to + the USB code. + +USB hub support +CONFIG_USB_HUB + Say Y here if you want to connect several USB devices to a single + USB port. You will need an USB hub to do this. + + If unsure, say Y. + + This code is also available as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + The module will be called hub.o. If you want to compile it as a + module, say M here and read Documentation/modules.txt. + +USB mouse support +CONFIG_USB_MOUSE + Say Y here if you want to connect a USB mouse to your computer's USB + port. + + This code is also available as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + The module will be called mouse.o. If you want to compile it as a + module, say M here and read Documentation/modules.txt. + +USB HP scanner support +CONFIG_USB_HP_SCANNER + Say Y here if you want to connect a USB HP scanner to your + computer's USB port. Please read drivers/usb/README.hp_scanner + for more information. + + This code is also available as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + The module will be called hp_scanner.o. If you want to compile it as + a module, say M here and read Documentation/modules.txt. + +USB keyboard support +CONFIG_USB_KBD + Say Y here if you want to connect a USB keyboard to your computer's + USB port. + + This code is also available as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + The module will be called usb-keyboard.o. If you want to compile it + as a module, say M here and read Documentation/modules.txt. + +USB audio parsing support +CONFIG_USB_AUDIO + Say Y here if you want to connect audio equipment such as USB + speakers to your computer's USB port. + + This code is also available as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + The module will be called audio.o. If you want to compile it as a + module, say M here and read Documentation/modules.txt. + +USB Communications Device Class (ACM) support (Preliminary) +CONFIG_USB_ACM + This driver allows for devices which support the Abstract Control + Model, including many USB-based modems, ISDN adapters, and network + adapters. + + This code is also available as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + The module will be called acm.o. If you want to compile it as a + module, say M here and read Documentation/modules.txt. + +USB Printer support +CONFIG_USB_PRINTER + Say Y here if you want to connect a printer to your computer's USB + port. + + This code is also available as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + The module will be called printer.o. If you want to compile it as a + module, say M here and read Documentation/modules.txt. + +USB CPiA Camera support +CONFIG_USB_CPIA + Say Y here if you want to connect this type of camera to your + computer's USB port. + + This code is also available as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + The module will be called cpia.o. If you want to compile it as a + module, say M here and read Documentation/modules.txt. + +USB SCSI Support +CONFIG_USB_SCSI + Say Y here if you want to connect SCSI devices to your computer's + USB port. + +USB SCSI verbose debug +CONFIG_USB_SCSI_DEBUG + Say Y here in order to have the USB SCSI code generate verbose + debugging messages. + +#EZUSB Firmware downloader +#CONFIG_USB_EZUSB + +USS720 parport driver +CONFIG_USB_USS720 + This driver is for USB parallel port adapters that use the Lucent + Technologies USS-720 chip. These adapters provide USB compatibility + to peripherals designed with parallel port interfaces. + + The chip has two modes: automatic mode and manual mode. In automatic + mode, it looks to the computer like a standard USB printer. Only + printers may be connected to the USS-720 in this mode. The generic + USB printer driver ("USB Printer support", above) may be used in + that mode, and you can say N here if you want to use the chip only + in this mode. + + Manual mode is not limited to printers, any parallel port + device should work. This driver utilizes manual mode. + Note however that some operations are three orders of a magnitude + slower than on a PCI/ISA Parallel Port, so timing critical + applications might not work. + + Say Y here if you own an USS-720 USB->Parport cable and intend to + connect anything other than a printer to it. + + This code is also available as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + The module will be called uss720.o. If you want to compile it as a + module, say M here and read Documentation/modules.txt. + +USB /proc filesystem entry support (Preliminary) +CONFIG_USB_PROC + This reports USB drivers and devices in the /proc filesystem. + Entries are located in /proc/bus/usb. The entries are described in + the file Documentation/proc_usb_info.txt. + + Note that you must say Y to "/proc filesystem support" below for + this to work. -Acorn's ADFS filesystem support (read only) (EXPERIMENTAL) -CONFIG_ADFS_FS - The Advanced Disk File System is the filesystem used on floppy and - hard disks by Acorn Systems. Currently in development, as a read- - only driver for hard disks. These should be the first partition - (eg. /dev/[sh]d?1) on each of your drives. If unsure, say N. +Generic ACPI support +CONFIG_ACPI + Advanced Configuration and Power Interface (ACPI) is an interface + specification to support power management of peripherals. If your + system supports it, say Y here. + + This code is also available as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + The module will be called acpi.o. If you want to compile it as a + module, say M here and read Documentation/modules.txt. + +PIIX4 ACPI support +CONFIG_PIIX4_ACPI + If you have a PIIX4 based motherboard (PCI ISA IDE Xcelerator + (PIIX4) is a multi-function PCI device) and you want support for + Advanced Configuration and Power Interface (ACPI) to support power + management of peripherals, say Y here. Minix fs support CONFIG_MINIX_FS @@ -7269,10 +7759,9 @@ filesystem support" below). Saying Y here will enlarge your kernel by about 44 kB. - The Ext2fs-Undeletion mini-HOWTO, available via FTP (user: - anonymous) from ftp://metalab.unc.edu/pub/Linux/docs/HOWTO/mini, - gives information about how to retrieve deleted files on ext2fs - filesystems. + The Ext2fs-Undeletion mini-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto , gives information about + how to retrieve deleted files on ext2fs filesystems. To change the behavior of ext2 filesystems, you can use the tune2fs utility ("man tune2fs"). To modify attributes of files and @@ -7280,12 +7769,12 @@ Ext2fs partitions can be read from within DOS using the ext2tool command line tool package (available via FTP (user: anonymous) from - ftp://metalab.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://metalab.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. + http://jnewbigin-pc.it.swin.edu.au/Linux/Explore2fs.htm . If you want to compile this filesystem as a module ( = code which can be inserted in and removed from the running kernel whenever you @@ -7304,9 +7793,8 @@ If you have a CDROM drive and want to do more with it than just 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://metalab.unc.edu/pub/Linux/docs/HOWTO), thereby enlarging your - kernel by about 27 kB; otherwise say N. + from http://metalab.unc.edu/mdw/linux.html#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 inserted in and removed from the running kernel whenever you want), @@ -7319,16 +7807,15 @@ which allows for long filenames in unicode format (unicode is the new 16 bit character code, successor to ASCII, which encodes the characters of almost all languages of the world; see - http://www.unicode.org for more information; to browse the WWW, you - need to have access to a machine on the Internet that has a program - like lynx or netscape). Say Y here if you want to be able to read - Joliet CDROMs under Linux. + http://www.unicode.org for more information). Say Y here if you want + to be able to read Joliet CDROMs under Linux. UDF Filesystem support CONFIG_UDF_FS - This is the new filesystem used by some CDROMS and DVD drivers. - Say Y if you intend to mount DVD discs or CDRWs written in packet mode, - or if written to by other UDF utilities, such as DirectCD. + This is the new filesystem used by some CDROMS and DVD drivers. Say + Y if you intend to mount DVD discs or CDRW's written in packet mode, + or if written to by other UDF utilities, such as DirectCD. Please + read Documentation/filesystems/udf.txt. This filesystem support is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you @@ -7384,9 +7871,9 @@ This allows you to mount MSDOS partitions of your hard drive (unless 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://metalab.unc.edu/pub/Linux/docs/HOWTO, or try dmsdosfs in - ftp://metalab.unc.edu/pub/Linux/system/filesystems/dosfs. If you + DOSEMU-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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 @@ -7468,11 +7955,8 @@ to use the same IRQ). The /proc filesystem is explained in the file - Documentation/proc.txt, in the Kernel Hacker's Guide at - http://www.redhat.com:8080/HyperNews/get/khg.html on the WWW (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 on the proc(8) - manpage ("man 8 proc"). + Documentation/filesystems/proc.txt and on the proc(5) manpage ("man + 5 proc"). This option will enlarge your kernel by about 67 KB. Several programs depend on this, so everyone should say Y here. @@ -7487,8 +7971,8 @@ client's hard disk. For this to work, the server must run the 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://metalab.unc.edu/pub/Linux/docs/LDP, on its man page: "man + Administrator's Guide, available from + http://metalab.unc.edu/mdw/linux.html#guide , on its man page: "man nfs", and in the NFS-HOWTO. A superior but less widely used alternative to NFS is provided by @@ -7538,8 +8022,8 @@ locations are given in the file Documentation/Changes in the NFS section. - Please read the NFS-HOWTO, available via FTP (user: anonymous) from - ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. + Please read the NFS-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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). @@ -7550,26 +8034,16 @@ CONFIG_NFSD_SUN If you would like for the server to allow clients to access directories that are mount points on the local filesystem (this is - how nfsd behaves on Sun systems), say yes here. If unsure, say N. + how nfsd behaves on Sun systems), say Y here. If unsure, say N. -OS/2 HPFS filesystem support (read/write) +OS/2 HPFS filesystem support (read only) CONFIG_HPFS_FS OS/2 is IBM's operating system for PC's, the same as Warp, and HPFS is the filesystem used for organizing files on OS/2 hard disk - partitions. Say Y if you want to be able to read and write files - on an OS/2 HPFS partition of your hard drive. OS/2 floppies however - are in regular MSDOS format, so you don't need this option in order - to be able to read them. Read Documentation/filesystems/hpfs.txt. - - Write support is new and experimental. I don't think it's so - "experimental" that it corrupts disks. (but you know: "There's no - warranty") There are many checks and filesystem is remounted read-only - if any inconsistency found. I use it quite long time and it works. - - This driver may not be able to write to HPFS386 disks on Warp server. - HPFS386 on Warp client seems to work ok. If some unknown HPFS386 - structures are deteced, they are not destroyed and filesystem is - remounted read-only. + partitions. Say Y if you want to be able to read files from an OS/2 + HPFS partition of your hard drive. OS/2 floppies however are in + regular MSDOS format, so you don't need this option in order to be + able to read them. Read Documentation/filesystems/hpfs.txt. This filesystem is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -7612,7 +8086,7 @@ Xenix, Wyse, UnixWare, Dell Unix and System V programs under Linux and is often needed to run commercial software that's only available for those systems. It's available via FTP (user: anonymous) from - ftp://tsx-11.mit.edu/pub/linux/BETA). + ftp://tsx-11.mit.edu/pub/linux/BETA ). If you only intend to mount files from some other Unix over the network using NFS, you don't need the System V filesystem support @@ -7645,11 +8119,9 @@ fs/affs/Changes. With this driver you can also mount disk files used by Bernd - Schmidt's Un*X Amiga Emulator (http://www.freiburg.linux.de/~uae/; - 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 - do this, you will also need to say Y or M to "Loop device support", - above. + Schmidt's Un*X Amiga Emulator (http://www.freiburg.linux.de/~uae/ ). + If you want to do this, you will also need to say Y or M to "Loop + device support", above. This filesystem is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -7709,7 +8181,7 @@ automounter (amd), which is a pure user space daemon. To use the automounter you need the user-space tools from - ftp://ftp.kernel.org/pub/linux/daemons/autofs; you also want to + ftp://ftp.kernel.org/pub/linux/daemons/autofs ; you also want to answer Y to "NFS filesystem support", below. If you want to compile this as a module ( = code which can be @@ -7720,6 +8192,26 @@ If you are not a part of a fairly large, distributed network, you probably do not need an automounter, and can say N here. +EFS filesystem support (experimental) +CONFIG_EFS_FS + EFS is an older filesystem used for non-ISO9660 CDROMs and hard disk + partitions by SGI's IRIX operating system (IRIX 6.0 and newer uses + the XFS filesystem for hard disk partitions however). + + This implementation only offers read-only access. If you don't know + what all this is about, it's safe to say N. For more information + about EFS see its home page at http://aeschi.ch.eu.org/efs/ . + + If you want to compile the UFS filesystem support 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 efs.o. + +SGI disklabel support +CONFIG_SGI_DISKLABEL + Say Y to this only if you plan on mounting disks with SGI + disklabels. This is not required to mount EFS-format CDROMs. + UFS filesystem support CONFIG_UFS_FS BSD and derivate versions of Unix (such as SunOS, FreeBSD, NetBSD, @@ -7755,29 +8247,30 @@ Say Y here if you want to try writing to UFS partitions. This is experimental, so you should back up your UFS partitions beforehand. -EFS filesystem support (experimental) -CONFIG_EFS_FS - EFS is the filesystem used for CDROMs and filesystems by SGI's IRIX. - This implementation only offers read-only access. If you don't know - what all this is about, it's safe to say N. For more information - about EFS see its homepage at http://aeschi.ch.eu.org/efs/. +Advanced partition selection +CONFIG_PARTITION_ADVANCED + Say Y here if you would like to use hard disks under Linux which + were partitioned under an operating system running on a different + architecture than your Linux system. -SGI disklabel support -CONFIG_SGI_DISKLABEL - Say Y to this only if you plan on mounting disks with SGI disklabels. - This is not required to mount EFS-format CDROMs. + Note that the answer to this question won't directly affect the + kernel: saying N will just cause this configure script to skip all + the questions about foreign partitioning schemes. If unsure, say N. -EFS filesystem support (experimental) -CONFIG_EFS_FS - EFS is the filesystem used for CDROMs and filesystems by SGI's IRIX. - This implementation only offers read-only access. If you don't know - what all this is about, it's safe to say N. For more information - about EFS see it's homepage at http://aeschi.ch.eu.org/efs. +Alpha OSF partition support +CONFIG_OSF_PARTITION + Say Y here if you would like to use hard disks under Linux which + were partitioned on an Alpha machine. -SGI disklabel support -CONFIG_SGI_DISKLABEL - Say Y to this only if you plan on mounting disks with SGI disklabels. - This is not required to mount EFS-format CDROMs. +Macintosh partition map support +CONFIG_MAC_PARTITION + Say Y here if you would like to use hard disks under Linux which + were partitioned on a Macintosh. + +PC BIOS (MSDOS partition tables) support +CONFIG_MSDOS_PARTITION + Say Y here if you would like to use hard disks under Linux which + were partitioned on an x86 PC (not necessarily by DOS). BSD disklabel (FreeBSD partition tables) support CONFIG_BSD_DISKLABEL @@ -7790,11 +8283,11 @@ filesystem support", above. If you don't know what all this is about, say N. -SMD disklabel (Sun partition tables) support -CONFIG_SMD_DISKLABEL +Sun partition tables support +CONFIG_SUN_PARTITION Like most systems, SunOS uses its own hard disk partition table format, incompatible with all others. Saying Y here allows you to - read these partition tables and further mount SunOS disks from + read these partition tables and further mount SunOS partitions from within Linux if you have also said Y to "UFS filesystem support", above. This is mainly used to carry data from a SPARC under SunOS to your Linux box via a removable medium like magneto-optical or ZIP @@ -7807,9 +8300,14 @@ CONFIG_SOLARIS_X86_PARTITION Like most systems, Solaris x86 uses its own hard disk partition table format, incompatible with all others. Saying Y here allows you - to read these partition tables and further mount Solaris x86 disks - from within Linux if you have also said Y to "UFS filesystem - support", above. + to read these partition tables and further mount Solaris x86 + partitions from within Linux if you have also said Y to "UFS + filesystem support", above. + +SGI partition support +CONFIG_SGI_PARTITION + Say Y here if you would like to be able to read the hard disk + partition table format used by SGI machines. ADFS filesystem support (read only) (EXPERIMENTAL) CONFIG_ADFS_FS @@ -7820,7 +8318,8 @@ and from ADFS-formatted floppy discs. The ADFS partition should be the first partition (i.e., - /dev/[hs]d?1) on each of your drives. + /dev/[hs]d?1) on each of your drives. Please read the file + Documentation/filesystems/adfs.txt for further details. This code is also available as a module called adfs.o ( = code which can be inserted in and removed from the running kernel whenever you @@ -7863,12 +8362,6 @@ 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 - partition tables of Macintosh hard drives, and thus use partitions - on those drives. - SMB filesystem support (to mount Windows shares etc...) CONFIG_SMB_FS SMB (Server Message Block) is the protocol Windows for Workgroups @@ -7878,20 +8371,17 @@ access them just like any other Unix directory. Currently, this works only if the Windows machines use TCP/IP as the underlying transport protocol, and not NetBEUI. For details, read - Documentation/filesystems/smbfs.txt and the SMB-HOWTO, available via - FTP (user: anonymous) from - ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. + Documentation/filesystems/smbfs.txt and the SMB-HOWTO, available + from http://metalab.unc.edu/mdw/linux.html#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://metalab.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 - browse the WWW, you need to have access to a machine on the Internet - that has a program like lynx or netscape). + Macs is on the WWW at http://www.eats.com/linux_mac_win.html . If you want to compile the SMB support as a module ( = code which can be inserted in and removed from the running kernel whenever you @@ -7912,9 +8402,7 @@ *client*. You will need user level code as well, both for the client and server. Servers are currently user level, i.e. need no kernel support. Please read Documentation/filesystems/coda.txt and check - out the Coda home page http://www.coda.cs.cmu.edu (to browse the - WWW, you need to have access to a machine on the Internet that has a - program like lynx or netscape). + out the Coda home page http://www.coda.cs.cmu.edu . If you want to compile the coda client support as a module ( = code which can be inserted in and removed from the running kernel @@ -7929,15 +8417,13 @@ 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://metalab.unc.edu/pub/Linux/docs/howto. + IPX-HOWTO from http://metalab.unc.edu/mdw/linux.html#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. 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 - browse the WWW, you need to have access to a machine on the Internet - that has a program like lynx or netscape). + Macs is on the WWW at http://www.eats.com/linux_mac_win.html . If you want to compile this as a module ( = code which can be inserted in and removed from the running kernel whenever you want), @@ -8300,7 +8786,7 @@ letters that were missing in Latin 4 to cover the entire Nordic area. -nls iso8859-14 +NLS ISO 8859-14 (Latin 8; Celtic) CONFIG_NLS_ISO8859_14 If you want to display filenames with native language characters from the Microsoft fat filesystem family or from JOLIET CDROMs @@ -8372,9 +8858,8 @@ would use the third virtual terminal as system console. (Try "man bootparam" or see the documentation 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://metalab.unc.edu/pub/Linux/docs/HOWTO.) + lilo procedure is also explained in the SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto .) If unsure, say Y. @@ -8416,9 +8901,9 @@ BTW1: If you have a mouseman serial mouse which is not recognized by the X window system, try running gpm first. - BTW2: If you intend to connect a so-called Winmodem to your - machine's serial port, forget it. These modems are crippled and - require proprietary drivers which are only available under Windows. + BTW2: If you intend to use a software modem (also called Winmodem) + under Linux, forget it. These modems are crippled and require + proprietary drivers which are only available under Windows. Most people will say Y or M here, so that they can use serial mice, modems and similar devices connecting to the standard serial ports. @@ -8437,8 +8922,8 @@ "console=ttyS1". (Try "man bootparam" or see the documentation 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://metalab.unc.edu/pub/Linux/docs/HOWTO.) + SCSI-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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 @@ -8501,6 +8986,21 @@ Also it's possible to say M here and compile this driver as kernel loadable module; the module will be called riscom8.o. +Computone IntelliPort Plus serial support +CONFIG_COMPUTONE + This driver supports the entire family of Intelliport II/Plus + controllers with the exception of the MicroChannel controllers. It + does not support products previous to the Intelliport II. These are + multiport cards, which give you many serial ports. You would need + something like this to connect more than two modems to your Linux + box, for instance in order to become a dial-in server. If you have a + card like that, say Y here and read Documentation/computone.txt. + + If you want to compile this 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. You will get two + modules called ip2.o and ip2main.o. + Specialix IO8+ card support CONFIG_SPECIALIX This is a driver for the Specialix IO8+ multiport card (both the @@ -8594,15 +9094,23 @@ Synchronous HDLC line discipline support CONFIG_N_HDLC - Allows synchronous HDLC communications with - tty device drivers that support synchronous - HDLC such as the Microgate SyncLink adapter. + Allows synchronous HDLC communications with tty device drivers that + support synchronous HDLC such as the Microgate SyncLink adapter. This driver can only be built as a module ( = code which can be inserted in and removed from the running kernel whenever you want). The module will be called n_hdlc.o. If you want to do that, say M here. +Specialix SX (and SI) card support +CONFIG_SX + This is a driver for the SX and SI multiport serial cards. + Please read the file Documentation/sx.txt for details. + + This driver can only be built as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + The module will be called sx.o. If you want to do that, say M here. + Hayes ESP serial port support CONFIG_ESPSERIAL This is a driver which supports Hayes ESP serial ports. Both single @@ -8665,25 +9173,24 @@ If you intend to attach a printer to the parallel port of your Linux 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + read the Printing-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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 corresponding drivers into the kernel. If you want to compile this driver as a module however ( = code which can be inserted in and removed from the running kernel whenever you want), say M here and - read Documentation/modules.txt and Documentation/parport.txt. The + read Documentation/modules.txt and Documentation/parport.txt. The module will be called lp.o. If you have several parallel ports, you can specify which ports to use with the "lp" kernel command line option. (Try "man bootparam" - or see the documentation 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://metalab.unc.edu/pub/Linux/docs/HOWTO.) - The syntax of the "lp" command line option can be found in - drivers/char/lp.c. + or see the documentation 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 from + http://metalab.unc.edu/mdw/linux.html#howto .) The syntax of the "lp" + command line option can be found in drivers/char/lp.c. If you have more than 3 printers, you need to increase the LP_NO variable in lp.c. @@ -8701,15 +9208,38 @@ If unsure, say N. -Mouse Support (not serial mice) -CONFIG_MOUSE - This is for machines with a bus mouse or a PS/2 mouse as opposed to - a serial mouse. Most people have a regular serial MouseSystem or +Bus Mouse Support +CONFIG_BUSMOUSE + Say Y here if your machine has a bus mouse as opposed to a serial + mouse. Most people have a regular serial MouseSystem or 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://metalab.unc.edu/pub/Linux/docs/HOWTO and - say Y here. + have something else, read the Busmouse-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto , and say Y here. + + If you have a laptop, you either have to check the documentation or + experiment a bit to find out whether the trackball is a serial mouse + or not; it's best to say Y here for you. + + This is the generic bus mouse driver code. If you have a bus mouse, + you will have to say Y here and also to the specific driver for your + mouse below. + + This code is also available as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + The module will be called busmouse.o. If you want to compile it as a + module, say M here and read Documentation/modules.txt. + +Mouse Support (not serial and bus mice) +CONFIG_MOUSE + This is for machines with a mouse which is neither a serial nor a + bus mouse. Examples are PS/2 mice (such as the track balls on some + laptops) and some digitizer pads. Most people have a regular serial + MouseSystem or 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 from + http://metalab.unc.edu/mdw/linux.html#howto . This HOWTO contains + information about all non-serial mice, not just bus mice. If you have a laptop, you either have to check the documentation or experiment a bit to find out whether the trackball is a serial mouse @@ -8720,13 +9250,12 @@ the questions about non-serial mice. If unsure, say Y. Logitech busmouse support -CONFIG_BUSMOUSE +CONFIG_LOGIBUSMOUSE Logitech mouse connected to a proprietary interface card. It's generally a round connector with 9 pins. Note that the newer mice 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + you don't need this option. You want to read the Busmouse-HOWTO , + available from http://metalab.unc.edu/mdw/linux.html#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), @@ -8745,29 +9274,27 @@ particular, the C&T 82C710 mouse on TI Travelmates is a PS/2 mouse. 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + in detail in the Busmouse-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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://metalab.unc.edu/pub/Linux/system/Daemons) solves this - problem, or you can get the "mconv" utility also from metalab. + ftp://metalab.unc.edu/pub/Linux/system/mouse ) solves this + problem, or you can get the "mconv2" utility from the same location. 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + doesn't work. Read the Busmouse-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . PC110 digitizer pad support CONFIG_PC110_PAD This drives the digitizer pad on the IBM PC110 palmtop (see - http://toy.cabi.net; to browse the WWW, you need to have access to a - machine on the Internet that has a program like lynx or - netscape). It can turn the digitizer pad into a PS/2 mouse emulation - with tap gestures or into an absolute pad. + http://toy.cabi.net ). It can turn the digitizer pad into a PS/2 + mouse emulation with tap gestures or into an absolute pad. If you want to compile this as a module ( = code which can be inserted in and removed from the running kernel whenever you want), @@ -8778,8 +9305,8 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + you have, say Y and read the Busmouse-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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 @@ -8791,12 +9318,25 @@ say M here and read Documentation/modules.txt. The module will be called msbusmouse.o. +Apple Desktop Bus mouse support +CONFIG_ADBMOUSE + Say Y here if you have this type of bus mouse (4 pin connector) as + is common on Macintoshes. You may want to read the Busmouse-HOWTO, + available from http://metalab.unc.edu/mdw/linux.html#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), + say M here and read Documentation/modules.txt. The module will be + called adbmouse.o. + ATIXL busmouse support 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://metalab.unc.edu/pub/Linux/docs/HOWTO. + ATI video card. Say Y if you have one of those. Note however that + most mice by ATI are actually Microsoft busmice; you should say Y to + "Microsoft busmouse support" above if you have one of those. Read + the Busmouse-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#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), @@ -8806,11 +9346,6 @@ If you are unsure, say N and read the HOWTO nevertheless: it will tell you what you have. -Support for PowerMac ADB mouse -CONFIG_ADBMOUSE - If you have an ADB mouse (4 pin connector) as is common on - Macintoshes, say Y here. - QIC-02 tape support CONFIG_QIC02_TAPE If you have a non-SCSI tape drive like that, say Y. Or, if you want @@ -8860,13 +9395,12 @@ Note that the Ftape-HOWTO is out of date (sorry) and documents the older version 2.08 of this software but still contains useful information. There is a web page with more recent documentation at - http://www-math.math.rwth-aachen.de/~LBFM/claus/ftape/ . This page + http://www.math1.rwth-aachen.de/~heine/ftape/ . This page always contains the latest release of the ftape driver and useful information (backup software, ftape related patches and - documentation, FAQ). (To browse the WWW, you need to have access to - a machine on the Internet that has a program like lynx or netscape.) - Note that the file system interface has changed quite a bit compared - to previous versions of ftape. Please read Documentation/ftape.txt. + documentation, FAQ). Note that the file system interface has changed + quite a bit compared to previous versions of ftape. Please read + Documentation/ftape.txt. The file system interface for ftape CONFIG_ZFTAPE @@ -8897,8 +9431,7 @@ most important changes in the file system interface compared to previous versions of ftape. The ftape home page http://www-math.math.rwth-aachen.de/~LBFM/claus/ftape/ contains - further information (to browse the WWW, you need to have access to a - machine on the Internet that has a program like lynx or netscape). + further information. IMPORTANT NOTE: zftape can read archives created by previous versions of ftape and provide file mark support (i.e. fast skipping @@ -9120,6 +9653,17 @@ speed. If unsure, leave this disabled, i.e. leave it at 2000 bits/sec. +Direct Rendering Manager (XFree86 DRI support) +CONFIG_DRM + Kernel-level support for the Direct Rendering Infrastructure (DRI) + introduced in XFree86 4.x. These modules provide support for + synchronization, security, and DMA transfers. Select the module that + provides support for your graphics card. + +3dlabs GMX 2000 Direct Rendering Driver (XFree86 DRI support) +CONFIG_DRM_GAMMA + Choose M here if you have a 3dlabs GMX 2000 graphics card. + MTRR control and configuration CONFIG_MTRR On Intel P6 family processors (Pentium Pro, Pentium II and later) @@ -9136,11 +9680,13 @@ The Cyrix 6x86, 6x86MX and M II processors have Address Range Registers (ARRs) which provide a similar functionality to MTRRs. For - these, the ARRs are used to emulate the MTRRs. + these, the ARRs are used to emulate the MTRRs, which means that it + makes sense to say Y here for these processors as well. The AMD K6-2 (stepping 8 and above) and K6-3 processors have two - MTRRs. These are supported. - + MTRRs. The Centaur C6 (WinChip) has 8 MCRs, allowing + write-combining. All of these processors are supported by this code. + The Centaur C6 (WinChip) has 8 MCRs, allowing write-combining. These are supported. @@ -9161,13 +9707,13 @@ Zilog serial support CONFIG_SUN_ZS - If you are asked this question, something is wrong with config scripts. - Zilog serial driver is always enabled in sparc architecture. + This driver does not exist at this point, so you might as well + say N. Double Talk PC internal speech card support CONFIG_DTLK This driver is for the DoubleTalk PC, a speech synthesizer - manufactured by RC Systems (http://www.rcsys.com/). It is also + manufactured by RC Systems (http://www.rcsys.com/ ). It is also called the `internal DoubleTalk'. If you want to compile this as a module ( = code which can be inserted in and removed from the running kernel whenever you want), say M here and read @@ -9175,7 +9721,7 @@ Siemens R3964 serial protocol support CONFIG_R3964 - This driver allows syncronous communication with devices using the + This driver allows synchronous communication with devices using the Siemens R3964 packet protocol. Unless you are dealing with special hardware like PLCs, you are unlikely to need this. @@ -9188,12 +9734,11 @@ Applicom intelligent fieldbus card support CONFIG_APPLICOM - This driver provides the kernel-side support for the intelligent + This driver provides the kernel-side support for the intelligent fieldbus cards made by Applicom International. More information about these cards can be found on the WWW at the address - http://www.applicom-int.com/ (to browse the WWW, you need to have - access to a machine on the Internet that has a program like lynx - or netscape), or by email from David Woodhouse . + http://www.applicom-int.com/ , or by email from David Woodhouse + . 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 @@ -9212,8 +9757,8 @@ receive notification of APM "events" (e.g., battery status change). Supporting software is available; for more information, read the - Battery Powered Linux mini-HOWTO, available via FTP (user: - anonymous) from ftp://metalab.unc.edu/pub/Linux/docs/HOWTO/mini. + Battery Powered Linux mini-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . This driver does not spin down disk drives (see the hdparm(8) manpage ("man 8 hdparm") for that), and it doesn't turn off @@ -9228,9 +9773,7 @@ If you are running Linux on a laptop, you may also want to read the Linux Laptop home page on the WWW at - http://www.cs.utexas.edu/users/kharker/linux-laptop/ (to browse the - WWW, you need to have access to a machine on the Internet that has a - program like lynx or netscape). + http://www.cs.utexas.edu/users/kharker/linux-laptop/ . Generally, if you don't have a battery in your machine, there isn't much point in using this driver and you should say N. If you get @@ -9257,6 +9800,11 @@ 11) exchange RAM chips 12) exchange the motherboard. + This driver is also available as a module ( = code which can be + inserted in and removed from the running kernel whenever you want). + If you want to compile it as a module, say M here and read + Documentation/modules.txt. The module will be called apm.o. + Ignore USER SUSPEND CONFIG_APM_IGNORE_USER_SUSPEND This option will ignore USER SUSPEND requests. On machines with a @@ -9307,11 +9855,10 @@ 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://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 - BIOS implementations. + ftp://metalab.unc.edu/pub/Linux/system/daemons/init/ 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 BIOS implementations. Ignore multiple suspend/standby events CONFIG_APM_IGNORE_MULTIPLE_SUSPEND @@ -9367,7 +9914,7 @@ The watchdog is usually used together with the watchdog daemon which is available via FTP (user: anonymous) from - ftp://tsx-11.mit.edu/pub/linux/sources/sbin/. This daemon can also + ftp://tsx-11.mit.edu/pub/linux/sources/sbin/ . This daemon can also monitor NFS connections and can reboot the machine when the process table is full. @@ -9425,8 +9972,7 @@ and if it does, it reboots your computer after a certain amount of time. This driver is like the WDT501 driver but for different hardware. Please read Documentation/pcwd-watchdog.txt. The PC - watchdog cards can be ordered from http://www.berkprod.com. Some - example rc.local files are available from ftp://ftp.bitgate.com. + watchdog cards can be ordered from http://www.berkprod.com . This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -9500,17 +10046,6 @@ The module will be called nvram.o. If you want to compile it as a module, say M here and read Documentation/modules.txt. -Atomwide Serial Support -CONFIG_ATOMWIDE_SERIAL - If you have an Atomwide Serial card for an Acorn system, say Y to - this option. The driver can handle 1, 2, or 3 port cards. - If unsure, say N - -The Serial Port Dual Serial Port -CONFIG_DUALSP_SERIAL - If you have the Serial Port's dual serial card for an Acorn system, - say Y to this option. If unsure, say N - Joystick support CONFIG_JOYSTICK If you have a joystick, you can say Y here to enable generic @@ -9616,32 +10151,37 @@ NetWinder Button CONFIG_NWBUTTON - If you enable this driver and create a character device node - /dev/nwbutton with major and minor numbers 10 and 158 ("man mknod"), - then every time the orange button is pressed a number of times, the - number of times the button was pressed will be written to that device. - This is most useful for applications, as yet unwritten, which perform - actions based on how many times the button is pressed in a row. - Do not hold the button down for too long, as the driver does not alter - the behaviour of the hardware reset circuitry attached to the button; - it will still execute a hard reset if the button is held down for - longer than approximately five seconds. + If you say Y here and create a character device node /dev/nwbutton + with major and minor numbers 10 and 158 ("man mknod"), then every + time the orange button is pressed a number of times, the number of + times the button was pressed will be written to that device. + + This is most useful for applications, as yet unwritten, which + perform actions based on how many times the button is pressed in a + row. + + Do not hold the button down for too long, as the driver does not + alter the behaviour of the hardware reset circuitry attached to the + button; it will still execute a hard reset if the button is held + down for longer than approximately five seconds. + This driver is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). If you want to compile it as a module, say M here and read Documentation/modules.txt. The module will be called nwbutton.o. + Most people will answer Y to this question and "Reboot Using Button" below to be able to initiate a system shutdown from the button. Reboot Using Button CONFIG_NWBUTTON_REBOOT - If you enable this option, then you will be able to initiate a system + If you say Y here, then you will be able to initiate a system shutdown and reboot by pressing the orange button a number of times. - The number of presses to initiate the shutdown is two by default, but - this can be altered by modifying the value of NUM_PRESSES_REBOOT in - nwbutton.h and recompiling the driver or, if you compile the driver as - a module, you can specify the number of presses at load time with - "insmod button reboot_count=". + The number of presses to initiate the shutdown is two by default, + but this can be altered by modifying the value of NUM_PRESSES_REBOOT + in nwbutton.h and recompiling the driver or, if you compile the + driver as a module, you can specify the number of presses at load + time with "insmod button reboot_count=". Sound card support CONFIG_SOUND @@ -9650,29 +10190,27 @@ 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://metalab.unc.edu/pub/Linux/docs/HOWTO. General - information about the modular sound system is contained in the files + You want to read the Sound-HOWTO, available from + http://metalab.unc.edu/mdw/linux.html#howto . General information + about the modular sound system is contained in the files Documentation/sound/Introduction. The file Documentation/sound/README.OSS contains some slightly outdated but still useful information as well. If you have a PnP sound card and you want to configure it at boot time using the ISA PnP tools (read - http://www.roestock.demon.co.uk/isapnptools/ (to browse the WWW, you - need to have access to a machine on the Internet that has a program - like lynx or netscape)), then you need to compile the sound card - support as a module ( = code which can be inserted in and removed - from the running kernel whenever you want) and load that module - after the PnP configuration is finished. To do this, say M here and - read Documentation/modules.txt as well as + http://www.roestock.demon.co.uk/isapnptools/ ), then you need to + compile the sound card support as a module ( = code which can be + inserted in and removed from the running kernel whenever you want) + and load that module after the PnP configuration is finished. To do + this, say M here and read Documentation/modules.txt as well as Documentation/sound/README.modules; the module will be called soundcore.o. I'm told that even without a sound card, you can make your computer say more than an occasional beep, by programming the PC speaker. Kernel patches and supporting utilities to do that are in the pcsp - package, available at http://www.imladris.demon.co.uk/pcsp/. + package, available at http://www.imladris.demon.co.uk/pcsp/ . OSS sound modules CONFIG_SOUND_OSS @@ -9858,6 +10396,12 @@ have their own MSS support and saying Y to this option will cause a conflict. +SGI Visual Workstation on-board audio +CONFIG_SOUND_VWSND + Say Y or M if you have an SGI Visual Workstation and you want to + be able to use its on-board audio. Read Documentation/sound/visws + for more info on this driver's capabilities. + Ensoniq Soundscape support CONFIG_SOUND_SSCAPE Answer Y if you have a sound card based on the Ensoniq SoundScape @@ -10058,8 +10602,8 @@ Say Y here if you have a Sound Blaster SB32, AWE32-PnP, SB AWE64 or similar sound card. See Documentation/sound/README.awe, Documentation/sound/AWE32 and the Soundblaster-AWE mini-HOWTO, - available via FTP (user: anonymous) from - ftp://metalab.unc.edu/pub/Linux/docs/HOWTO/mini for more info. + available from http://metalab.unc.edu/mdw/linux.html#howto for more + info. Gallant's Audio Excel DSP 16 support (SC-6000 and SC-6600) CONFIG_AEDSP16 @@ -10101,9 +10645,9 @@ 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'. + 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 @@ -10157,12 +10701,6 @@ you compiled aedsp16.o as a module you can specify this parameter as 'mpu_irq=NN'. -SGI Visual Workstation on-board audio -CONFIG_SOUND_VWSND - Say Y or M if you have an SGI Visual Workstation and you want to - be able to use its on-board audio. Read Documentation/sound/visws - for more info on this driver's capabilities. - Ensoniq ES1370 based PCI sound cards CONFIG_SOUND_ES1370 Say Y or M if you have a PCI sound card utilizing the Ensoniq @@ -10174,10 +10712,6 @@ This driver differs slightly from OSS/Free, so PLEASE READ Documentation/sound/es1370. -Joystick support at boot time -CONFIG_SOUND_ES1370_JOYPORT_BOOT - Say Y here to use the joystick port of your sound card. - Ensoniq ES1371 based PCI sound cards CONFIG_SOUND_ES1371 Say Y or M if you have a PCI sound card utilizing the Ensoniq @@ -10188,19 +10722,6 @@ models are either ES1370 or ES1371 based. This driver differs slightly from OSS/Free, so PLEASE READ Documentation/sound/es1371. -Joystick support at boot time -CONFIG_SOUND_ES1371_JOYPORT_BOOT - Say Y here to use the joystick port of your sound card. - -Gameport I/O-range selection -CONFIG_SOUND_ES1371_GAMEPORT - Select the I/O-range of the gameport on a ES1371 based sound card. - 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 sound card. - ESS Solo1 based PCI sound cards (eg. SC1938) CONFIG_SOUND_ESSSOLO1 Say Y or M if you have a PCI sound card utilizing the ESS Technology @@ -10263,9 +10784,7 @@ conversations while downloading stuff. It only works if your computer is equipped with an ISDN card and both you and your service provider purchased an ISDN line from the phone company. For details, - read http://alumni.caltech.edu/~dank/isdn/ on the WWW. (To browse - the WWW, you need to have access to a machine on the Internet that - has a program like lynx or netscape.) + read http://alumni.caltech.edu/~dank/isdn/ on the WWW. This driver allows you to use an ISDN-card for networking connections and as dialin/out device. The isdn-tty's have a built in @@ -10325,15 +10844,18 @@ CONFIG_ISDN_DIVERSION This option allows you to use some supplementary diversion services in conjunction with the HiSax driver on an EURO/DSS1 - line. Supported options are CD (call deflection), CFU (Call - forward unconditional), CFB (Call forward when busy) and CFNR - (call forward not reachable). - Additionally the actual CFU, CFB and CFNR state may be - interrogated. The use of CFU, CFB, CFNR and interrogation may - be limited to some countries. The keypad protocol is still not - implemented. - CD should work in all countries if this service has been sub- - scribed. + line. + + Supported options are CD (call deflection), CFU (Call forward + unconditional), CFB (Call forward when busy) and CFNR (call forward + not reachable). Additionally the actual CFU, CFB and CFNR state may + be interrogated. + + The use of CFU, CFB, CFNR and interrogation may be limited to some + countries. The keypad protocol is still not implemented. CD should + work in all countries if the service has been subscribed to. + + Please read the file Documentation/isdn/README.diversion. ICN 2B and 4B support CONFIG_ISDN_DRV_ICN @@ -10557,32 +11079,30 @@ can be inserted in and removed from the running kernel whenever you want, details in Documentation/modules.txt); the module will be called sc.o. See Documentation/isdn/README.sc and - http://www.spellcast.com for more information (to browse the WWW, - you need to have access to a machine on the Internet that has a - program like lynx or netscape). + http://www.spellcast.com for more information. Eicon.Diehl active card support CONFIG_ISDN_DRV_EICON Say Y here if you have an Eicon active ISDN card. In order to use this card, additional firmware is necessary, which has to be loaded - into the card using the eiconctrl utility which is part of the latest - isdn4k-utils package. Please read the file + into the card using the eiconctrl utility which is part of the + latest isdn4k-utils package. Please read the file Documentation/isdn/README.eicon for more information. Eicon old-type card support CONFIG_ISDN_DRV_EICON_ISA - Say Y here if you have an old-type Eicon active ISDN card. In order to - use this card, additional firmware is necessary, which has to be loaded - into the card using the eiconctrl utility which is part of the latest - isdn4k-utils package. Please read the file + Say Y here if you have an old-type Eicon active ISDN card. In order + to use this card, additional firmware is necessary, which has to be + loaded into the card using the eiconctrl utility which is part of + the latest isdn4k-utils package. Please read the file Documentation/isdn/README.eicon for more information. Support AT-Fax Class 2 commands CONFIG_ISDN_TTY_FAX If you say Y here, the modem-emulator will support a subset of the Fax Class 2 commands. Using a getty with fax-support - (mgetty+sendfax, hylafax), you will be able to use your Linux box - as an ISDN-fax-machine. This must be supported by the lowlevel driver + (mgetty+sendfax, hylafax), you will be able to use your Linux box as + an ISDN-fax-machine. This must be supported by the lowlevel driver also. See Documentation/isdn/README.fax for more information. AVM-B1 with CAPI2.0 support @@ -10590,12 +11110,10 @@ This enables support for the AVM B1 ISDN networking cards. In addition, a CAPI (Common ISDN Application Programming Interface, a standard making it easy for programs to access ISDN hardware, see - http://www.capi.org/; to browse the WWW, you need to have access to - a machine on the Internet that has a program like lynx or netscape) - interface for this card is provided. In order to use this card, - additional firmware is necessary, which has to be downloaded into - the card using a utility which is distributed separately. Please - read the file Documentation/isdn/README.avmb1. + http://www.capi.org/ ) interface for this card is provided. In order + to use this card, additional firmware is necessary, which has to be + downloaded into the card using a utility which is distributed + separately. Please read the file Documentation/isdn/README.avmb1. This code is also available as a module ( = code which can be inserted in and removed from the running kernel whenever you want). @@ -10620,9 +11138,8 @@ CONFIG_AP1000 This enables support for a SPARC based parallel multi-computer called AP1000+. For details on our efforts to port Linux to this - machine see http://cap.anu.edu.au/cap/projects/linux (to browse the - WWW, you need to have access to a machine on the Internet that has a - program like lynx or netscape) or mail to hackers@cafe.anu.edu.au + machine see http://cap.anu.edu.au/cap/projects/linux or mail to + hackers@cafe.anu.edu.au Support for Sun4 architecture CONFIG_SUN4 @@ -10648,12 +11165,11 @@ Mostek real time clock support CONFIG_SUN_MOSTEK_RTC The Mostek RTC chip is used on all knows Sun computers except - some JavaStation-s. For a JavaStation you need to say Y both here - and to CONFIG_RTC. + some JavaStations. For a JavaStation you need to say Y both here + and to "Enhanced Real Time Clock Support". Say Y here unless you are building a special purpose kernel. -# #Siemens SAB82532 serial support #CONFIG_SAB82532 ### @@ -10700,13 +11216,13 @@ Sun 3 support CONFIG_SUN3 - This option enables support for the Sun 3 series of workstations. - Be warned that this support is very experimental. You will also - want to say Y to 68020 support and N to the other processors below. - Currently, it is not possible to build a kernel with support for - the Sun 3 and and something else, so make sure you have said N to - all the other machines. This option does not support the sun3x series - of machines (the Sun 3/80 and 3/460). If you don't want to compile a + This option enables support for the Sun 3 series of workstations. Be + warned that this support is very experimental. You will also want to + say Y to 68020 support and N to the other processors below. + Currently, it is not possible to build a kernel with support for the + Sun 3 and something else, so make sure you have said N to all the + other machines. This option does not support the sun3x series of + machines (the Sun 3/80 and 3/460). If you don't want to compile a kernel for a Sun 3, say N. 68020 support @@ -10793,9 +11309,10 @@ Note that even if you say N here, you can still use your expansion cards. If in doubt, say Y. +Amiga 1200/600 PCMCIA support CONFIG_AMIGA_PCMCIA - Include support in the kernel for pcmcia on Amiga 1200 and Amiga 600. - If you intend to use pcmcia cards say Y; otherwise say N. + Include support in the kernel for pcmcia on Amiga 1200 and Amiga + 600. If you intend to use pcmcia cards say Y; otherwise say N. Amiga GSP (TMS340x0) support CONFIG_AMIGA_GSP @@ -11177,14 +11694,6 @@ 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 - partitioned on an MS-DOS system. This may be useful if you are - sharing a hard disk between i386 and m68k Linux boxes, for example. - Say Y if you need this feature; users who are only using their - system-native partitioning scheme can say N here. - Processor Type CONFIG_6xx There are two types of PowerPC chips supported. The more common @@ -11267,7 +11776,7 @@ Support for audio/video capture and overlay devices and FM radio cards. The exact capabilities of each device vary. User tools for this are available from - ftp://ftp.uk.linux.org/pub/linux/video4linux. + ftp://ftp.uk.linux.org/pub/linux/video4linux . If you are interested in writing a driver for such an audio/video device or user software interacting with such a driver, please read @@ -11278,17 +11787,6 @@ whenever you want). If you want to compile it as a module, say M here and read Documentation/modules.txt. -Direct Rendering Manager (XFree86 DRI support) -CONFIG_DRM - Kernel-level support for the Direct Rendering Infrastructure (DRI) - introduced in XFree86 4.x. These modules provide support for - synchronization, security, and DMA transfers. Select the module that - provides support for your graphics card. - -3dlabs GMX 2000 Direct Rendering Driver (XFree86 DRI support) -CONFIG_DRM_GAMMA - Choose M here if you have a 3dlabs GMX 2000 graphics card. - AIMSlab RadioTrack (aka RadioReveal) support CONFIG_RADIO_RTRACK Choose Y here if you have one of these FM radio cards, and then fill @@ -11298,13 +11796,16 @@ and are not supported by this driver. For these cards, use the RadioTrack II driver below. + If you have a GemTeks combined (PnP) sound- and radio card you must + use this driver as a module and setup the card with isapnptools. You + must also pass the module a suitable io parameter, 0x248 has been + reported to be used by these cards. + In order to control your radio card, you will need to use programs - that are compatible with the Video for Linux API. Information on + 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. More information is contained in the - file Documentation/video4linux/radiotrack.txt. + http://roadrunner.swansea.uk.linux.org/v4l.shtml . More information + is contained in the file Documentation/video4linux/radiotrack.txt. 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), @@ -11321,17 +11822,10 @@ Choose Y here if you have this FM radio card, and then fill in the port address below. - If you have GemTeks combined (PnP) sound- and radio card you must use - this driver as a module and setup the card with isapnptools. You must - also pass the module a suitable io parameter, 0x248 has been reported - to be used by these cards. - 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. + http://roadrunner.swansea.uk.linux.org/v4l.shtml . 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), @@ -11351,9 +11845,7 @@ 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. + http://roadrunner.swansea.uk.linux.org/v4l.shtml . 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), @@ -11366,6 +11858,28 @@ haven't changed the setting of jumper JP3 on the card. Removing the jumper sets the card to 0x358. +ADS Cadet AM/FM Radio Tuner Card +CONFIG_RADIO_CADET + Choose Y here if you have one of these AM/FM radio cards, 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 . + + Further documentation on this driver can be found on the WWW at + http://linux.blackhawke.net/cadet.html . + + 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-cadet.o. + +ADS Cadet AM/FM Radio Tuner Card I/O Port +CONFIG_RADIO_CADET_PORT + Enter the I/O address of the card here (most commonly 330). + SF16FMI Radio CONFIG_RADIO_SF16FMI Choose Y here if you have one of these FM radio cards, and then fill @@ -11374,9 +11888,7 @@ 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. + http://roadrunner.swansea.uk.linux.org/v4l.shtml . 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), @@ -11395,9 +11907,7 @@ 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. + http://roadrunner.swansea.uk.linux.org/v4l.shtml . 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), @@ -11433,9 +11943,7 @@ 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. + http://roadrunner.swansea.uk.linux.org/v4l.shtml . 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), @@ -11446,21 +11954,16 @@ CONFIG_RADIO_ZOLTRIX_PORT Enter the I/O port of your Zoltrix radio card. -ADS Cadet AM/FM Tuner -CONFIG_RADIO_CADET - Say Y here if this is your AM/FM radio card. - - 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. +IIC on parallel port +CONFIG_I2C_PARPORT + I2C is a simple serial bus system used in many micro controller + applications. Saying Y here will allow you to use your parallel port + as an I2C interface. 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-cadet.o + called i2c-parport.o. Miro PCM20 Radio CONFIG_RADIO_MIROPCM20 @@ -11471,9 +11974,7 @@ 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. + http://roadrunner.swansea.uk.linux.org/v4l.shtml . 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), @@ -11488,9 +11989,7 @@ 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. + http://roadrunner.swansea.uk.linux.org/v4l.shtml . 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), @@ -11516,11 +12015,11 @@ Choose Y here if you have this FM radio card, and then fill in the port address below. (TODO) - Note: This driver is in its early stages. Right now volume and frequency - control and muting works at least for me, but unfortunately i have not - found anybody who wants to use this card with linux. So if it is this - what YOU are trying to do right now, PLEASE DROP ME A NOTE!! - Rolf Offermanns (rolf@offermanns.de) + Note: This driver is in its early stages. Right now volume and + frequency control and muting works at least for me, but + unfortunately i have not found anybody who wants to use this card + with linux. So if it is this what YOU are trying to do right now, + PLEASE DROP ME A NOTE!! Rolf Offermanns (rolf@offermanns.de) In order to control your radio card, you will need to use programs that are compatible with the Video for Linux API. Information on @@ -11529,12 +12028,16 @@ 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-terratec.o. - + +# Zoran ZR36057/36060 support +# CONFIG_VIDEO_ZORAN + +# Include support for Iomega Buz +# CONFIG_VIDEO_BUZ BT848 Video For Linux CONFIG_VIDEO_BT848 @@ -11586,10 +12089,10 @@ CONFIG_BLK_CPQ_DA This is the driver for Compaq Smart Array controllers. Everyone using these boards should say Y here. - See "linux/Documentation/cpqarray.txt" for the current list of + See the file Documentation/cpqarray.txt for the current list of boards supported by this driver, and for further information on the use of this driver. - + # # ARM options # @@ -11615,24 +12118,36 @@ Include support for Intel EBSA285 CONFIG_ARCH_EBSA285 - Say Y here if you intend to run this kernel on an EBSA-285 evaluation board. Include support for the NetWinder CONFIG_ARCH_NETWINDER Say Y here if you intend to run this kernel on the NetWinder. +Maximum Physical Memory +CONFIG_1GB + Linux can use up to 2 Gigabytes (= 2^31 bytes) of physical memory. + If you are compiling a kernel which will never run on a machine with + more than 1 Gigabyte, answer "1GB" here. Otherwise, say "2GB". + + The actual amount of physical memory should be specified using a + kernel command line option such as "mem=256M". (Try "man bootparam" + or see the documentation 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 from + http://metalab.unc.edu/mdw/linux.html#howto .) + Math emulation CONFIG_NWFPE - Say Y to include the NWFPE floating point emulator in the kernel. This - is necessary to run most binaries. Linux does not currently support - floating point hardware so you need to say Y here even if your machine - has an FPA or floating point co-processor podule. + Say Y to include the NWFPE floating point emulator in the kernel. + This is necessary to run most binaries. Linux does not currently + support floating point hardware so you need to say Y here even if + your machine has an FPA or floating point co-processor podule. It is also possible to say M to build the emulator as a module (nwfpe.o) or indeed to leave it out altogether. However, unless you - know what you are doing this can easily render your machine unbootable. - Saying Y is the safe option. + know what you are doing this can easily render your machine + unbootable. Saying Y is the safe option. You may say N here if you are going to load the Acorn FPEmulator early in the bootup. @@ -11656,6 +12171,12 @@ you are concerned with the code size or don't want to see these messages. +Build Tools Selection +CONFIG_BINUTILS_NEW + Say Y here if and only if you're using GCC 2.8.1/EGCS with a + binutils version >= 2.8.1 to compile the kernel (check with "gcc + --version" and "ld -v"). + Compile kernel with frame pointer CONFIG_FRAME_POINTER If you say Y here, the resulting kernel will be slightly larger and @@ -11664,10 +12185,10 @@ User fault debugging CONFIG_DEBUG_USER - When a user program crashes due to an exception, the kernel can print - a brief message explaining what the problem was. This is sometimes - helpful for debugging but serves no purpose on a production system. - Most people should say N here. + When a user program crashes due to an exception, the kernel can + print a brief message explaining what the problem was. This is + sometimes helpful for debugging but serves no purpose on a + production system. Most people should say N here. Include gdb debugging information in kernel binary CONFIG_DEBUG_INFO @@ -11675,25 +12196,27 @@ `vmlinux' binary image. This is handy if you want to use gdb or addr2line to debug the kernel. It has no impact on the in-memory footprint of the running kernel but it can increase the amount of - time and disk space needed for compilation. If in doubt say N. + time and disk space needed for compilation of the kernel. If in + doubt say N. Split initialisation functions into discardable section CONFIG_TEXT_SECTIONS - Normally code that is only used during initialisation is collected - into a special area of the kernel so that it can be discarded and - the memory reclaimed when initialisation is complete. In addition, - if the kernel you wish to build is able to run on multiple - architectures, it allows the unused code to be discarded. Some - versions of binutils, however, have a bug that causes the kernel - to crash during startup when this option is enabled. Say Y unless - you experience problems that you suspect may be caused by this. + If you say Y here, kernel code that is only used during + initialisation is collected into a special area of the kernel so + that it can be discarded and the memory reclaimed when + initialisation is complete. In addition, if the kernel you wish to + build is able to run on multiple architectures, it allows the unused + code to be discarded. Some versions of binutils, however, have a bug + that causes the kernel to crash during startup when this option is + enabled. Say Y unless you experience problems that you suspect may + be caused by this. Disable pgtable cache CONFIG_NO_PGT_CACHE - Normally the kernel maintains a `quicklist' of preallocated pagetable - structures in order to increase performance. On machines with very - few pages this may however be a loss. Say Y here to disable the pgtable - cache. + Normally the kernel maintains a `quicklist' of preallocated + pagetable structures in order to increase performance. On machines + with very few pages this may however be a loss. Say Y here to + disable the pgtable cache. RISC OS personality CONFIG_ARTHUR @@ -11709,16 +12232,17 @@ 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) + memory size and the root device (e.g., mem=64M root=/dev/nfs) Hardware alignment trap CONFIG_ALIGNMENT_TRAP - ARM processors can not fetch/store information which is not naturally - aligned on the bus, ie, a 4 byte fetch must start at an address divisable - by 4. On 32-bit ARM processors, these instructions can be emulated in - software with a severe performance impact. This is necessary for correct - operation of some network protocols. With an IP-only configuration - it is safe to say N, otherwise say Y. + ARM processors can not fetch/store information which is not + naturally aligned on the bus, i.e., a 4 byte fetch must start at an + address divisible by 4. On 32-bit ARM processors, these non-aligned + fetch/store instructions will be emulated in software if you say + here, which has a severe performance impact. This is necessary for + correct operation of some network protocols. With an IP-only + configuration it is safe to say N, otherwise say Y. 21285 serial port support CONFIG_SERIAL_21285 @@ -11729,32 +12253,32 @@ Console on 21285 serial port CONFIG_SERIAL_21285_CONSOLE If you have enabled the serial port on the 21285 footbridge you can - make it the console by answering 'Y' to this option. + make it the console by answering Y to this option. Footbridge Mode CONFIG_HOST_FOOTBRIDGE The 21285 Footbridge chip can operate in either `host mode' or `add-in' mode. Say Y if your 21285 is in host mode, and therefore - is the configuration master, otherwise say N. This must not be - set to 'Y' if the card is used in 'add-in' mode. + is the configuration master, otherwise say N. This must not be + set to Y if the card is used in 'add-in' mode. -MFM harddisk support +MFM hard disk support CONFIG_BLK_DEV_MFM Support the MFM hard drives on the Acorn Archimedes both on-board the A4x0 motherboards and via the Acorn MFM podules. - Drives upto 64MB are supported. If you haven't got one of these - machines or drives just say 'N'. + Drives up to 64MB are supported. If you haven't got one of these + machines or drives just say N. Old Archimedes floppy (1772) support CONFIG_BLK_DEV_FD1772 Support the floppy drive on the Acorn Archimedes (A300, A4x0, A540, R140 and R260) series of computers; it supports only 720K floppies at the moment. If you don't have one of these machines just answer - 'N'. + N. Autodetect hard drive geometry CONFIG_BLK_DEV_MFM_AUTODETECT - If you answer 'Y' the MFM code will attempt to automatically detect + If you answer Y, the MFM code will attempt to automatically detect the cylinders/heads/sectors count on your hard drive. WARNING: This sometimes doesn't work and it also does some dodgy stuff which potentially might damage your drive. @@ -11769,12 +12293,10 @@ some user-space utilities like the irmanager and probably irattach as well. For more information, see the file Documentation/networking/irda.txt. You also want to read the - IR-HOWTO, available from - ftp://metalab.unc.edu/pub/Linux/docs/HOWTO. + IR-HOWTO, available at http://metalab.unc.edu/mdw/linux.html#howto . This support is also available as a module. If you want to compile - it as a module, say M here and read Documentation/modules.txt. The - module will be called + it as a module, say M here and read Documentation/modules.txt. IrDA Cache last LSAP CONFIG_IRDA_CACHE_LAST_LSAP @@ -11878,6 +12400,17 @@ If unsure, say Y. +SiS5513 chipset support +CONFIG_BLK_DEV_SIS5513 + This driver ensures (U)DMA support for SIS5513 chipset based + mainboards. SiS620/530 UDMA mode 4, SiS5600/5597 UDMA mode 2, all + other DMA mode 2 limited chipsets are unsupported to date. + + If you say Y here, you need to say Y to "Use DMA by default when + available" as well. + + Please read the comments at the top of drivers/block/sis5513.c + Winbond W83977AF IrDA Device Driver CONFIG_WINBOND_FIR Say Y here if you want to build IrDA support for the Winbond @@ -11945,15 +12478,6 @@ by IrTTY. To activate support for Greenwich dongles you will have to insert "irattach -d girbil" in the /etc/irda/drivers script. -Adaptec Airport 1000 and 2000 dongle -CONFIG_AIRPORT_DONGLE - Say Y here if you want to build support for the Adaptec Airport 1000 - and 2000 dongles. If you want to compile it as a module, say M here - and read Documentation/modules.txt. The Airport dongle attaches to - the normal 9-pin serial port connector, and can currently only be - used by IrTTY. To activate support for Airport dongles you will have - to insert "irattach -d airport" in the /etc/irda/drivers script. - Parallax Litelink dongle CONFIG_LITELINK_DONGLE Say Y here if you want to build support for the Parallax Litelink @@ -11963,6 +12487,16 @@ by IrTTY. To activate support for Parallax dongles you will have to insert "irattach -d litelink" in the /etc/irda/drivers script. +Adaptec Airport 1000 and 2000 dongle +CONFIG_AIRPORT_DONGLE + Say Y here if you want to build support for the Adaptec Airport 1000 + and 2000 dongles. If you want to compile it as a module, say M here + and read Documentation/modules.txt. The module will be called + airport.o. The Airport dongle attaches to the normal 9-pin serial + port connector, and can currently only be used by IrTTY. To activate + support for Airport dongles you will have to insert "irattach -d + airport" 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 @@ -12041,104 +12575,10 @@ boards from BVM Ltd. Everyone using one of these boards should say Y here. -Universal Serial Bus (USB) Support (Experimental) -CONFIG_USB - This will enable support for the Universal Serial Bus (USB). USB - allows you to connect up to 127 external devices such as keyboards, - mice, printers and modems to your computer through a USB connector. - This code can also be built as a module (i.e. code outside the - kernel that can be added and removed at runtime), consult - Documentation/modules.txt for more information. - -UHCI (intel PIIX4 and others) support -CONFIG_USB_UHCI - The UHCI is the USB host controller for many computers, and is built - into all recent boards with intel PCI chipsets. This driver is - needed for these motherboards to support USB. - -OHCI (compaq and some others) support -CONFIG_USB_OHCI - The OHCI (Open Host Controller Interface) is the USB host controller - on most non-Intel architectures, several USB-adding PCI cards, and - is on several x86 compatibles with non-Intel chipsets. This driver - is needed for these motherboards to support USB. There is presently - two OHCI drivers in development. Say 'N' here if you would like to - compile the other OHCI driver into the linux kernel. - -OHCI-HCD (other OHCI opt. Virt. Root Hub) support -CONFIG_USB_OHCI_HCD - The OHCI (Open Host Controller Interface) is the USB host controller - on most non-Intel architectures, several USB-adding PCI cards, and - is on several x86 compatibles with non-Intel chipsets. This driver - is needed for these motherboards to support USB. There is presently - two OHCI drivers in development. - -USB hub support -CONFIG_USB_HUB - To expand beyond the USB ports on the computer, a device called a - hub is used. This driver supports hubs, allowing them to be used. - Say 'Y'. - -USB mouse support -CONFIG_USB_MOUSE - This driver allows mice to work under the USB stack. It currently - patches into /dev/ps2aux, although it does not require the ps2 - mouse code to be included in the kernel as well. - -USB keyboard support -CONFIG_USB_KBD - This driver allows USB keyboards to work under the USB stack. - -USB audio parsing support (Preliminary) -CONFIG_USB_AUDIO - This driver will eventually handle audio devices, such - as USB speakers. - -USB Communications Device Class (ACM) support (Preliminary) -CONFIG_USB_ACM - This driver handles devices which support the Abstract Control Model, - a subtype of the USB Communications Device Class. This includes many - USB-based modems and ISDN adapters. Add special files with: - mknod /dev/ttyACM0 c 166 0 - mknod /dev/ttyACM1 c 166 1 - mknod /dev/ttyACM2 c 166 2 - mknod /dev/ttyACM3 c 166 3 - -USB Printer Device Class support (Preliminary) -CONFIG_USB_PRINTER - This is a generic driver for USB printers. - -USS720 parport driver -CONFIG_USB_USS720 - This driver is for USB parallel port adapters that use the - Lucent Technologies USS-720 chip. - - The chip has two modes: automatic mode and manual mode. - In automatic mode, it looks like a standard USB printer. Only - Printers may be connected to the USS-720 in this mode. - The generic USB printer driver (CONFIG_USB_PRINTER, above) - may be used in that mode. - - Manual mode is not limited to printers, any parallel port - device should work. This driver utilizes manual mode. - Note however that some operations are three orders of a magnitude - slower than on a PCI/ISA Parallel Port, so timing critical - applications might not work. - - Say Y or M if you own an USS-720 USB->Parport cable and - intend to connect anything other than a printer to it. - -USB /proc filesystem entry support (Preliminary) -CONFIG_USB_PROC - This reports USB drivers and devices in the /proc filesystem. - Entries are located in /proc/bus/usb. - Note that you must enable support for the proc filesystem - for this to work. - Support for user-space parallel port device drivers CONFIG_PPDEV Saying Y to this adds support for /dev/parport device nodes. This - is needed for programs that want low-level access to the parallel + is needed for programs that want portable access to the parallel port, for instance deviceid (which displays Plug-and-Play device IDs) and vlp (which makes a Linux computer act as though it's a printer). @@ -12147,10 +12587,16 @@ It is safe to say N to this -- it is not needed for normal printing or parallel port CD-ROM/disk support. + This support is also available as a module. If you want to compile + it as a module, say M here and read Documentation/modules.txt. The + module will be called ppdev.o. + + If unsure, say N. + Kernel httpd acceleration (experimental) CONFIG_KHTTPD The kernel httpd acceleration daemon (kHTTPd) is a (limited) - webserver build into the kernel. It is limited since it can only + web server build into the kernel. It is limited since it can only serve files from the filesystem. Saying "M" here builds the kHTTPd module; this is NOT enough to have a working kHTTPd. For safety reasons, the module has to be activated by doing a @@ -12161,7 +12607,6 @@ The kHTTPd is experimental. Be careful when using it on a production machine. Also note that kHTTPd doesn't support virtual servers yet. - # # A couple of things I keep forgetting: # capitalize: AppleTalk, Ethernet, DOS, DMA, FAT, FTP, Internet, @@ -12302,7 +12747,7 @@ # LocalWords: KERNNAME kname ktype kernelname Kerneltype KERNTYPE Alt RX mdafb # LocalWords: dataless kerneltype SYSNAME Comtrol Rocketport palmtop fbset EGS # LocalWords: nvram SYSRQ SysRq PrintScreen sysrq NVRAMs NvRAM Shortwave RTTY -# LocalWords: hayes TX TMOUT +# LocalWords: Sitor Amtor Pactor GTOR hayes TX TMOUT JFdocs BIGMEM DAC IRQ's # LocalWords: IDEPCI IDEDMA idedma PDC pdc TRM trm raidtools luthien nuclecu # LocalWords: unam mx miguel koobera uic EMUL solaris pp ieee lpsg co DMAs TOS # LocalWords: BLDCONFIG preloading jumperless BOOTINIT modutils multipath GRE @@ -12388,5 +12833,40 @@ # LocalWords: BVME BVME WRITETHROUGH copyback writethrough fwmark syncookie tu # LocalWords: alphalinux GOBIOS csn chemnitz nat ACARD AMI MegaRAID megaraid # LocalWords: QNXFS ISI isicom xterms Apollos VPN RCPCI rcpci sgi visws pcmcia -# LocalWords: IrLPT UIRCC Tecra - +# LocalWords: IrLPT UIRCC Tecra Strebel jstrebel suse Eichwalder ke INI INIA +# LocalWords: FCP qlogicfc sym isapnp DTLK DoubleTalk rcsys dtlk DMAP SGIVW ar +# LocalWords: dmabuf EcoRadio MUTEFREQ GIrBIL girbil tepkom vol mha diplom PQS +# LocalWords: bmac Microgate SyncLink synclink hdlc excl ioaddr Tane tanep TCQ +# LocalWords: PDS SMALLDOS charsets bigfoot kernelfr mcs cls fw rsvp SKnet sk +# LocalWords: SKMC USB UHCI OHCI intel compaq usb ohci HCD Virt Compaq's hcd +# LocalWords: VROOTHUB KBD ARRs MCRs NWBUTTON nwbutton NUM WaveArtist APNE cpu +# LocalWords: apne blackhawke PlanB lu mlan planb NWFPE FPA nwfpe unbootable +# LocalWords: FPEmulator ds vmlinux initialisation discardable pgtable PGT mdw +# LocalWords: quicklist pagetable arthur StrongARM podule podules Autodetect +# LocalWords: dodgy IrPORT irport Litelink litelink SuSE rtfm internet hda CY +# LocalWords: multmode DriveReady SeekComplete DriveStatusError miscompile AEC +# LocalWords: mainboard's Digital's alim FastTrak aec PIIXn piix Gayle Eyetech +# LocalWords: Catweasel IDEDOUBLER Powerbook Centris ICSIDE RapIDE OSM HDM IOP +# LocalWords: HDM's OSM's lan FibreChannel ECP autoprobe itg lbl ipmasq cjb IC +# LocalWords: bieringer Caulfield's dreamtime decnet SIOCFIGCONF SIOCGIFCONF +# LocalWords: rtnetlink Endnode Aironet Arlan Telxon ylenurme arlan ACB aeschi +# LocalWords: Sealevel sealevel Cyclom br wanconfig tarball conectiva cycsyn +# LocalWords: devel bazar cyclomx NetGear GA IBMOL Lanstreamer uhci eu efs CYZ +# LocalWords: olympic linuxtr usbcore acm EZUSB downloader EFS XFS INTR op IIC +# LocalWords: heine soundcore JavaStations JavaStation GemTeks TerraTec TODO +# LocalWords: ActiveRadio Standalone terratec Rolf Offermanns rolf offermanns +# LocalWords: Zoran ZR Buz LML CPQ DA cpqarray PPDEV deviceid vlp ppdev atyfb +# LocalWords: AcceleRAID eXtremeRAID NETFILTER Netfilter masqueraded netfilter +# LocalWords: kernelnotes Cardbus PCMCIA's CardBus clgenfb Permedia YAM MMAP +# LocalWords: mmapped ATM atm PVCs SVCs InARP ATMARP neighbour neighbours MPOA +# LocalWords: VCs ENI FPGA Tonga MMF MF UTP printks ZeitNet ZN ZATM uPD SAR PN +# LocalWords: approx NICStAR NICs ForeRunnerLE Madge Collage ATMizer Dxxxx VCI +# LocalWords: ServeRAID IPS ips ipslinux gzip BSDCOMP LZW RAYCS Interphase app +# LocalWords: Tachyon IPHASE Surfboard NextLevel SURFboard jacksonville Tigon +# LocalWords: fventuri adelphia siglercm linuxpower AceNICs Starfire starfire +# LocalWords: ISOC CPiA cpia uss ACPI UDF DirectCD udf CDRW's OSF Manx acpi +# LocalWords: Unixware cymru Computone IntelliPort Intelliport computone SI sx +# LocalWords: adbmouse DRI DRM dlabs GMX PLCs Applicom fieldbus applicom int +# LocalWords: VWSND eg ESSSOLO CFU CFNR scribed eiconctrl eicon hylafax KFPU +# LocalWords: EXTRAPREC fpu mainboards KHTTPD kHTTPd khttpd Xcelerator +# LocalWords: LOGIBUSMOUSE diff -u --recursive --new-file v2.3.19/linux/Documentation/devices.tex linux/Documentation/devices.tex --- v2.3.19/linux/Documentation/devices.tex Thu Aug 5 18:48:45 1999 +++ linux/Documentation/devices.tex Thu Oct 7 10:17:08 1999 @@ -254,11 +254,13 @@ \major{86}{}{char }{SCSI media changer} \major{87}{}{char }{Sony Control-A1 stereo control bus} \major{88}{}{char }{COMX synchronous serial card} -\major{ }{}{block}{Sixth IDE hard disk/CD-ROM interface} -\major{89}{}{char }{I$^2$C bus interface} \major{ }{}{block}{Seventh IDE hard disk/CD-ROM interface} +\major{89}{}{char }{I$^2$C bus interface} +\major{ }{}{block}{Eighth IDE hard disk/CD-ROM interface} \major{90}{}{char }{Memory Technology Device (RAM, ROM, Flash)} +\major{ }{}{block}{Ninth IDE hard disk/CD-ROM interface} \major{91}{}{char }{CAN-Bus controller} +\major{ }{}{block}{Tenth IDE hard disk/CD-ROM interface} \major{92}{}{char }{Reserved for ith Kommunikationstechnik MIC ISDN card} \major{93}{}{char }{IBM Smart Capture Card frame grabber} \major{94}{}{char }{miroVIDEO DC10/30 capture/playback device} @@ -1748,7 +1750,7 @@ \end{devicelist} \begin{devicelist} -\major{ }{}{block}{Sixth IDE hard disk/CD-ROM interface} +\major{ }{}{block}{Seventh IDE hard disk/CD-ROM interface} \minor{0}{/dev/hdm}{Master: whole disk (or CD-ROM)} \minor{64}{/dev/hdn}{Slave: whole disk (or CD-ROM)} \end{devicelist} @@ -1765,7 +1767,7 @@ \end{devicelist} \begin{devicelist} -\major{ }{}{block}{Seventh IDE hard disk/CD-ROM interface} +\major{ }{}{block}{Eighth IDE hard disk/CD-ROM interface} \minor{0}{/dev/hdo}{Master: whole disk (or CD-ROM)} \minor{64}{/dev/hdp}{Slave: whole disk (or CD-ROM)} \end{devicelist} @@ -1784,7 +1786,7 @@ \end{devicelist} \begin{devicelist} -\major{ }{}{block}{Eighth IDE hard disk/CD-ROM interface} +\major{ }{}{block}{Ninth IDE hard disk/CD-ROM interface} \minor{0}{/dev/hdq}{Master: whole disk (or CD-ROM)} \minor{64}{/dev/hdr}{Slave: whole disk (or CD-ROM)} \end{devicelist} @@ -1801,7 +1803,7 @@ \end{devicelist} \begin{devicelist} -\major{ }{}{block}{Ninth IDE hard disk/CD-ROM interface} +\major{ }{}{block}{Tenth IDE hard disk/CD-ROM interface} \minor{0}{/dev/hds}{Master: whole disk (or CD-ROM)} \minor{64}{/dev/hdt}{Slave: whole disk (or CD-ROM)} \end{devicelist} diff -u --recursive --new-file v2.3.19/linux/Documentation/devices.txt linux/Documentation/devices.txt --- v2.3.19/linux/Documentation/devices.txt Thu Aug 5 18:48:45 1999 +++ linux/Documentation/devices.txt Thu Oct 7 10:17:08 1999 @@ -1215,7 +1215,7 @@ 1 = /dev/comx1 COMX channel 1 ... - block Sixth IDE hard disk/CD-ROM interface + block Seventh IDE hard disk/CD-ROM interface 0 = /dev/hdm Master: whole disk (or CD-ROM) 64 = /dev/hdn Slave: whole disk (or CD-ROM) @@ -1227,7 +1227,7 @@ 1 = /dev/i2c1 Second I2C adapter ... - block Seventh IDE hard disk/CD-ROM interface + block Eighth IDE hard disk/CD-ROM interface 0 = /dev/hdo Master: whole disk (or CD-ROM) 64 = /dev/hdp Slave: whole disk (or CD-ROM) @@ -1241,7 +1241,7 @@ 30 = /dev/mtd15 16th MTD (rw) 31 = /dev/mtdr15 16th MTD (ro) - block Eighth IDE hard disk/CD-ROM interface + block Ninth IDE hard disk/CD-ROM interface 0 = /dev/hdq Master: whole disk (or CD-ROM) 64 = /dev/hdr Slave: whole disk (or CD-ROM) @@ -1253,7 +1253,7 @@ 1 = /dev/can1 Second CAN-Bus controller ... - block Ninth IDE hard disk/CD-ROM interface + block Tenth IDE hard disk/CD-ROM interface 0 = /dev/hds Master: whole disk (or CD-ROM) 64 = /dev/hdt Slave: whole disk (or CD-ROM) diff -u --recursive --new-file v2.3.19/linux/Documentation/kbuild/config-language.txt linux/Documentation/kbuild/config-language.txt --- v2.3.19/linux/Documentation/kbuild/config-language.txt Mon Feb 1 12:03:20 1999 +++ linux/Documentation/kbuild/config-language.txt Thu Oct 7 10:17:08 1999 @@ -1,5 +1,5 @@ Config Language Specification -21 January 1999 +28 September 1999 Michael Elizabeth Chastain, @@ -82,7 +82,10 @@ double-quoted string. If the word is unquoted or double quoted, then $-substition will be performed on the word. - A /symbol/ is a single unquoted word. + A /symbol/ is a single unquoted word. A symbol must have a name of + the form CONFIG_*. scripts/mkdep.c relies on this convention in order + to generate dependencies on individual CONFIG_* symbols instead of + making one massive dependency on include/linux/autoconf.h. A /dep/ is a dependency. Syntactically, it is a /word/. At run time, a /dep/ must evaluate to "y", "m", "n", or "". @@ -355,8 +358,8 @@ number is a legal value. Configure: implemented -Menuconfig: not implemented -Xconfig: not implemented +Menuconfig: implemented +Xconfig: implemented mconfig: implemented Example: @@ -377,8 +380,8 @@ legal value. Configure: implemented -Menuconfig: not implemented -Xconfig: not implemented +Menuconfig: implemented +Xconfig: implemented mconfig: implemented Example: @@ -394,8 +397,8 @@ are any ASCII string, except for the characters '"' and '\\'. Configure: implemented -Menuconfig: not implemented -Xconfig: not implemented +Menuconfig: implemented +Xconfig: implemented mconfig: implemented Example @@ -414,9 +417,9 @@ instead of define_bool to define tristate values. This aids in static type checking. -Configure: not implemented -Menuconfig: not implemented -Xconfig: not implemented +Configure: implemented +Menuconfig: implemented +Xconfig: implemented mconfig: implemented Example: @@ -433,22 +436,27 @@ This verb evaluates all of the dependencies in the dependency list. Any dependency which has a value of "y" does not restrict the input -range. Any dependency which has a value of "n", or which has some -other value, restricts the input range to "n". +range. Any dependency which has an empty value is ignored. +Any dependency which has a value of "n", or which has some other value, +restricts the input range to "n". Quoting dependencies is not allowed. +Using dependencies with an empty value possible is not recommended. If the input range is restricted to the single choice "n", dep_bool silently assigns "n" to /symbol/. If the input range has more than one choice, dep_bool displays /prompt/ to the user, accepts a value from the user, and assigns that value to /symbol/. -Configure: not implemented -Menuconfig: not implemented -XConfig: not implemented +Configure: implemented +Menuconfig: implemented +XConfig: implemented mconfig: implemented # not from the corpus dep_bool 'RZ1000 chipset bugfix/support' CONFIG_BLK_DEV_RZ1000 $CONFIG_PCI +Known bugs: +- Xconfig does not write "# foo is not set" to .config (as well as + "#unset foo" to autoconf.h) if command is disabled by its dependencies. === dep_hex /prompt/ /symbol/ /word/ /dep/ ... @@ -464,13 +472,15 @@ -=== dep_tristate /prompt/ /symbol /dep/ ... +=== dep_tristate /prompt/ /symbol/ /dep/ ... This verb evaluates all of the dependencies in the dependency list. -Any dependency which as a value of "y" does not restrict the input range. +Any dependency which has a value of "y" does not restrict the input range. Any dependency which has a value of "m" restricts the input range to -"m" or "n". Any dependency which has a value of "n", or which has some -other value, restricts the input range to "n". +"m" or "n". Any dependency which has an empty value is ignored. +Any dependency which has a value of "n", or which has some other value, +restricts the input range to "n". Quoting dependencies is not allowed. +Using dependencies with an empty value possible is not recommended. If the input range is restricted to the single choice "n", dep_tristate silently assigns "n" to /symbol/. If the input range has more than @@ -478,10 +488,13 @@ from the user, and assigns that value to /symbol/. Configure: implemented -Menuconfig: implemented (but silently ignores dependencies after the first) -Xconfig: implemented (but silently ignores dependencies after the first) +Menuconfig: implemented +Xconfig: implemented mconfig: implemented +Known bugs: +- Xconfig does not write "# foo is not set" to .config (as well as + "#unset foo" to autoconf.h) if command is disabled by its dependencies. === unset /symbol/ ... @@ -492,7 +505,7 @@ Configure: implemented Menuconfig: implemented -Xconfig: not implemented +Xconfig: implemented (with bugs) mconfig: implemented @@ -570,14 +583,9 @@ XConfig: implemented, with bugs mconfig: implemented -Xconfig has several known bugs, and probably some unknown bugs too: - -- In a comparison, if the left-hand atom is a variable and that variable - is from a choice list, the right-hand atom must be "y". +Xconfig has some known bugs, and probably some unknown bugs too: -- In a comparison, if the right-hand atom is a variable and that variable - is from a choice list, you lose. tkparse will throw a segmentation - violation, silently generate bizarre TCL code, or something else. +- literals with an empty "" value are not properly handled. - tkparse gives the wrong precedence to -o, -a, and !. Don't use both -o and -a in an expression. Don't use ! at all. diff -u --recursive --new-file v2.3.19/linux/Documentation/kernel-parameters.txt linux/Documentation/kernel-parameters.txt --- v2.3.19/linux/Documentation/kernel-parameters.txt Wed Jul 21 12:54:07 1999 +++ linux/Documentation/kernel-parameters.txt Thu Oct 7 10:17:08 1999 @@ -266,9 +266,11 @@ IRQ/DMA settings because of possible conflicts). You can specify the base address, IRQ, and DMA settings; IRQ - and DMA should be numbers or 'auto' + and DMA should be numbers, or 'auto' (for using detected settings on that - particular port). Parallel ports are + particular port), or 'nofifo' (to + avoid using a FIFO even if it is + detected). Parallel ports are assigned in the order they are specified on the command line, starting with parport0. diff -u --recursive --new-file v2.3.19/linux/Documentation/networking/ray_cs.txt linux/Documentation/networking/ray_cs.txt --- v2.3.19/linux/Documentation/networking/ray_cs.txt Wed Dec 31 16:00:00 1969 +++ linux/Documentation/networking/ray_cs.txt Thu Oct 7 10:17:08 1999 @@ -0,0 +1,151 @@ +September 21, 1999 + +Copyright (c) 1998 Corey Thomas (corey@world.std.com) + +This file is the documentation for the Raylink Wireless LAN card driver for +Linux. The Raylink wireless LAN card is a PCMCIA card which provides IEEE +802.11 compatible wireless network connectivity at 1 and 2 megabits/second. +See http://www.raytheon.com/micro/raylink/ for more information on the Raylink +card. This driver is in early development and does have bugs. See the known +bugs and limitations at the end of this document for more information. +This driver also works with WebGear's Aviator 2.4 and Aviator Pro +wireless LAN cards. + +As of kernel 2.3.18, the ray_cs driver is part of the Linux kernel +source. My web page for the development of ray_cs is at +http://world.std.com/~corey/raylink.html and I can be emailed at +corey@world.std.com + +The kernel driver is based on ray_cs-1.62.tgz + +The driver at my web page is intended to be used as an add on to +David Hinds pcmcia package. All the command line parameters are +available when compiled as a module. When built into the kernel, only +the essid= string parameter is available via the kernel command line. +This will change after the method of sorting out parameters for all +the PCMCIA drivers is agreed upon. If you must have a built in driver +with nondefault parameters, they can be edited in +/usr/src/linux/drivers/net/pcmcia/ray_cs.c. Searching for MODULE_PARM +will find them all. + +Information on card services is available at: + ftp://hyper.stanford.edu/pub/pcmcia/doc + http://hyper.stanford.edu/HyperNews/get/pcmcia/home.html + + +Card services user programs are still required for PCMCIA devices. +pcmcia-cs-3.1.1 or greater is required for the kernel version of +the driver. + +Currently, ray_cs is not part of David Hinds card services package, +so the following magic is required. + +At the end of the /etc/pcmcia/config.opts file, add the line: +source ./ray_cs.opts +This will make card services read the ray_cs.opts file +when starting. Create the file /etc/pcmcia/ray_cs.opts containing the +following: + +#### start of /etc/pcmcia/ray_cs.opts ################### +# Configuration options for Raylink Wireless LAN PCMCIA card +device "ray_cs" + class "network" module "misc/ray_cs" + +card "RayLink PC Card WLAN Adapter" + manfid 0x01a6, 0x0000 + bind "ray_cs" + +module "misc/ray_cs" opts "" +#### end of /etc/pcmcia/ray_cs.opts ##################### + + +To join an existing network with +different parameters, contact the network administrator for the +configuration information, and edit /etc/pcmcia/ray_cs.opts. +Add the parameters below between the empty quotes. + +Parameters for ray_cs driver which may be specified in ray_cs.opts: + +bc integer 0 = normal mode (802.11 timing) + 1 = slow down inter frame timing to allow + operation with older breezecom access + points. + +beacon_period integer beacon period in Kilo-microseconds + legal values = must be integer multiple + of hop dwell + default = 256 + +country integer 1 = USA (default) + 2 = Europe + 3 = Japan + 4 = Korea + 5 = Spain + 6 = France + 7 = Israel + 8 = Australia + +essid string ESS ID - network name to join + string with maximum length of 32 chars + default value = "ADHOC_ESSID" + +hop_dwell integer hop dwell time in Kilo-microseconds + legal values = 16,32,64,128(default),256 + +irq_mask integer linux standard 16 bit value 1bit/IRQ + lsb is IRQ 0, bit 1 is IRQ 1 etc. + Used to restrict choice of IRQ's to use. + Recommended method for controlling + interrupts is in /etc/pcmcia/config.opts + +net_type integer 0 (default) = adhoc network, + 1 = infrastructure + +phy_addr string string containing new MAC address in + hex, must start with x eg + x00008f123456 + +psm integer 0 = continuously active + 1 = power save mode (not useful yet) + +pc_debug integer (0-5) larger values for more verbose + logging. Replaces ray_debug. + +ray_debug integer Replaced with pc_debug + +ray_mem_speed integer defaults to 500 + +sniffer integer 0 = not sniffer (default) + 1 = sniffer which can be used to record all + network traffic using tcpdump or similar, + but no normal network use is allowed. + +translate integer 0 = no translation (encapsulate frames) + 1 = translation (RFC1042/802.1) + + +More on sniffer mode: + +tcpdump does not understand 802.11 headers, so it can't +interpret the contents, but it can record to a file. This is only +useful for debugging 802.11 lowlevel protocols that are not visible to +linux. If you want to watch ftp xfers, or do similar things, you +don't need to use sniffer mode. Also, some packet types are never +sent up by the card, so you will never see them (ack, rts, cts, probe +etc.) There is a simple program (showcap) included in the ray_cs +package which parses the 802.11 headers. + +Known Problems and missing features + + Does not work with non x86 + + Does not work with SMP + + Support for defragmenting frames is not yet debugged, and in + fact is known to not work. I have never encountered a net set + up to fragment, but still, it should be fixed. + + The ioctl support is incomplete. The hardware address cannot be set + using ifconfig yet. If a different hardware address is needed, it may + be set using the phy_addr parameter in ray_cs.opts. This requires + a card insertion to take effect. diff -u --recursive --new-file v2.3.19/linux/Documentation/nmi_watchdog.txt linux/Documentation/nmi_watchdog.txt --- v2.3.19/linux/Documentation/nmi_watchdog.txt Wed Dec 31 16:00:00 1969 +++ linux/Documentation/nmi_watchdog.txt Thu Oct 7 10:17:08 1999 @@ -0,0 +1,33 @@ + +Is your SMP system locking up unpredictably? No keyboard activity, just +a frustrating complete hard lockup? Do you want to help us debugging +such lockups? If all yes then this document is definitely for you. + +on Intel SMP hardware there is a feature that enables us to generate +'watchdog NMI interrupts'. (NMI: Non Maskable Interrupt - these get +executed even if the system is otherwise locked up hard) This can be +used to debug hard kernel lockups. By executing periodic NMI interrupts, +the kernel can monitor wether any CPU has locked up, and print out +debugging messages if so. You can enable/disable the NMI watchdog at boot +time with the 'nmi_watchdog=1' boot parameter. Eg. the relevant +lilo.conf entry: + + append="nmi_watchdog=1" + +A 'lockup' is the following scenario: if any CPU in the system does not +execute the period local timer interrupt for more than 5 seconds, then +the NMI handler generates an oops and kills the process. This +'controlled crash' (and the resulting kernel messages) can be used to +debug the lockup. Thus whenever the lockup happens, wait 5 seconds and +the oops will show up automatically. If the kernel produces no messages +then the system has crashed so hard (eg. hardware-wise) that either it +cannot even accept NMI interrupts, or the crash has made the kernel +unable to print messages. + +NOTE: currently the NMI-oopser is enabled unconditionally on x86 SMP +boxes. + +[ feel free to send bug reports, suggestions and patches to + Ingo Molnar or the Linux SMP mailing + list at ] + diff -u --recursive --new-file v2.3.19/linux/Documentation/parport.txt linux/Documentation/parport.txt --- v2.3.19/linux/Documentation/parport.txt Thu Aug 12 10:19:59 1999 +++ linux/Documentation/parport.txt Thu Oct 7 10:17:08 1999 @@ -67,7 +67,7 @@ kernel boot parameters to get the same effect. Add something like the following to your LILO command line: - parport=0x3bc parport=0x378,7 parport=0x278,auto + parport=0x3bc parport=0x378,7 parport=0x278,auto,nofifo You can have many `parport=...' statements, one for each port you want to add. Adding `parport=0' to the kernel command-line will disable diff -u --recursive --new-file v2.3.19/linux/MAINTAINERS linux/MAINTAINERS --- v2.3.19/linux/MAINTAINERS Mon Oct 4 15:49:29 1999 +++ linux/MAINTAINERS Thu Oct 7 10:17:08 1999 @@ -434,6 +434,11 @@ L: linux-kernel@vger.rutgers.edu S: Maintained +INTEL APIC/IOAPIC, LOWLEVEL X86 SMP SUPPORT +P: Ingo Molnar +M: mingo@redhat.com +S: Maintained + IP MASQUERADING: P: Juanjo Ciarlante M: jjciarla@raiz.uncu.edu.ar diff -u --recursive --new-file v2.3.19/linux/Makefile linux/Makefile --- v2.3.19/linux/Makefile Mon Oct 4 15:49:29 1999 +++ linux/Makefile Thu Oct 7 10:17:08 1999 @@ -1,6 +1,6 @@ VERSION = 2 PATCHLEVEL = 3 -SUBLEVEL = 19 +SUBLEVEL = 20 EXTRAVERSION = ARCH := $(shell uname -m | sed -e s/i.86/i386/ -e s/sun4u/sparc64/ -e s/arm.*/arm/ -e s/sa110/arm/) diff -u --recursive --new-file v2.3.19/linux/arch/alpha/kernel/core_apecs.c linux/arch/alpha/kernel/core_apecs.c --- v2.3.19/linux/arch/alpha/kernel/core_apecs.c Tue Sep 7 12:14:05 1999 +++ linux/arch/alpha/kernel/core_apecs.c Thu Oct 7 12:23:21 1999 @@ -18,7 +18,6 @@ #include #include #include -#include #define __EXTERN_INLINE inline #include diff -u --recursive --new-file v2.3.19/linux/arch/alpha/kernel/core_cia.c linux/arch/alpha/kernel/core_cia.c --- v2.3.19/linux/arch/alpha/kernel/core_cia.c Tue Sep 7 12:14:05 1999 +++ linux/arch/alpha/kernel/core_cia.c Thu Oct 7 12:23:21 1999 @@ -19,7 +19,6 @@ #include #include -#include #define __EXTERN_INLINE inline #include diff -u --recursive --new-file v2.3.19/linux/arch/alpha/kernel/core_lca.c linux/arch/alpha/kernel/core_lca.c --- v2.3.19/linux/arch/alpha/kernel/core_lca.c Tue Sep 7 12:14:05 1999 +++ linux/arch/alpha/kernel/core_lca.c Thu Oct 7 12:23:21 1999 @@ -17,7 +17,6 @@ #include #include #include -#include #define __EXTERN_INLINE inline #include diff -u --recursive --new-file v2.3.19/linux/arch/alpha/kernel/core_mcpcia.c linux/arch/alpha/kernel/core_mcpcia.c --- v2.3.19/linux/arch/alpha/kernel/core_mcpcia.c Tue Sep 7 12:14:05 1999 +++ linux/arch/alpha/kernel/core_mcpcia.c Thu Oct 7 12:23:21 1999 @@ -15,7 +15,6 @@ #include #include -#include #include #define __EXTERN_INLINE inline diff -u --recursive --new-file v2.3.19/linux/arch/alpha/kernel/core_polaris.c linux/arch/alpha/kernel/core_polaris.c --- v2.3.19/linux/arch/alpha/kernel/core_polaris.c Tue Aug 31 17:29:12 1999 +++ linux/arch/alpha/kernel/core_polaris.c Thu Oct 7 12:23:21 1999 @@ -12,7 +12,6 @@ #include #include -#include #define __EXTERN_INLINE inline #include diff -u --recursive --new-file v2.3.19/linux/arch/alpha/kernel/core_pyxis.c linux/arch/alpha/kernel/core_pyxis.c --- v2.3.19/linux/arch/alpha/kernel/core_pyxis.c Tue Sep 7 12:14:05 1999 +++ linux/arch/alpha/kernel/core_pyxis.c Thu Oct 7 12:23:21 1999 @@ -14,7 +14,6 @@ #include #include -#include #define __EXTERN_INLINE inline #include diff -u --recursive --new-file v2.3.19/linux/arch/alpha/kernel/core_t2.c linux/arch/alpha/kernel/core_t2.c --- v2.3.19/linux/arch/alpha/kernel/core_t2.c Tue Sep 7 12:14:05 1999 +++ linux/arch/alpha/kernel/core_t2.c Thu Oct 7 12:23:21 1999 @@ -17,7 +17,6 @@ #include #include -#include #define __EXTERN_INLINE #include diff -u --recursive --new-file v2.3.19/linux/arch/alpha/kernel/core_tsunami.c linux/arch/alpha/kernel/core_tsunami.c --- v2.3.19/linux/arch/alpha/kernel/core_tsunami.c Tue Sep 7 12:14:05 1999 +++ linux/arch/alpha/kernel/core_tsunami.c Thu Oct 7 12:23:21 1999 @@ -14,7 +14,6 @@ #include #include -#include #include #define __EXTERN_INLINE inline diff -u --recursive --new-file v2.3.19/linux/arch/alpha/kernel/pci.c linux/arch/alpha/kernel/pci.c --- v2.3.19/linux/arch/alpha/kernel/pci.c Tue Sep 7 12:14:05 1999 +++ linux/arch/alpha/kernel/pci.c Thu Oct 7 12:23:21 1999 @@ -10,7 +10,6 @@ #include #include #include -#include #include #include "proto.h" @@ -81,6 +80,13 @@ for (dev = pci_devices; dev; dev = dev->next) { if (dev->class >> 8 != PCI_CLASS_STORAGE_IDE) continue; + /* Resource 1 of IDE controller is the address of HD_CMD + register which actually occupies a single byte (0x3f6 + for ide0) in reported 0x3f4-3f7 range. We have to fix + that to avoid resource conflict with AT-style floppy + controller. */ + dev->resource[1].start += 2; + dev->resource[1].end = dev->resource[1].start; for (i = 0; i < PCI_NUM_RESOURCES; i++) { if (dev->resource[i].flags) pci_claim_resource(dev, i); diff -u --recursive --new-file v2.3.19/linux/arch/alpha/kernel/setup.c linux/arch/alpha/kernel/setup.c --- v2.3.19/linux/arch/alpha/kernel/setup.c Tue Aug 31 17:29:12 1999 +++ linux/arch/alpha/kernel/setup.c Thu Oct 7 12:23:21 1999 @@ -40,7 +40,6 @@ #include #include #include -#include #include "proto.h" #include "pci_impl.h" diff -u --recursive --new-file v2.3.19/linux/arch/alpha/kernel/sys_dp264.c linux/arch/alpha/kernel/sys_dp264.c --- v2.3.19/linux/arch/alpha/kernel/sys_dp264.c Tue Aug 31 17:29:12 1999 +++ linux/arch/alpha/kernel/sys_dp264.c Thu Oct 7 12:23:21 1999 @@ -22,7 +22,6 @@ #include #include #include -#include #include #include #include diff -u --recursive --new-file v2.3.19/linux/arch/alpha/kernel/sys_rawhide.c linux/arch/alpha/kernel/sys_rawhide.c --- v2.3.19/linux/arch/alpha/kernel/sys_rawhide.c Tue Sep 7 12:14:06 1999 +++ linux/arch/alpha/kernel/sys_rawhide.c Thu Oct 7 12:23:21 1999 @@ -19,7 +19,6 @@ #include #include #include -#include #include #include #include diff -u --recursive --new-file v2.3.19/linux/arch/alpha/kernel/sys_sio.c linux/arch/alpha/kernel/sys_sio.c --- v2.3.19/linux/arch/alpha/kernel/sys_sio.c Tue Aug 31 17:29:12 1999 +++ linux/arch/alpha/kernel/sys_sio.c Thu Oct 7 12:23:21 1999 @@ -28,7 +28,6 @@ #include #include #include -#include #include "proto.h" #include "irq_impl.h" diff -u --recursive --new-file v2.3.19/linux/arch/arm/config.in linux/arch/arm/config.in --- v2.3.19/linux/arch/arm/config.in Tue Aug 31 17:29:12 1999 +++ linux/arch/arm/config.in Thu Oct 7 10:17:08 1999 @@ -7,6 +7,11 @@ define_bool CONFIG_ARM y mainmenu_option next_comment +comment 'Code maturity level options' +bool 'Prompt for development and/or incomplete code/drivers' CONFIG_EXPERIMENTAL +endmenu + +mainmenu_option next_comment comment 'System and processor type' choice 'ARM system type' \ @@ -17,24 +22,24 @@ FootBridge-based CONFIG_FOOTBRIDGE" RiscPC if [ "$CONFIG_FOOTBRIDGE" = "y" ]; then - bool 'FootBridge in HOST mode' CONFIG_HOST_FOOTBRIDGE - if [ "$CONFIG_HOST_FOOTBRIDGE" = "y" ]; then - define_bool CONFIG_ADDIN_FOOTBRIDGE n - else - define_bool CONFIG_ADDIN_FOOTBRIDGE y - fi + bool 'FootBridge in HOST mode' CONFIG_HOST_FOOTBRIDGE + if [ "$CONFIG_HOST_FOOTBRIDGE" = "y" ]; then + define_bool CONFIG_ADDIN_FOOTBRIDGE n + else + define_bool CONFIG_ADDIN_FOOTBRIDGE y + fi fi if [ "$CONFIG_HOST_FOOTBRIDGE" = "y" ]; then - bool ' Include support for Intel EBSA285' CONFIG_ARCH_EBSA285 - bool ' Include support for Chalice CATS boards' CONFIG_CATS - bool ' Include support for Corel NetWinder' CONFIG_ARCH_NETWINDER + bool ' Include support for Intel EBSA285' CONFIG_ARCH_EBSA285 + bool ' Include support for Chalice CATS boards' CONFIG_CATS + bool ' Include support for Corel NetWinder' CONFIG_ARCH_NETWINDER fi if [ "$CONFIG_ADDIN_FOOTBRIDGE" = "y" ]; then - # If we get any other footbridge-based plug-in boards, then - # add your architecture options here - define_bool CONFIG_ARCH_CO285 y + # If we get any other footbridge-based plug-in boards, then + # add your architecture options here + define_bool CONFIG_ARCH_CO285 y fi # @@ -44,9 +49,9 @@ if [ "$CONFIG_ARCH_ARC" = "y" -o \ "$CONFIG_ARCH_A5K" = "y" -o \ "$CONFIG_ARCH_RPC" = "y" ]; then - define_bool CONFIG_ARCH_ACORN y + define_bool CONFIG_ARCH_ACORN y else - define_bool CONFIG_ARCH_ACORN n + define_bool CONFIG_ARCH_ACORN n fi # @@ -56,33 +61,33 @@ # if [ "$CONFIG_ARCH_ARC" = "y" -o \ "$CONFIG_ARCH_A5K" = "y" ]; then - define_bool CONFIG_CPU_32 n - define_bool CONFIG_CPU_26 y + define_bool CONFIG_CPU_32 n + define_bool CONFIG_CPU_26 y - # - # Select memory size - # - bool '2MB physical memory' CONFIG_PAGESIZE_16 + # + # Select memory size + # + bool '2MB physical memory' CONFIG_PAGESIZE_16 else - define_bool CONFIG_CPU_32 y - define_bool CONFIG_CPU_26 n + define_bool CONFIG_CPU_32 y + define_bool CONFIG_CPU_26 n - # - # Select CPU and optimisation dependent on architecture - # - if [ "$CONFIG_ARCH_EBSA110" = "y" -o \ - "$CONFIG_FOOTBRIDGE" = "y" -o \ - "$CONFIG_ARCH_NEXUSPCI" = "y" ]; then - define_bool CONFIG_CPU_32v4 y - define_bool CONFIG_CPU_SA110 y - else - if [ "$CONFIG_ARCH_RPC" = "y" ]; then - define_bool CONFIG_CPU_32v3 y - bool 'Support ARM610' CONFIG_CPU_ARM6 - bool 'Support ARM710' CONFIG_CPU_ARM7 - bool 'Support StrongARM110' CONFIG_CPU_SA110 - fi - fi + # + # Select CPU and optimisation dependent on architecture + # + if [ "$CONFIG_ARCH_EBSA110" = "y" -o \ + "$CONFIG_FOOTBRIDGE" = "y" -o \ + "$CONFIG_ARCH_NEXUSPCI" = "y" ]; then + define_bool CONFIG_CPU_32v4 y + define_bool CONFIG_CPU_SA110 y + else + if [ "$CONFIG_ARCH_RPC" = "y" ]; then + define_bool CONFIG_CPU_32v3 y + bool 'Support ARM610' CONFIG_CPU_ARM6 + bool 'Support ARM710' CONFIG_CPU_ARM7 + bool 'Support StrongARM110' CONFIG_CPU_SA110 + fi + fi fi # @@ -90,7 +95,7 @@ # if [ "$CONFIG_ARCH_NEXUSPCI" = "y" -o \ "$CONFIG_HOST_FOOTBRIDGE" = "y" ]; then - define_bool CONFIG_PCI y + define_bool CONFIG_PCI y fi # @@ -98,18 +103,15 @@ # if [ "$CONFIG_CATS" = "y" -o \ "$CONFIG_ARCH_NETWINDER" = "y" ]; then - define_bool CONFIG_ISA_DMA y + define_bool CONFIG_ISA_DMA y else - define_bool CONFIG_ISA_DMA n + define_bool CONFIG_ISA_DMA n fi endmenu -mainmenu_option next_comment -comment 'Code maturity level options' -bool 'Prompt for development and/or incomplete code/drivers' CONFIG_EXPERIMENTAL -if [ "$CONFIG_CPU_32" = "y" -a "$CONFIG_ARCH_EBSA110" != "y" ]; then - bool 'Enable kernel-mode alignment trap handler (EXPERIMENTAL)' CONFIG_ALIGNMENT_TRAP +if [ "$CONFIG_CPU_32" = "y" -a "$CONFIG_ARCH_EBSA110" != "y" -a "$CONFIG_EXPERIMENTAL" ]; then + bool 'Enable kernel-mode alignment trap handler (EXPERIMENTAL)' CONFIG_ALIGNMENT_TRAP fi #bool 'Split text into discardable sections' CONFIG_TEXT_SECTIONS endmenu @@ -118,8 +120,8 @@ comment 'Loadable module support' bool 'Enable loadable module support' CONFIG_MODULES if [ "$CONFIG_MODULES" = "y" ]; then - bool 'Set version information on all symbols for modules' CONFIG_MODVERSIONS - bool 'Kernel module loader' CONFIG_KMOD + bool ' Set version information on all symbols for modules' CONFIG_MODVERSIONS + bool ' Kernel module loader' CONFIG_KMOD fi endmenu @@ -134,41 +136,41 @@ tristate 'Kernel support for ELF binaries' CONFIG_BINFMT_ELF tristate 'Kernel support for MISC binaries' CONFIG_BINFMT_MISC if [ "$CONFIG_CPU_32" = "y" ]; then - tristate 'RISC OS personality' CONFIG_ARTHUR + tristate 'RISC OS personality' CONFIG_ARTHUR fi tristate 'Parallel port support' CONFIG_PARPORT if [ "$CONFIG_PARPORT" != "n" ]; then - if [ "$CONFIG_ARCH_ARC" = "y" ]; then - dep_tristate ' Archimedes hardware' CONFIG_PARPORT_ARC $CONFIG_PARPORT - fi - dep_tristate ' PC-style hardware' CONFIG_PARPORT_PC $CONFIG_PARPORT -# If exactly one hardware type is selected then parport will optimise away -# support for loading any others. Defeat this if the user is keen. - if [ "$CONFIG_PARPORT_PC" = "n" -o "$CONFIG_PARPORT_ARC" = "n" ]; then - if [ "$CONFIG_PARPORT_PC" != "n" -o "$CONFIG_PARPORT_ARC" != "n" ]; then - bool ' Support foreign hardware' CONFIG_PARPORT_OTHER - fi - fi + if [ "$CONFIG_ARCH_ARC" = "y" ]; then + dep_tristate ' Archimedes hardware' CONFIG_PARPORT_ARC $CONFIG_PARPORT + fi + dep_tristate ' PC-style hardware' CONFIG_PARPORT_PC $CONFIG_PARPORT + # If exactly one hardware type is selected then parport will optimise away + # support for loading any others. Defeat this if the user is keen. + if [ "$CONFIG_PARPORT_PC" = "n" -o "$CONFIG_PARPORT_ARC" = "n" ]; then + if [ "$CONFIG_PARPORT_PC" != "n" -o "$CONFIG_PARPORT_ARC" != "n" ]; then + bool ' Support foreign hardware' CONFIG_PARPORT_OTHER + fi + fi fi if [ "$CONFIG_ARCH_EBSA110" = "y" -o \ "$CONFIG_ARCH_NETWINDER" = "y" -o \ "$CONFIG_CATS" = "y" ]; then - string 'Initial kernel command string' CONFIG_CMDLINE + string 'Initial kernel command string' CONFIG_CMDLINE fi if [ "$CONFIG_ARCH_NETWINDER" = "y" -o \ "$CONFIG_ARCH_EBSA110" = "y" -o \ "$CONFIG_ARCH_EBSA285" = "y" -o \ "$CONFIG_ARCH_CO285" = "y" ]; then - bool 'Timer and CPU usage LEDs' CONFIG_LEDS - if [ "$CONFIG_LEDS" = "y" ]; then - if [ "$CONFIG_ARCH_NETWINDER" = "y" -o \ - "$CONFIG_ARCH_EBSA285" = "y" -o \ - "$CONFIG_ARCH_CO285" = "y" ]; then - bool ' Timer LED' CONFIG_LEDS_TIMER - bool ' CPU usage LED' CONFIG_LEDS_CPU - fi - fi + bool 'Timer and CPU usage LEDs' CONFIG_LEDS + if [ "$CONFIG_LEDS" = "y" ]; then + if [ "$CONFIG_ARCH_NETWINDER" = "y" -o \ + "$CONFIG_ARCH_EBSA285" = "y" -o \ + "$CONFIG_ARCH_CO285" = "y" ]; then + bool ' Timer LED' CONFIG_LEDS_TIMER + bool ' CPU usage LED' CONFIG_LEDS_CPU + fi + fi fi endmenu @@ -179,48 +181,48 @@ source drivers/block/Config.in if [ "$CONFIG_ARCH_ACORN" = "y" ]; then - source drivers/acorn/block/Config.in + source drivers/acorn/block/Config.in fi source drivers/char/Config.in if [ "$CONFIG_ARCH_ACORN" = "y" ]; then - if [ "$CONFIG_MOUSE" = "y" ]; then - if [ "$CONFIG_ARCH_RPC" != "y" ]; then - define_bool CONFIG_KBDMOUSE y - else - define_bool CONFIG_RPCMOUSE y - fi - fi + if [ "$CONFIG_MOUSE" = "y" ]; then + if [ "$CONFIG_ARCH_RPC" != "y" ]; then + define_bool CONFIG_KBDMOUSE y + else + define_bool CONFIG_RPCMOUSE y + fi + fi fi source drivers/usb/Config.in if [ "$CONFIG_VT" = "y" ]; then - mainmenu_option next_comment - comment 'Console drivers' - if [ "$CONFIG_ARCH_ACORN" != "y" -a "$CONFIG_ARCH_EBSA110" != "y" ]; then - bool 'VGA text console' CONFIG_VGA_CONSOLE - fi - bool 'Support Frame buffer devices' CONFIG_FB - source drivers/video/Config.in - endmenu + mainmenu_option next_comment + comment 'Console drivers' + if [ "$CONFIG_ARCH_ACORN" != "y" -a "$CONFIG_ARCH_EBSA110" != "y" ]; then + bool 'VGA text console' CONFIG_VGA_CONSOLE + fi + bool 'Support Frame buffer devices' CONFIG_FB + source drivers/video/Config.in + endmenu fi if [ "$CONFIG_NET" = "y" ]; then - source net/Config.in + source net/Config.in - source net/ax25/Config.in + source net/ax25/Config.in - source net/irda/Config.in + source net/irda/Config.in - mainmenu_option next_comment - comment 'Network device support' + mainmenu_option next_comment + comment 'Network device support' - bool 'Network device support?' CONFIG_NETDEVICES - if [ "$CONFIG_NETDEVICES" = "y" ]; then - source drivers/net/Config.in - fi - endmenu + bool 'Network device support?' CONFIG_NETDEVICES + if [ "$CONFIG_NETDEVICES" = "y" ]; then + source drivers/net/Config.in + fi + endmenu fi # mainmenu_option next_comment @@ -238,19 +240,19 @@ tristate 'SCSI support?' CONFIG_SCSI if [ "$CONFIG_SCSI" != "n" ]; then - source drivers/scsi/Config.in + source drivers/scsi/Config.in fi endmenu if [ "$CONFIG_ARCH_ACORN" = "y" -o "$CONFIG_PCI" = "y" ]; then - mainmenu_option next_comment - comment 'Sound' + mainmenu_option next_comment + comment 'Sound' - tristate 'Sound support' CONFIG_SOUND - if [ "$CONFIG_SOUND" != "n" ]; then - source drivers/sound/Config.in - fi - endmenu + tristate 'Sound support' CONFIG_SOUND + if [ "$CONFIG_SOUND" != "n" ]; then + source drivers/sound/Config.in + fi + endmenu fi source fs/Config.in diff -u --recursive --new-file v2.3.19/linux/arch/i386/boot/setup.S linux/arch/i386/boot/setup.S --- v2.3.19/linux/arch/i386/boot/setup.S Mon Oct 4 15:49:29 1999 +++ linux/arch/i386/boot/setup.S Thu Oct 7 10:17:08 1999 @@ -641,36 +641,9 @@ out #0xf1,al call delay -! well, that went ok, I hope. Now we have to reprogram the interrupts :-( -! we put them right after the intel-reserved hardware interrupts, at -! int 0x20-0x2F. There they won't mess up anything. Sadly IBM really -! messed this up with the original PC, and they haven't been able to -! rectify it afterwards. Thus the bios puts interrupts at 0x08-0x0f, -! which is used for the internal hardware interrupts as well. We just -! have to reprogram the 8259's, and it isn't fun. +! well, that went ok, I hope. Now we mask all interrupts - the rest +! is done in init_IRQ(). - mov al,#0x11 ! initialization sequence - out #0x20,al ! send it to 8259A-1 - call delay - out #0xA0,al ! and to 8259A-2 - call delay - mov al,#0x20 ! start of hardware int's (0x20) - out #0x21,al - call delay - mov al,#0x28 ! start of hardware int's 2 (0x28) - out #0xA1,al - call delay - mov al,#0x04 ! 8259-1 is master - out #0x21,al - call delay - mov al,#0x02 ! 8259-2 is slave - out #0xA1,al - call delay - mov al,#0x01 ! 8086 mode for both - out #0x21,al - call delay - out #0xA1,al - call delay mov al,#0xFF ! mask off all interrupts for now out #0xA1,al call delay diff -u --recursive --new-file v2.3.19/linux/arch/i386/config.in linux/arch/i386/config.in --- v2.3.19/linux/arch/i386/config.in Tue Sep 7 12:14:06 1999 +++ linux/arch/i386/config.in Fri Oct 8 10:06:21 1999 @@ -59,29 +59,30 @@ bool 'BIGMEM support' CONFIG_BIGMEM bool 'Networking support' CONFIG_NET -bool 'PCI support' CONFIG_PCI -if [ "$CONFIG_PCI" = "y" ]; then - choice 'PCI access mode' \ - "BIOS CONFIG_PCI_GOBIOS \ - Direct CONFIG_PCI_GODIRECT \ - Any CONFIG_PCI_GOANY" Any - if [ "$CONFIG_PCI_GOBIOS" = "y" -o "$CONFIG_PCI_GOANY" = "y" ]; then - define_bool CONFIG_PCI_BIOS y - fi - if [ "$CONFIG_PCI_GODIRECT" = "y" -o "$CONFIG_PCI_GOANY" = "y" ]; then - define_bool CONFIG_PCI_DIRECT y - fi -fi -bool 'MCA support' CONFIG_MCA bool 'SGI Visual Workstation support' CONFIG_VISWS if [ "$CONFIG_VISWS" = "y" ]; then define_bool CONFIG_X86_VISWS_APIC y define_bool CONFIG_X86_LOCAL_APIC y + define_bool CONFIG_PCI y else if [ "$CONFIG_SMP" = "y" ]; then define_bool CONFIG_X86_IO_APIC y define_bool CONFIG_X86_LOCAL_APIC y fi + bool 'PCI support' CONFIG_PCI + if [ "$CONFIG_PCI" = "y" ]; then + choice 'PCI access mode' \ + "BIOS CONFIG_PCI_GOBIOS \ + Direct CONFIG_PCI_GODIRECT \ + Any CONFIG_PCI_GOANY" Any + if [ "$CONFIG_PCI_GOBIOS" = "y" -o "$CONFIG_PCI_GOANY" = "y" ]; then + define_bool CONFIG_PCI_BIOS y + fi + if [ "$CONFIG_PCI_GODIRECT" = "y" -o "$CONFIG_PCI_GOANY" = "y" ]; then + define_bool CONFIG_PCI_DIRECT y + fi + fi + bool 'MCA support' CONFIG_MCA fi source drivers/pcmcia/Config.in diff -u --recursive --new-file v2.3.19/linux/arch/i386/defconfig linux/arch/i386/defconfig --- v2.3.19/linux/arch/i386/defconfig Mon Oct 4 15:49:29 1999 +++ linux/arch/i386/defconfig Thu Oct 7 13:05:00 1999 @@ -360,6 +360,7 @@ # # Misc devices # +CONFIG_ACPI=y # # Filesystems diff -u --recursive --new-file v2.3.19/linux/arch/i386/kernel/Makefile linux/arch/i386/kernel/Makefile --- v2.3.19/linux/arch/i386/kernel/Makefile Thu Aug 26 13:05:34 1999 +++ linux/arch/i386/kernel/Makefile Fri Oct 8 10:06:21 1999 @@ -19,7 +19,12 @@ MX_OBJS := ifdef CONFIG_PCI -O_OBJS += bios32.o +O_OBJS += pci-i386.o +ifdef CONFIG_VISWS +O_OBJS += pci-visws.o +else +O_OBJS += pci-pc.o +endif endif ifdef CONFIG_MCA @@ -43,7 +48,7 @@ endif ifdef CONFIG_SMP -O_OBJS += smp.o trampoline.o +O_OBJS += smp.o smpboot.o trampoline.o endif ifdef CONFIG_X86_IO_APIC diff -u --recursive --new-file v2.3.19/linux/arch/i386/kernel/bios32.c linux/arch/i386/kernel/bios32.c --- v2.3.19/linux/arch/i386/kernel/bios32.c Fri Sep 10 23:57:27 1999 +++ linux/arch/i386/kernel/bios32.c Wed Dec 31 16:00:00 1969 @@ -1,1220 +0,0 @@ -/* - * bios32.c - Low-Level PCI Access - * - * $Id: bios32.c,v 1.48 1998/09/26 08:06:55 mj Exp $ - * - * Copyright 1993, 1994 Drew Eckhardt - * Visionary Computing - * (Unix and Linux consulting and custom programming) - * Drew@Colorado.EDU - * +1 (303) 786-7975 - * - * Drew's work was sponsored by: - * iX Multiuser Multitasking Magazine - * Hannover, Germany - * hm@ix.de - * - * Copyright 1997--1999 Martin Mares - * - * For more information, please consult the following manuals (look at - * http://www.pcisig.com/ for how to get them): - * - * PCI BIOS Specification - * PCI Local Bus Specification - * PCI to PCI Bridge Specification - * PCI System Design Guide - * - * - * CHANGELOG : - * Jun 17, 1994 : Modified to accommodate the broken pre-PCI BIOS SPECIFICATION - * Revision 2.0 present on 's ASUS mainboard. - * - * Jan 5, 1995 : Modified to probe PCI hardware at boot time by Frederic - * Potter, potter@cao-vlsi.ibp.fr - * - * Jan 10, 1995 : Modified to store the information about configured pci - * devices into a list, which can be accessed via /proc/pci by - * Curtis Varner, cvarner@cs.ucr.edu - * - * Jan 12, 1995 : CPU-PCI bridge optimization support by Frederic Potter. - * Alpha version. Intel & UMC chipset support only. - * - * Apr 16, 1995 : Source merge with the DEC Alpha PCI support. Most of the code - * moved to drivers/pci/pci.c. - * - * Dec 7, 1996 : Added support for direct configuration access of boards - * with Intel compatible access schemes (tsbogend@alpha.franken.de) - * - * Feb 3, 1997 : Set internal functions to static, save/restore flags - * avoid dead locks reading broken PCI BIOS, werner@suse.de - * - * Apr 26, 1997 : Fixed case when there is BIOS32, but not PCI BIOS - * (mj@atrey.karlin.mff.cuni.cz) - * - * May 7, 1997 : Added some missing cli()'s. [mj] - * - * Jun 20, 1997 : Corrected problems in "conf1" type accesses. - * (paubert@iram.es) - * - * Aug 2, 1997 : Split to PCI BIOS handling and direct PCI access parts - * and cleaned it up... Martin Mares - * - * Feb 6, 1998 : No longer using BIOS to find devices and device classes. [mj] - * - * May 1, 1998 : Support for peer host bridges. [mj] - * - * Jun 19, 1998 : Changed to use spinlocks, so that PCI configuration space - * can be accessed from interrupts even on SMP systems. [mj] - * - * August 1998 : Better support for peer host bridges and more paranoid - * checks for direct hardware access. Ugh, this file starts to look as - * a large gallery of common hardware bug workarounds (watch the comments) - * -- the PCI specs themselves are sane, but most implementors should be - * hit hard with \hammer scaled \magstep5. [mj] - * - * Jan 23, 1999 : More improvements to peer host bridge logic. i450NX fixup. [mj] - * - * Feb 8, 1999 : Added UM8886BF I/O address fixup. [mj] - * - * August 1999 : New resource management and configuration access stuff. [mj] - */ - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include -#include -#include -#include -#include - -#undef DEBUG - -#ifdef DEBUG -#define DBG(x...) printk(x) -#else -#define DBG(x...) -#endif - -#define PCI_PROBE_BIOS 1 -#define PCI_PROBE_CONF1 2 -#define PCI_PROBE_CONF2 4 -#define PCI_NO_SORT 0x100 -#define PCI_BIOS_SORT 0x200 -#define PCI_NO_CHECKS 0x400 -#define PCI_NO_PEER_FIXUP 0x800 -#define PCI_ASSIGN_ROMS 0x1000 - -static unsigned int pci_probe = PCI_PROBE_BIOS | PCI_PROBE_CONF1 | PCI_PROBE_CONF2; - -/* - * Direct access to PCI hardware... - */ - -#ifdef CONFIG_PCI_DIRECT - -/* - * Functions for accessing PCI configuration space with type 1 accesses - */ - -#define CONFIG_CMD(dev, where) (0x80000000 | (dev->bus->number << 16) | (dev->devfn << 8) | (where & ~3)) - -static int pci_conf1_read_config_byte(struct pci_dev *dev, int where, u8 *value) -{ - outl(CONFIG_CMD(dev,where), 0xCF8); - *value = inb(0xCFC + (where&3)); - return PCIBIOS_SUCCESSFUL; -} - -static int pci_conf1_read_config_word(struct pci_dev *dev, int where, u16 *value) -{ - outl(CONFIG_CMD(dev,where), 0xCF8); - *value = inw(0xCFC + (where&2)); - return PCIBIOS_SUCCESSFUL; -} - -static int pci_conf1_read_config_dword(struct pci_dev *dev, int where, u32 *value) -{ - outl(CONFIG_CMD(dev,where), 0xCF8); - *value = inl(0xCFC); - return PCIBIOS_SUCCESSFUL; -} - -static int pci_conf1_write_config_byte(struct pci_dev *dev, int where, u8 value) -{ - outl(CONFIG_CMD(dev,where), 0xCF8); - outb(value, 0xCFC + (where&3)); - return PCIBIOS_SUCCESSFUL; -} - -static int pci_conf1_write_config_word(struct pci_dev *dev, int where, u16 value) -{ - outl(CONFIG_CMD(dev,where), 0xCF8); - outw(value, 0xCFC + (where&2)); - return PCIBIOS_SUCCESSFUL; -} - -static int pci_conf1_write_config_dword(struct pci_dev *dev, int where, u32 value) -{ - outl(CONFIG_CMD(dev,where), 0xCF8); - outl(value, 0xCFC); - return PCIBIOS_SUCCESSFUL; -} - -#undef CONFIG_CMD - -static struct pci_ops pci_direct_conf1 = { - pci_conf1_read_config_byte, - pci_conf1_read_config_word, - pci_conf1_read_config_dword, - pci_conf1_write_config_byte, - pci_conf1_write_config_word, - pci_conf1_write_config_dword -}; - -/* - * Functions for accessing PCI configuration space with type 2 accesses - */ - -#define IOADDR(devfn, where) ((0xC000 | ((devfn & 0x78) << 5)) + where) -#define FUNC(devfn) (((devfn & 7) << 1) | 0xf0) -#define SET(dev) if (dev->devfn) return PCIBIOS_DEVICE_NOT_FOUND; \ - outb(FUNC(dev->devfn), 0xCF8); \ - outb(dev->bus->number, 0xCFA); - -static int pci_conf2_read_config_byte(struct pci_dev *dev, int where, u8 *value) -{ - SET(dev); - *value = inb(IOADDR(dev->devfn,where)); - outb (0, 0xCF8); - return PCIBIOS_SUCCESSFUL; -} - -static int pci_conf2_read_config_word(struct pci_dev *dev, int where, u16 *value) -{ - SET(dev); - *value = inw(IOADDR(dev->devfn,where)); - outb (0, 0xCF8); - return PCIBIOS_SUCCESSFUL; -} - -static int pci_conf2_read_config_dword(struct pci_dev *dev, int where, u32 *value) -{ - SET(dev); - *value = inl (IOADDR(dev->devfn,where)); - outb (0, 0xCF8); - return PCIBIOS_SUCCESSFUL; -} - -static int pci_conf2_write_config_byte(struct pci_dev *dev, int where, u8 value) -{ - SET(dev); - outb (value, IOADDR(dev->devfn,where)); - outb (0, 0xCF8); - return PCIBIOS_SUCCESSFUL; -} - -static int pci_conf2_write_config_word(struct pci_dev *dev, int where, u16 value) -{ - SET(dev); - outw (value, IOADDR(dev->devfn,where)); - outb (0, 0xCF8); - return PCIBIOS_SUCCESSFUL; -} - -static int pci_conf2_write_config_dword(struct pci_dev *dev, int where, u32 value) -{ - SET(dev); - outl (value, IOADDR(dev->devfn,where)); - outb (0, 0xCF8); - return PCIBIOS_SUCCESSFUL; -} - -#undef SET -#undef IOADDR -#undef FUNC - -static struct pci_ops pci_direct_conf2 = { - pci_conf2_read_config_byte, - pci_conf2_read_config_word, - pci_conf2_read_config_dword, - pci_conf2_write_config_byte, - pci_conf2_write_config_word, - pci_conf2_write_config_dword -}; - -/* - * Before we decide to use direct hardware access mechanisms, we try to do some - * trivial checks to ensure it at least _seems_ to be working -- we just test - * whether bus 00 contains a host bridge (this is similar to checking - * techniques used in XFree86, but ours should be more reliable since we - * attempt to make use of direct access hints provided by the PCI BIOS). - * - * This should be close to trivial, but it isn't, because there are buggy - * chipsets (yes, you guessed it, by Intel and Compaq) that have no class ID. - */ -static int __init pci_sanity_check(struct pci_ops *o) -{ - u16 x; - struct pci_bus bus; /* Fake bus and device */ - struct pci_dev dev; - -#ifdef CONFIG_VISWS - return 1; /* Lithium PCI Bridges are non-standard */ -#endif - - if (pci_probe & PCI_NO_CHECKS) - return 1; - bus.number = 0; - dev.bus = &bus; - for(dev.devfn=0; dev.devfn < 0x100; dev.devfn++) - if ((!o->read_word(&dev, PCI_CLASS_DEVICE, &x) && - (x == PCI_CLASS_BRIDGE_HOST || x == PCI_CLASS_DISPLAY_VGA)) || - (!o->read_word(&dev, PCI_VENDOR_ID, &x) && - (x == PCI_VENDOR_ID_INTEL || x == PCI_VENDOR_ID_COMPAQ))) - return 1; - DBG("PCI: Sanity check failed\n"); - return 0; -} - -static struct pci_ops * __init pci_check_direct(void) -{ - unsigned int tmp; - unsigned long flags; - - __save_flags(flags); __cli(); - - /* - * Check if configuration type 1 works. - */ - if (pci_probe & PCI_PROBE_CONF1) { - outb (0x01, 0xCFB); - tmp = inl (0xCF8); - outl (0x80000000, 0xCF8); - if (inl (0xCF8) == 0x80000000 && - pci_sanity_check(&pci_direct_conf1)) { - outl (tmp, 0xCF8); - __restore_flags(flags); - printk("PCI: Using configuration type 1\n"); - return &pci_direct_conf1; - } - outl (tmp, 0xCF8); - } - - /* - * Check if configuration type 2 works. - */ - if (pci_probe & PCI_PROBE_CONF2) { - outb (0x00, 0xCFB); - outb (0x00, 0xCF8); - outb (0x00, 0xCFA); - if (inb (0xCF8) == 0x00 && inb (0xCFA) == 0x00 && - pci_sanity_check(&pci_direct_conf2)) { - __restore_flags(flags); - printk("PCI: Using configuration type 2\n"); - return &pci_direct_conf2; - } - } - - __restore_flags(flags); - return NULL; -} - -#endif - -/* - * BIOS32 and PCI BIOS handling. - */ - -#ifdef CONFIG_PCI_BIOS - -#define PCIBIOS_PCI_FUNCTION_ID 0xb1XX -#define PCIBIOS_PCI_BIOS_PRESENT 0xb101 -#define PCIBIOS_FIND_PCI_DEVICE 0xb102 -#define PCIBIOS_FIND_PCI_CLASS_CODE 0xb103 -#define PCIBIOS_GENERATE_SPECIAL_CYCLE 0xb106 -#define PCIBIOS_READ_CONFIG_BYTE 0xb108 -#define PCIBIOS_READ_CONFIG_WORD 0xb109 -#define PCIBIOS_READ_CONFIG_DWORD 0xb10a -#define PCIBIOS_WRITE_CONFIG_BYTE 0xb10b -#define PCIBIOS_WRITE_CONFIG_WORD 0xb10c -#define PCIBIOS_WRITE_CONFIG_DWORD 0xb10d - -/* BIOS32 signature: "_32_" */ -#define BIOS32_SIGNATURE (('_' << 0) + ('3' << 8) + ('2' << 16) + ('_' << 24)) - -/* PCI signature: "PCI " */ -#define PCI_SIGNATURE (('P' << 0) + ('C' << 8) + ('I' << 16) + (' ' << 24)) - -/* PCI service signature: "$PCI" */ -#define PCI_SERVICE (('$' << 0) + ('P' << 8) + ('C' << 16) + ('I' << 24)) - -/* PCI BIOS hardware mechanism flags */ -#define PCIBIOS_HW_TYPE1 0x01 -#define PCIBIOS_HW_TYPE2 0x02 -#define PCIBIOS_HW_TYPE1_SPEC 0x10 -#define PCIBIOS_HW_TYPE2_SPEC 0x20 - -/* - * This is the standard structure used to identify the entry point - * to the BIOS32 Service Directory, as documented in - * Standard BIOS 32-bit Service Directory Proposal - * Revision 0.4 May 24, 1993 - * Phoenix Technologies Ltd. - * Norwood, MA - * and the PCI BIOS specification. - */ - -union bios32 { - struct { - unsigned long signature; /* _32_ */ - unsigned long entry; /* 32 bit physical address */ - unsigned char revision; /* Revision level, 0 */ - unsigned char length; /* Length in paragraphs should be 01 */ - unsigned char checksum; /* All bytes must add up to zero */ - unsigned char reserved[5]; /* Must be zero */ - } fields; - char chars[16]; -}; - -/* - * Physical address of the service directory. I don't know if we're - * allowed to have more than one of these or not, so just in case - * we'll make pcibios_present() take a memory start parameter and store - * the array there. - */ - -static struct { - unsigned long address; - unsigned short segment; -} bios32_indirect = { 0, __KERNEL_CS }; - -/* - * Returns the entry point for the given service, NULL on error - */ - -static unsigned long bios32_service(unsigned long service) -{ - unsigned char return_code; /* %al */ - unsigned long address; /* %ebx */ - unsigned long length; /* %ecx */ - unsigned long entry; /* %edx */ - unsigned long flags; - - __save_flags(flags); __cli(); - __asm__("lcall (%%edi)" - : "=a" (return_code), - "=b" (address), - "=c" (length), - "=d" (entry) - : "0" (service), - "1" (0), - "D" (&bios32_indirect)); - __restore_flags(flags); - - switch (return_code) { - case 0: - return address + entry; - case 0x80: /* Not present */ - printk("bios32_service(0x%lx): not present\n", service); - return 0; - default: /* Shouldn't happen */ - printk("bios32_service(0x%lx): returned 0x%x, report to .\n", - service, return_code); - return 0; - } -} - -static struct { - unsigned long address; - unsigned short segment; -} pci_indirect = { 0, __KERNEL_CS }; - -static int pci_bios_present; - -static int __init check_pcibios(void) -{ - u32 signature, eax, ebx, ecx; - u8 status, major_ver, minor_ver, hw_mech, last_bus; - unsigned long flags, pcibios_entry; - - if ((pcibios_entry = bios32_service(PCI_SERVICE))) { - pci_indirect.address = pcibios_entry + PAGE_OFFSET; - - __save_flags(flags); __cli(); - __asm__( - "lcall (%%edi)\n\t" - "jc 1f\n\t" - "xor %%ah, %%ah\n" - "1:" - : "=d" (signature), - "=a" (eax), - "=b" (ebx), - "=c" (ecx) - : "1" (PCIBIOS_PCI_BIOS_PRESENT), - "D" (&pci_indirect) - : "memory"); - __restore_flags(flags); - - status = (eax >> 8) & 0xff; - hw_mech = eax & 0xff; - major_ver = (ebx >> 8) & 0xff; - minor_ver = ebx & 0xff; - last_bus = ecx & 0xff; - DBG("PCI: BIOS probe returned s=%02x hw=%02x ver=%02x.%02x l=%02x\n", - status, hw_mech, major_ver, minor_ver, last_bus); - if (status || signature != PCI_SIGNATURE) { - printk (KERN_ERR "PCI: BIOS BUG #%x[%08x] found, report to \n", - status, signature); - return 0; - } - printk("PCI: PCI BIOS revision %x.%02x entry at 0x%lx\n", - major_ver, minor_ver, pcibios_entry); -#ifdef CONFIG_PCI_DIRECT - if (!(hw_mech & PCIBIOS_HW_TYPE1)) - pci_probe &= ~PCI_PROBE_CONF1; - if (!(hw_mech & PCIBIOS_HW_TYPE2)) - pci_probe &= ~PCI_PROBE_CONF2; -#endif - return 1; - } - return 0; -} - -#if 0 /* Not used */ - -static int pci_bios_find_class (unsigned int class_code, unsigned short index, - unsigned char *bus, unsigned char *device_fn) -{ - unsigned long bx; - unsigned long ret; - - __asm__ ("lcall (%%edi)\n\t" - "jc 1f\n\t" - "xor %%ah, %%ah\n" - "1:" - : "=b" (bx), - "=a" (ret) - : "1" (PCIBIOS_FIND_PCI_CLASS_CODE), - "c" (class_code), - "S" ((int) index), - "D" (&pci_indirect)); - *bus = (bx >> 8) & 0xff; - *device_fn = bx & 0xff; - return (int) (ret & 0xff00) >> 8; -} - -#endif - -static int __init pci_bios_find_device (unsigned short vendor, unsigned short device_id, - unsigned short index, unsigned char *bus, unsigned char *device_fn) -{ - unsigned short bx; - unsigned short ret; - - __asm__("lcall (%%edi)\n\t" - "jc 1f\n\t" - "xor %%ah, %%ah\n" - "1:" - : "=b" (bx), - "=a" (ret) - : "1" (PCIBIOS_FIND_PCI_DEVICE), - "c" (device_id), - "d" (vendor), - "S" ((int) index), - "D" (&pci_indirect)); - *bus = (bx >> 8) & 0xff; - *device_fn = bx & 0xff; - return (int) (ret & 0xff00) >> 8; -} - -static int pci_bios_read_config_byte(struct pci_dev *dev, int where, u8 *value) -{ - unsigned long ret; - unsigned long bx = (dev->bus->number << 8) | dev->devfn; - - __asm__("lcall (%%esi)\n\t" - "jc 1f\n\t" - "xor %%ah, %%ah\n" - "1:" - : "=c" (*value), - "=a" (ret) - : "1" (PCIBIOS_READ_CONFIG_BYTE), - "b" (bx), - "D" ((long) where), - "S" (&pci_indirect)); - return (int) (ret & 0xff00) >> 8; -} - -static int pci_bios_read_config_word(struct pci_dev *dev, int where, u16 *value) -{ - unsigned long ret; - unsigned long bx = (dev->bus->number << 8) | dev->devfn; - - __asm__("lcall (%%esi)\n\t" - "jc 1f\n\t" - "xor %%ah, %%ah\n" - "1:" - : "=c" (*value), - "=a" (ret) - : "1" (PCIBIOS_READ_CONFIG_WORD), - "b" (bx), - "D" ((long) where), - "S" (&pci_indirect)); - return (int) (ret & 0xff00) >> 8; -} - -static int pci_bios_read_config_dword(struct pci_dev *dev, int where, u32 *value) -{ - unsigned long ret; - unsigned long bx = (dev->bus->number << 8) | dev->devfn; - - __asm__("lcall (%%esi)\n\t" - "jc 1f\n\t" - "xor %%ah, %%ah\n" - "1:" - : "=c" (*value), - "=a" (ret) - : "1" (PCIBIOS_READ_CONFIG_DWORD), - "b" (bx), - "D" ((long) where), - "S" (&pci_indirect)); - return (int) (ret & 0xff00) >> 8; -} - -static int pci_bios_write_config_byte(struct pci_dev *dev, int where, u8 value) -{ - unsigned long ret; - unsigned long bx = (dev->bus->number << 8) | dev->devfn; - - __asm__("lcall (%%esi)\n\t" - "jc 1f\n\t" - "xor %%ah, %%ah\n" - "1:" - : "=a" (ret) - : "0" (PCIBIOS_WRITE_CONFIG_BYTE), - "c" (value), - "b" (bx), - "D" ((long) where), - "S" (&pci_indirect)); - return (int) (ret & 0xff00) >> 8; -} - -static int pci_bios_write_config_word(struct pci_dev *dev, int where, u16 value) -{ - unsigned long ret; - unsigned long bx = (dev->bus->number << 8) | dev->devfn; - - __asm__("lcall (%%esi)\n\t" - "jc 1f\n\t" - "xor %%ah, %%ah\n" - "1:" - : "=a" (ret) - : "0" (PCIBIOS_WRITE_CONFIG_WORD), - "c" (value), - "b" (bx), - "D" ((long) where), - "S" (&pci_indirect)); - return (int) (ret & 0xff00) >> 8; -} - -static int pci_bios_write_config_dword(struct pci_dev *dev, int where, u32 value) -{ - unsigned long ret; - unsigned long bx = (dev->bus->number << 8) | dev->devfn; - - __asm__("lcall (%%esi)\n\t" - "jc 1f\n\t" - "xor %%ah, %%ah\n" - "1:" - : "=a" (ret) - : "0" (PCIBIOS_WRITE_CONFIG_DWORD), - "c" (value), - "b" (bx), - "D" ((long) where), - "S" (&pci_indirect)); - return (int) (ret & 0xff00) >> 8; -} - -/* - * Function table for BIOS32 access - */ - -static struct pci_ops pci_bios_access = { - pci_bios_read_config_byte, - pci_bios_read_config_word, - pci_bios_read_config_dword, - pci_bios_write_config_byte, - pci_bios_write_config_word, - pci_bios_write_config_dword -}; - -/* - * Try to find PCI BIOS. - */ - -static struct pci_ops * __init pci_find_bios(void) -{ - union bios32 *check; - unsigned char sum; - int i, length; - - /* - * Follow the standard procedure for locating the BIOS32 Service - * directory by scanning the permissible address range from - * 0xe0000 through 0xfffff for a valid BIOS32 structure. - */ - - for (check = (union bios32 *) __va(0xe0000); - check <= (union bios32 *) __va(0xffff0); - ++check) { - if (check->fields.signature != BIOS32_SIGNATURE) - continue; - length = check->fields.length * 16; - if (!length) - continue; - sum = 0; - for (i = 0; i < length ; ++i) - sum += check->chars[i]; - if (sum != 0) - continue; - if (check->fields.revision != 0) { - printk("PCI: unsupported BIOS32 revision %d at 0x%p, report to \n", - check->fields.revision, check); - continue; - } - DBG("PCI: BIOS32 Service Directory structure at 0x%p\n", check); - if (check->fields.entry >= 0x100000) { - printk("PCI: BIOS32 entry (0x%p) in high memory, cannot use.\n", check); - return NULL; - } else { - unsigned long bios32_entry = check->fields.entry; - DBG("PCI: BIOS32 Service Directory entry at 0x%lx\n", bios32_entry); - bios32_indirect.address = bios32_entry + PAGE_OFFSET; - if (check_pcibios()) - return &pci_bios_access; - } - break; /* Hopefully more than one BIOS32 cannot happen... */ - } - - return NULL; -} - -/* - * Sort the device list according to PCI BIOS. Nasty hack, but since some - * fool forgot to define the `correct' device order in the PCI BIOS specs - * and we want to be (possibly bug-to-bug ;-]) compatible with older kernels - * which used BIOS ordering, we are bound to do this... - */ - -static void __init pcibios_sort(void) -{ - struct pci_dev *dev = pci_devices; - struct pci_dev **last = &pci_devices; - struct pci_dev *d, **dd, *e; - int idx; - unsigned char bus, devfn; - - DBG("PCI: Sorting device list...\n"); - while ((e = dev)) { - idx = 0; - while (pci_bios_find_device(e->vendor, e->device, idx, &bus, &devfn) == PCIBIOS_SUCCESSFUL) { - idx++; - for(dd=&dev; (d = *dd); dd = &d->next) { - if (d->bus->number == bus && d->devfn == devfn) { - *dd = d->next; - *last = d; - last = &d->next; - break; - } - } - if (!d) { - printk("PCI: BIOS reporting unknown device %02x:%02x\n", bus, devfn); - /* - * We must not continue scanning as several buggy BIOSes - * return garbage after the last device. Grr. - */ - break; - } - } - if (e == dev) { - printk("PCI: Device %02x:%02x not found by BIOS\n", - dev->bus->number, dev->devfn); - d = dev; - dev = dev->next; - *last = d; - last = &d->next; - } - } - *last = NULL; -} - -#endif - -/* - * Several BIOS'es forget to assign addresses to I/O ranges. Try to fix it. - */ - -static void __init pcibios_fixup_io_addr(struct pci_dev *dev, int idx) -{ - unsigned int reg = PCI_BASE_ADDRESS_0 + 4*idx; - struct resource *r = &dev->resource[idx]; - unsigned int size = r->end - r->start + 1; - - if (((dev->class >> 8) == PCI_CLASS_STORAGE_IDE && idx < 4) || - (dev->class >> 8) == PCI_CLASS_DISPLAY_VGA) { - /* - * In case the BIOS didn't assign an address 0--3 to an IDE - * controller, we don't try to fix it as it means "use default - * addresses" at least with several broken chips and the IDE - * driver needs the original settings to recognize which devices - * correspond to the primary controller. - * - * We don't assign VGA I/O ranges as well. - */ - return; - } - /* - * We need to avoid collisions with `mirrored' VGA ports and other strange - * ISA hardware, so we always want the addresses kilobyte aligned. - */ - if (!size || size > 256) { - printk(KERN_ERR "PCI: Cannot assign I/O space to device %s, %d bytes are too much.\n", dev->name, size); - return; - } else { - u32 try; - - r->start = 0; - r->end = size - 1; - if (pci_assign_resource(dev, idx)) { - printk(KERN_ERR "PCI: Unable to find free %d bytes of I/O space for device %s.\n", size, dev->name); - return; - } - printk("PCI: Assigned I/O space %04lx-%04lx to device %s\n", r->start, r->end, dev->name); - pci_read_config_dword(dev, reg, &try); - if ((try & PCI_BASE_ADDRESS_IO_MASK) != r->start) { - r->start = 0; - pci_write_config_dword(dev, reg, 0); - printk(KERN_ERR "PCI: I/O address setup failed, got %04x\n", try); - } - } -} - -/* - * Assign address to expansion ROM. This is a highly experimental feature - * and you must enable it by "pci=rom". It's even not guaranteed to work - * with all cards since the PCI specs allow address decoders to be shared - * between the ROM space and one of the standard regions (sigh!). - */ -static void __init pcibios_fixup_rom_addr(struct pci_dev *dev) -{ - int reg = (dev->hdr_type == 1) ? PCI_ROM_ADDRESS1 : PCI_ROM_ADDRESS; - struct resource *r = &dev->resource[PCI_ROM_RESOURCE]; - unsigned long rom_size = r->end - r->start + 1; - - r->start = 0; - r->end = rom_size - 1; - if (pci_assign_resource(dev, PCI_ROM_RESOURCE)) - printk(KERN_ERR "PCI: Unable to find free space for expansion ROM of device %s (0x%lx bytes)\n", - dev->name, rom_size); - else { - DBG("PCI: Assigned address %08lx to expansion ROM of %s (0x%lx bytes)\n", r->start, dev->name, rom_size); - pci_write_config_dword(dev, reg, r->start | PCI_ROM_ADDRESS_ENABLE); - r->flags |= PCI_ROM_ADDRESS_ENABLE; - } -} - -/* - * Several buggy motherboards address only 16 devices and mirror - * them to next 16 IDs. We try to detect this `feature' on all - * primary busses (those containing host bridges as they are - * expected to be unique) and remove the ghost devices. - */ - -static void __init pcibios_fixup_ghosts(struct pci_bus *b) -{ - struct pci_dev *d, *e, **z; - int mirror = PCI_DEVFN(16,0); - int seen_host_bridge = 0; - int i; - - DBG("PCI: Scanning for ghost devices on bus %d\n", b->number); - for(d=b->devices; d && d->devfn < mirror; d=d->sibling) { - if ((d->class >> 8) == PCI_CLASS_BRIDGE_HOST) - seen_host_bridge++; - for(e=d->next; e; e=e->sibling) { - if (e->devfn != d->devfn + mirror || - e->vendor != d->vendor || - e->device != d->device || - e->class != d->class) - continue; - for(i=0; iresource[i].start != d->resource[i].start || - e->resource[i].end != d->resource[i].end || - e->resource[i].flags != d->resource[i].flags) - continue; - break; - } - if (!e) - return; - } - if (!seen_host_bridge) - return; - printk("PCI: Ignoring ghost devices on bus %d\n", b->number); - for(e=b->devices; e->sibling != d; e=e->sibling); - e->sibling = NULL; - for(z=&pci_devices; (d=*z);) - if (d->bus == b && d->devfn >= mirror) { - *z = d->next; - kfree_s(d, sizeof(*d)); - } else - z = &d->next; -} - -/* - * In case there are peer host bridges, scan bus behind each of them. - * Although several sources claim that the host bridges should have - * header type 1 and be assigned a bus number as for PCI2PCI bridges, - * the reality doesn't pass this test and the bus number is usually - * set by BIOS to the first free value. - */ -static void __init pcibios_fixup_peer_bridges(void) -{ - struct pci_bus *b = pci_root; - int n, cnt=-1; - struct pci_dev *d; - struct pci_ops *ops = pci_root->ops; - -#ifdef CONFIG_VISWS - pci_scan_bus(1, ops, NULL); - return; -#endif - -#ifdef CONFIG_PCI_DIRECT - /* - * Don't search for peer host bridges if we use config type 2 - * since it reads bogus values for non-existent busses and - * chipsets supporting multiple primary busses use conf1 anyway. - */ - if (ops == &pci_direct_conf2) - return; -#endif - - for(d=b->devices; d; d=d->sibling) - if ((d->class >> 8) == PCI_CLASS_BRIDGE_HOST) - cnt++; - n = b->subordinate + 1; - while (n <= 0xff) { - int found = 0; - u16 l; - struct pci_bus bus; - struct pci_dev dev; - bus.number = n; - bus.ops = ops; - dev.bus = &bus; - for(dev.devfn=0; dev.devfn<256; dev.devfn += 8) - if (!pci_read_config_word(&dev, PCI_VENDOR_ID, &l) && - l != 0x0000 && l != 0xffff) { -#ifdef CONFIG_PCI_BIOS - if (pci_bios_present) { - int err, idx = 0; - u8 bios_bus, bios_dfn; - u16 d; - pci_read_config_word(&dev, PCI_DEVICE_ID, &d); - DBG("BIOS test for %02x:%02x (%04x:%04x)\n", n, dev.devfn, l, d); - while (!(err = pci_bios_find_device(l, d, idx, &bios_bus, &bios_dfn)) && - (bios_bus != n || bios_dfn != dev.devfn)) - idx++; - if (err) - break; - } -#endif - DBG("Found device at %02x:%02x\n", n, dev.devfn); - found++; - if (!pci_read_config_word(&dev, PCI_CLASS_DEVICE, &l) && - l == PCI_CLASS_BRIDGE_HOST) - cnt++; - } - if (cnt-- <= 0) - break; - if (found) { - printk("PCI: Discovered primary peer bus %02x\n", n); - b = pci_scan_bus(n, ops, NULL); - if (b) - n = b->subordinate; - } - n++; - } -} - -/* - * Exceptions for specific devices. Usually work-arounds for fatal design flaws. - */ - -static void __init pci_fixup_i450nx(struct pci_dev *d) -{ - /* - * i450NX -- Find and scan all secondary buses on all PXB's. - */ - int pxb, reg; - u8 busno, suba, subb; - printk("PCI: Searching for i450NX host bridges on %s\n", d->name); - reg = 0xd0; - for(pxb=0; pxb<2; pxb++) { - pci_read_config_byte(d, reg++, &busno); - pci_read_config_byte(d, reg++, &suba); - pci_read_config_byte(d, reg++, &subb); - DBG("i450NX PXB %d: %02x/%02x/%02x\n", pxb, busno, suba, subb); - if (busno) - pci_scan_bus(busno, pci_root->ops, NULL); /* Bus A */ - if (suba < subb) - pci_scan_bus(suba+1, pci_root->ops, NULL); /* Bus B */ - } - pci_probe |= PCI_NO_PEER_FIXUP; -} - -static void __init pci_fixup_umc_ide(struct pci_dev *d) -{ - /* - * UM8886BF IDE controller sets region type bits incorrectly, - * therefore they look like memory despite of them being I/O. - */ - int i; - - printk("PCI: Fixing base address flags for device %s\n", d->name); - for(i=0; i<4; i++) - d->resource[i].flags |= PCI_BASE_ADDRESS_SPACE_IO; -} - -struct pci_fixup pcibios_fixups[] = { - { PCI_FIXUP_HEADER, PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_82451NX, pci_fixup_i450nx }, - { PCI_FIXUP_HEADER, PCI_VENDOR_ID_UMC, PCI_DEVICE_ID_UMC_UM8886BF, pci_fixup_umc_ide }, - { 0 } -}; - -/* - * Allocate resources for all PCI devices. We need to do that before - * we try to fix up anything. - */ - -static void __init pcibios_claim_resources(struct pci_bus *bus) -{ - struct pci_dev *dev; - int idx; - - while (bus) { - for (dev=bus->devices; dev; dev=dev->sibling) - for (idx = 0; idx < PCI_NUM_RESOURCES; idx++) { - struct resource *r = &dev->resource[idx]; - struct resource *pr; - if (!r->start) - continue; - pr = pci_find_parent_resource(dev, r); - if (!pr || request_resource(pr, r) < 0) { - printk(KERN_ERR "PCI: Address space collision on region %d of device %s\n", idx, dev->name); - /* We probably should disable the region, shouldn't we? */ - } - } - if (bus->children) - pcibios_claim_resources(bus->children); - bus = bus->next; - } -} - -/* - * Fix base addresses, I/O and memory enables and IRQ's (mostly work-arounds - * for buggy PCI BIOS'es :-[). - */ - -extern int skip_ioapic_setup; - -static void __init pcibios_fixup_devices(void) -{ - struct pci_dev *dev; - int i, has_io, has_mem; - unsigned short cmd; - - for(dev = pci_devices; dev; dev=dev->next) { - /* - * There are buggy BIOSes that forget to enable I/O and memory - * access to PCI devices. We try to fix this, but we need to - * be sure that the BIOS didn't forget to assign an address - * to the device. [mj] - */ - has_io = has_mem = 0; - for(i=0; i<6; i++) { - struct resource *r = &dev->resource[i]; - if (r->flags & PCI_BASE_ADDRESS_SPACE_IO) { - has_io = 1; - if (!r->start || r->start == PCI_BASE_ADDRESS_IO_MASK) - pcibios_fixup_io_addr(dev, i); - } else if (r->start) - has_mem = 1; - } - /* - * Don't enable VGA-compatible cards since they have - * fixed I/O and memory space. - * - * Don't enabled disabled IDE interfaces either because - * some BIOSes may reallocate the same address when they - * find that no devices are attached. - */ - if (((dev->class >> 8) != PCI_CLASS_DISPLAY_VGA) && - ((dev->class >> 8) != PCI_CLASS_STORAGE_IDE)) { - pci_read_config_word(dev, PCI_COMMAND, &cmd); - if (has_io && !(cmd & PCI_COMMAND_IO)) { - printk("PCI: Enabling I/O for device %s\n", dev->name); - cmd |= PCI_COMMAND_IO; - pci_write_config_word(dev, PCI_COMMAND, cmd); - } - if (has_mem && !(cmd & PCI_COMMAND_MEMORY)) { - printk("PCI: Enabling memory for device %s\n", dev->name); - cmd |= PCI_COMMAND_MEMORY; - pci_write_config_word(dev, PCI_COMMAND, cmd); - } - } - /* - * Assign address to expansion ROM if requested. - */ - if ((pci_probe & PCI_ASSIGN_ROMS) && dev->resource[PCI_ROM_RESOURCE].end) - pcibios_fixup_rom_addr(dev); -#if defined(CONFIG_X86_IO_APIC) - /* - * Recalculate IRQ numbers if we use the I/O APIC - */ - if(!skip_ioapic_setup) - { - int irq; - unsigned char pin; - - pci_read_config_byte(dev, PCI_INTERRUPT_PIN, &pin); - if (pin) { - pin--; /* interrupt pins are numbered starting from 1 */ - irq = IO_APIC_get_PCI_irq_vector(dev->bus->number, PCI_SLOT(dev->devfn), pin); - if (irq < 0 && dev->bus->parent) { /* go back to the bridge */ - struct pci_dev * bridge = dev->bus->self; - - pin = (pin + PCI_SLOT(dev->devfn)) % 4; - irq = IO_APIC_get_PCI_irq_vector(bridge->bus->number, - PCI_SLOT(bridge->devfn), pin); - if (irq >= 0) - printk(KERN_WARNING "PCI: using PPB(B%d,I%d,P%d) to get irq %d\n", - bridge->bus->number, PCI_SLOT(bridge->devfn), pin, irq); - } - if (irq >= 0) { - printk("PCI->APIC IRQ transform: (B%d,I%d,P%d) -> %d\n", - dev->bus->number, PCI_SLOT(dev->devfn), pin, irq); - dev->irq = irq; - } - } - } -#endif - /* - * Fix out-of-range IRQ numbers - */ - if (dev->irq >= NR_IRQS) - dev->irq = 0; - } -} - -/* - * Called after each bus is probed, but before its children - * are examined. - */ - -void __init pcibios_fixup_bus(struct pci_bus *b) -{ - pcibios_fixup_ghosts(b); -} - -/* - * Initialization. Try all known PCI access methods. Note that we support - * using both PCI BIOS and direct access: in such cases, we use I/O ports - * to access config space, but we still keep BIOS order of cards to be - * compatible with 2.0.X. This should go away some day. - */ - -void __init pcibios_init(void) -{ - struct pci_ops *bios = NULL; - struct pci_ops *dir = NULL; - struct pci_ops *ops; - -#ifdef CONFIG_PCI_BIOS - if ((pci_probe & PCI_PROBE_BIOS) && ((bios = pci_find_bios()))) { - pci_probe |= PCI_BIOS_SORT; - pci_bios_present = 1; - } -#endif -#ifdef CONFIG_PCI_DIRECT - if (pci_probe & (PCI_PROBE_CONF1 | PCI_PROBE_CONF2)) - dir = pci_check_direct(); -#endif - if (dir) - ops = dir; - else if (bios) - ops = bios; - else { - printk("PCI: No PCI bus detected\n"); - return; - } - - printk("PCI: Probing PCI hardware\n"); - pci_scan_bus(0, ops, NULL); - - if (!(pci_probe & PCI_NO_PEER_FIXUP)) - pcibios_fixup_peer_bridges(); - pcibios_claim_resources(pci_root); - pcibios_fixup_devices(); - -#ifdef CONFIG_PCI_BIOS - if ((pci_probe & PCI_BIOS_SORT) && !(pci_probe & PCI_NO_SORT)) - pcibios_sort(); -#endif -} - -char * __init pcibios_setup(char *str) -{ - if (!strcmp(str, "off")) { - pci_probe = 0; - return NULL; - } -#ifdef CONFIG_PCI_BIOS - else if (!strcmp(str, "bios")) { - pci_probe = PCI_PROBE_BIOS; - return NULL; - } else if (!strcmp(str, "nobios")) { - pci_probe &= ~PCI_PROBE_BIOS; - return NULL; - } else if (!strcmp(str, "nosort")) { - pci_probe |= PCI_NO_SORT; - return NULL; - } -#endif -#ifdef CONFIG_PCI_DIRECT - else if (!strcmp(str, "conf1")) { - pci_probe = PCI_PROBE_CONF1 | PCI_NO_CHECKS; - return NULL; - } - else if (!strcmp(str, "conf2")) { - pci_probe = PCI_PROBE_CONF2 | PCI_NO_CHECKS; - return NULL; - } -#endif - else if (!strcmp(str, "nopeer")) { - pci_probe |= PCI_NO_PEER_FIXUP; - return NULL; - } else if (!strcmp(str, "rom")) { - pci_probe |= PCI_ASSIGN_ROMS; - return NULL; - } - return str; -} diff -u --recursive --new-file v2.3.19/linux/arch/i386/kernel/entry.S linux/arch/i386/kernel/entry.S --- v2.3.19/linux/arch/i386/kernel/entry.S Tue Sep 7 12:14:06 1999 +++ linux/arch/i386/kernel/entry.S Thu Oct 7 10:17:08 1999 @@ -323,9 +323,14 @@ jmp error_code ENTRY(nmi) + pushl %eax + SAVE_ALL + movl %esp,%edx pushl $0 - pushl $ SYMBOL_NAME(do_nmi) - jmp error_code + pushl %edx + call SYMBOL_NAME(do_nmi) + addl $8,%esp + RESTORE_ALL ENTRY(int3) pushl $0 diff -u --recursive --new-file v2.3.19/linux/arch/i386/kernel/head.S linux/arch/i386/kernel/head.S --- v2.3.19/linux/arch/i386/kernel/head.S Sun Jul 11 09:11:46 1999 +++ linux/arch/i386/kernel/head.S Thu Oct 7 10:17:08 1999 @@ -243,6 +243,15 @@ xorl %eax,%eax lldt %ax cld # gcc2 wants the direction flag cleared at all times +#ifdef __SMP__ + movb ready, %cl + cmpb $1,%cl + je 1f # the first CPU calls start_kernel + # all other CPUs call initialize_secondary + call SYMBOL_NAME(initialize_secondary) + jmp L6 +1: +#endif call SYMBOL_NAME(start_kernel) L6: jmp L6 # main should never return here, but diff -u --recursive --new-file v2.3.19/linux/arch/i386/kernel/i386_ksyms.c linux/arch/i386/kernel/i386_ksyms.c --- v2.3.19/linux/arch/i386/kernel/i386_ksyms.c Tue Aug 31 17:29:12 1999 +++ linux/arch/i386/kernel/i386_ksyms.c Thu Oct 7 10:17:08 1999 @@ -8,6 +8,7 @@ #include #include #include +#include #include #include @@ -41,6 +42,7 @@ EXPORT_SYMBOL(disable_irq); EXPORT_SYMBOL(disable_irq_nosync); EXPORT_SYMBOL(kernel_thread); +EXPORT_SYMBOL(acpi_idle); EXPORT_SYMBOL_NOVERS(__down_failed); EXPORT_SYMBOL_NOVERS(__down_failed_interruptible); diff -u --recursive --new-file v2.3.19/linux/arch/i386/kernel/i8259.c linux/arch/i386/kernel/i8259.c --- v2.3.19/linux/arch/i386/kernel/i8259.c Mon Oct 4 15:49:29 1999 +++ linux/arch/i386/kernel/i8259.c Thu Oct 7 10:17:08 1999 @@ -1,7 +1,6 @@ #include #include #include -#include #include #include #include @@ -9,68 +8,23 @@ #include #include #include -#include #include #include +#include #include #include #include #include -#include #include #include #include #include - -/* - * Intel specific no controller code - * odd that no-controller should be architecture dependent - * but see the ifdef __SMP__ - */ - -static void enable_none(unsigned int irq) { } -static unsigned int startup_none(unsigned int irq) { return 0; } -static void disable_none(unsigned int irq) { } -static void ack_none(unsigned int irq) -{ -#ifdef __SMP__ - /* - * [currently unexpected vectors happen only on SMP and APIC. - * if we want to have non-APIC and non-8259A controllers - * in the future with unexpected vectors, this ack should - * probably be made controller-specific.] - */ - ack_APIC_irq(); -#endif -} - -/* startup is the same as "enable", shutdown is same as "disable" */ -#define shutdown_none disable_none -#define end_none enable_none - -struct hw_interrupt_type no_irq_type = { - "none", - startup_none, - shutdown_none, - enable_none, - disable_none, - ack_none, - end_none -}; - - -/* - * This is the 'legacy' 8259A Programmable Interrupt Controller, - * present in the majority of PC/AT boxes. - * plus some generic x86 specific things if generic specifics makes - * any sense at all. - * this file should become arch/i386/kernel/irq.c when the old irq.c - * moves to arch independent land - */ /* + * Common place to define all x86 IRQ vectors + * * This builds up the IRQ handler stubs using some ugly macros in irq.h * * These macros create the low-level assembly IRQ routines that save @@ -79,7 +33,6 @@ * interrupt-controller happy. */ - BUILD_COMMON_IRQ() #define BI(x,y) \ @@ -93,7 +46,7 @@ /* * ISA PIC or low IO-APIC triggered (INTA-cycle or APIC) interrupts: - * (these are usually mapped to vectors 0x20-0x30) + * (these are usually mapped to vectors 0x20-0x2f) */ BUILD_16_IRQS(0x0) @@ -126,9 +79,9 @@ */ BUILD_SMP_INTERRUPT(reschedule_interrupt,RESCHEDULE_VECTOR) BUILD_SMP_INTERRUPT(invalidate_interrupt,INVALIDATE_TLB_VECTOR) -BUILD_SMP_INTERRUPT(stop_cpu_interrupt,STOP_CPU_VECTOR) BUILD_SMP_INTERRUPT(call_function_interrupt,CALL_FUNCTION_VECTOR) BUILD_SMP_INTERRUPT(spurious_interrupt,SPURIOUS_APIC_VECTOR) +BUILD_SMP_INTERRUPT(error_interrupt,ERROR_APIC_VECTOR) /* * every pentium local APIC has two 'local interrupts', with a @@ -150,7 +103,7 @@ IRQ(x,8), IRQ(x,9), IRQ(x,a), IRQ(x,b), \ IRQ(x,c), IRQ(x,d), IRQ(x,e), IRQ(x,f) -static void (*interrupt[NR_IRQS])(void) = { +void (*interrupt[NR_IRQS])(void) = { IRQLIST_16(0x0), #ifdef CONFIG_X86_IO_APIC @@ -164,17 +117,23 @@ #undef IRQ #undef IRQLIST_16 +/* + * This is the 'legacy' 8259A Programmable Interrupt Controller, + * present in the majority of PC/AT boxes. + * plus some generic x86 specific things if generic specifics makes + * any sense at all. + * this file should become arch/i386/kernel/irq.c when the old irq.c + * moves to arch independent land + */ - - -static void enable_8259A_irq(unsigned int irq); +void enable_8259A_irq(unsigned int irq); void disable_8259A_irq(unsigned int irq); /* shutdown is same as "disable" */ #define end_8259A_irq enable_8259A_irq #define shutdown_8259A_irq disable_8259A_irq -static void mask_and_ack_8259A(unsigned int); +void mask_and_ack_8259A(unsigned int); static unsigned int startup_8259A_irq(unsigned int irq) { @@ -207,8 +166,8 @@ /* * Not all IRQs can be routed through the IO-APIC, eg. on certain (older) - * boards the timer interrupt is not connected to any IO-APIC pin, it's - * fed to the CPU IRQ line directly. + * boards the timer interrupt is not really connected to any IO-APIC pin, + * it's fed to the master 8259A's IR0 line only. * * Any '1' bit in this mask means the IRQ is routed through the IO-APIC. * this 'mixed mode' IRQ handling costs nothing because it's only used @@ -224,22 +183,20 @@ { unsigned int mask = 1 << irq; cached_irq_mask |= mask; - if (irq & 8) { + if (irq & 8) outb(cached_A1,0xA1); - } else { + else outb(cached_21,0x21); - } } -static void enable_8259A_irq(unsigned int irq) +void enable_8259A_irq(unsigned int irq) { unsigned int mask = ~(1 << irq); cached_irq_mask &= mask; - if (irq & 8) { + if (irq & 8) outb(cached_A1,0xA1); - } else { + else outb(cached_21,0x21); - } } int i8259A_irq_pending(unsigned int irq) @@ -260,26 +217,141 @@ } /* + * This function assumes to be called rarely. Switching between + * 8259A registers is slow. + */ +static inline int i8259A_irq_real(unsigned int irq) +{ + int value; + int irqmask = 1<> 8); + outb(0x0A,0xA0); /* back to the IRR register */ + return value; +} + +/* * Careful! The 8259A is a fragile beast, it pretty * much _has_ to be done exactly like this (mask it * first, _then_ send the EOI, and the order of EOI * to the two 8259s is important! */ -static void mask_and_ack_8259A(unsigned int irq) +void mask_and_ack_8259A(unsigned int irq) { - cached_irq_mask |= 1 << irq; + unsigned int irqmask = 1 << irq; + + /* + * Lightweight spurious IRQ detection. We do not want + * to overdo spurious IRQ handling - it's usually a sign + * of hardware problems, so we only do the checks we can + * do without slowing down good hardware unnecesserily. + * + * Note that IRQ7 and IRQ15 (the two spurious IRQs + * usually resulting from the 8259A-1|2 PICs) occur + * even if the IRQ is masked in the 8259A. Thus we + * can check spurious 8259A IRQs without doing the + * quite slow i8259A_irq_real() call for every IRQ. + * This does not cover 100% of spurious interrupts, + * but should be enough to warn the user that there + * is something bad going on ... + */ + if (cached_irq_mask & irqmask) + goto spurious_8259A_irq; + cached_irq_mask |= irqmask; + +handle_real_irq: if (irq & 8) { - inb(0xA1); /* DUMMY */ + inb(0xA1); /* DUMMY - (do we need this?) */ outb(cached_A1,0xA1); - outb(0x62,0x20); /* Specific EOI to cascade */ - outb(0x20,0xA0); + outb(0x62,0x20); /* 'Specific EOI' to master-IRQ2 */ + outb(0x20,0xA0); /* 'generic EOI' to slave */ } else { - inb(0x21); /* DUMMY */ + inb(0x21); /* DUMMY - (do we need this?) */ outb(cached_21,0x21); - outb(0x20,0x20); + outb(0x20,0x20); /* 'generic EOI' to master */ + } + return; + +spurious_8259A_irq: + /* + * this is the slow path - should happen rarely. + */ + if (i8259A_irq_real(irq)) + /* + * oops, the IRQ _is_ in service according to the + * 8259A - not spurious, go handle it. + */ + goto handle_real_irq; + + { + static int spurious_irq_mask = 0; + /* + * At this point we can be sure the IRQ is spurious, + * lets ACK and report it. [once per IRQ] + */ + if (!(spurious_irq_mask & irqmask)) { + printk("spurious 8259A interrupt: IRQ%d.\n", irq); + spurious_irq_mask |= irqmask; + } + irq_err_count++; + /* + * Theoretically we do not have to handle this IRQ, + * but in Linux this does not cause problems and is + * simpler for us. + */ + goto handle_real_irq; } } +void init_8259A(int auto_eoi) +{ + unsigned long flags; + + save_flags(flags); + cli(); + + outb(0xff, 0x21); /* mask all of 8259A-1 */ + outb(0xff, 0xA1); /* mask all of 8259A-2 */ + + /* + * outb_p - this has to work on a wide range of PC hardware. + */ + outb_p(0x11, 0x20); /* ICW1: select 8259A-1 init */ + outb_p(0x20 + 0, 0x21); /* ICW2: 8259A-1 IR0-7 mapped to 0x20-0x27 */ + outb_p(0x04, 0x21); /* 8259A-1 (the master) has a slave on IR2 */ + if (auto_eoi) + outb_p(0x03, 0x21); /* master does Auto EOI */ + else + outb_p(0x01, 0x21); /* master expects normal EOI */ + + outb_p(0x11, 0xA0); /* ICW1: select 8259A-2 init */ + outb_p(0x20 + 8, 0xA1); /* ICW2: 8259A-2 IR0-7 mapped to 0x28-0x2f */ + outb_p(0x02, 0xA1); /* 8259A-2 is a slave on master's IR2 */ + outb_p(0x01, 0xA1); /* (slave's support for AEOI in flat mode + is to be investigated) */ + + if (auto_eoi) + /* + * in AEOI mode we just have to mask the interrupt + * when acking. + */ + i8259A_irq_type.ack = disable_8259A_irq; + + udelay(100); /* wait for 8259A to initialize */ + + outb(cached_21, 0x21); /* restore master IRQ mask */ + outb(cached_A1, 0xA1); /* restore slave IRQ mask */ + + restore_flags(flags); +} + #ifndef CONFIG_VISWS /* * Note that on a 486, we don't want to do a SIGFPE on an irq13 @@ -307,7 +379,7 @@ * IRQ2 is cascade interrupt to second interrupt controller */ -static struct irqaction irq2 = { no_action, 0, 0, "cascade", NULL, NULL}; +static struct irqaction irq2 = { no_action, 0, 0, "cascade", NULL, NULL}; #endif @@ -315,6 +387,8 @@ { int i; + init_8259A(0); + for (i = 0; i < NR_IRQS; i++) { irq_desc[i].status = IRQ_DISABLED; irq_desc[i].action = 0; @@ -357,9 +431,9 @@ #ifdef __SMP__ /* - IRQ0 must be given a fixed assignment and initialized - before init_IRQ_SMP. - */ + * IRQ0 must be given a fixed assignment and initialized, + * because it's used before the IO-APIC is set up. + */ set_intr_gate(IRQ0_TRAP_VECTOR, interrupt[0]); /* @@ -371,17 +445,15 @@ /* IPI for invalidation */ set_intr_gate(INVALIDATE_TLB_VECTOR, invalidate_interrupt); - /* IPI for CPU halt */ - set_intr_gate(STOP_CPU_VECTOR, stop_cpu_interrupt); - /* self generated IPI for local APIC timer */ set_intr_gate(LOCAL_TIMER_VECTOR, apic_timer_interrupt); /* IPI for generic function call */ set_intr_gate(CALL_FUNCTION_VECTOR, call_function_interrupt); - /* IPI vector for APIC spurious interrupts */ + /* IPI vectors for APIC spurious and error interrupts */ set_intr_gate(SPURIOUS_APIC_VECTOR, spurious_interrupt); + set_intr_gate(ERROR_APIC_VECTOR, error_interrupt); #endif /* @@ -397,13 +469,3 @@ setup_irq(13, &irq13); #endif } - -#ifdef CONFIG_X86_IO_APIC -void __init init_IRQ_SMP(void) -{ - int i; - for (i = 0; i < NR_IRQS ; i++) - if (IO_APIC_VECTOR(i) > 0) - set_intr_gate(IO_APIC_VECTOR(i), interrupt[i]); -} -#endif diff -u --recursive --new-file v2.3.19/linux/arch/i386/kernel/io_apic.c linux/arch/i386/kernel/io_apic.c --- v2.3.19/linux/arch/i386/kernel/io_apic.c Tue Aug 31 17:29:12 1999 +++ linux/arch/i386/kernel/io_apic.c Thu Oct 7 10:17:08 1999 @@ -1,7 +1,7 @@ /* * Intel IO-APIC support for multi-Pentium hosts. * - * Copyright (C) 1997, 1998 Ingo Molnar, Hajnalka Szabo + * Copyright (C) 1997, 1998, 1999 Ingo Molnar, Hajnalka Szabo * * Many thanks to Stig Venaas for trying out countless experimental * patches and reporting/debugging problems patiently! @@ -18,15 +18,21 @@ #include #include #include +#include #include +#undef __init +#define __init + /* * volatile is justified in this case, IO-APIC register contents * might change spontaneously, GCC should not cache it */ #define IO_APIC_BASE(idx) ((volatile int *)__fix_to_virt(FIX_IO_APIC_BASE_0 + idx)) +extern int nmi_watchdog; + /* * The structure of the IO-APIC: */ @@ -59,6 +65,11 @@ enum ioapic_irq_destination_types { dest_Fixed = 0, dest_LowestPrio = 1, + dest_SMI = 2, + dest__reserved_1 = 3, + dest_NMI = 4, + dest_INIT = 5, + dest__reserved_2 = 6, dest_ExtINT = 7 }; @@ -94,14 +105,7 @@ * MP-BIOS irq configuration table structures: */ -enum mp_irq_source_types { - mp_INT = 0, - mp_NMI = 1, - mp_SMI = 2, - mp_ExtINT = 3 -}; - -struct mpc_config_ioapic mp_apics[MAX_IO_APICS];/* I/O APIC entries */ +struct mpc_config_ioapic mp_ioapics[MAX_IO_APICS];/* I/O APIC entries */ int mp_irq_entries = 0; /* # of MP IRQ source entries */ struct mpc_config_intsrc mp_irqs[MAX_IRQ_SOURCES]; /* MP IRQ source entries */ @@ -202,16 +206,10 @@ FINAL; \ } -/* - * We disable IO-APIC IRQs by setting their 'destination CPU mask' to - * zero. Trick by Ramesh Nalluri. - */ -DO_ACTION( disable, 1, &= 0x00ffffff, io_apic_sync(entry->apic))/* destination = 0x00 */ -DO_ACTION( enable, 1, |= 0xff000000, ) /* destination = 0xff */ DO_ACTION( mask, 0, |= 0x00010000, io_apic_sync(entry->apic))/* mask = 1 */ DO_ACTION( unmask, 0, &= 0xfffeffff, ) /* mask = 0 */ -static void clear_IO_APIC_pin(unsigned int apic, unsigned int pin) +void clear_IO_APIC_pin(unsigned int apic, unsigned int pin) { struct IO_APIC_route_entry entry; @@ -289,7 +287,7 @@ for (i = 0; i < mp_irq_entries; i++) if ( (mp_irqs[i].mpc_irqtype == type) && - (mp_irqs[i].mpc_dstapic == mp_apics[apic].mpc_apicid) && + (mp_irqs[i].mpc_dstapic == mp_ioapics[apic].mpc_apicid) && (mp_irqs[i].mpc_dstirq == pin)) return i; @@ -330,7 +328,7 @@ int lbus = mp_irqs[i].mpc_srcbus; for (apic = 0; apic < nr_ioapics; apic++) - if (mp_apics[apic].mpc_apicid == mp_irqs[i].mpc_dstapic) + if (mp_ioapics[apic].mpc_apicid == mp_irqs[i].mpc_dstapic) break; if ((apic || IO_APIC_IRQ(mp_irqs[i].mpc_dstirq)) && @@ -589,24 +587,30 @@ static int current_vector = IRQ0_TRAP_VECTOR, offset = 0; if (IO_APIC_VECTOR(irq) > 0) return IO_APIC_VECTOR(irq); + if (current_vector == 0xFF) + panic("ran out of interrupt sources!"); +next: current_vector += 8; - if (current_vector > 0xFE) { + if (current_vector == SYSCALL_VECTOR) + goto next; + + if (current_vector > 0xFF) { offset++; current_vector = IRQ0_TRAP_VECTOR + offset; - printk("WARNING: ASSIGN_IRQ_VECTOR wrapped back to %02X\n", - current_vector); } - if (current_vector == SYSCALL_VECTOR) - panic("ran out of interrupt sources!"); IO_APIC_VECTOR(irq) = current_vector; return current_vector; } +extern void (*interrupt[NR_IRQS])(void); +static struct hw_interrupt_type ioapic_level_irq_type; +static struct hw_interrupt_type ioapic_edge_irq_type; + void __init setup_IO_APIC_irqs(void) { struct IO_APIC_route_entry entry; - int apic, pin, idx, irq, first_notcon = 1; + int apic, pin, idx, irq, first_notcon = 1, vector; printk("init IO_APIC IRQs\n"); @@ -621,15 +625,15 @@ entry.delivery_mode = dest_LowestPrio; entry.dest_mode = 1; /* logical delivery */ entry.mask = 0; /* enable IRQ */ - entry.dest.logical.logical_dest = 0; /* but no route */ + entry.dest.logical.logical_dest = APIC_ALL_CPUS; /* all CPUs */ idx = find_irq_entry(apic,pin,mp_INT); if (idx == -1) { if (first_notcon) { - printk(" IO-APIC (apicid-pin) %d-%d", mp_apics[apic].mpc_apicid, pin); + printk(" IO-APIC (apicid-pin) %d-%d", mp_ioapics[apic].mpc_apicid, pin); first_notcon = 0; } else - printk(", %d-%d", mp_apics[apic].mpc_apicid, pin); + printk(", %d-%d", mp_ioapics[apic].mpc_apicid, pin); continue; } @@ -639,17 +643,29 @@ if (irq_trigger(idx)) { entry.trigger = 1; entry.mask = 1; - entry.dest.logical.logical_dest = 0xff; + entry.dest.logical.logical_dest = APIC_ALL_CPUS; } - irq = pin_2_irq(idx,apic,pin); + irq = pin_2_irq(idx, apic, pin); add_pin_to_irq(irq, apic, pin); if (!apic && !IO_APIC_IRQ(irq)) continue; - entry.vector = assign_irq_vector(irq); + if (IO_APIC_IRQ(irq)) { + vector = assign_irq_vector(irq); + entry.vector = vector; + + if (IO_APIC_irq_trigger(irq)) + irq_desc[irq].handler = &ioapic_level_irq_type; + else + irq_desc[irq].handler = &ioapic_edge_irq_type; + set_intr_gate(vector, interrupt[irq]); + + if (!apic && (irq < 16)) + disable_8259A_irq(irq); + } io_apic_write(apic, 0x11+2*pin, *(((int *)&entry)+1)); io_apic_write(apic, 0x10+2*pin, *(((int *)&entry)+0)); } @@ -660,34 +676,47 @@ } /* - * Set up a certain pin as ExtINT delivered interrupt + * Set up the 8259A-master output pin as broadcast to all + * CPUs. */ -void __init setup_ExtINT_pin(unsigned int apic, unsigned int pin, int irq) +void __init setup_ExtINT_IRQ0_pin(unsigned int pin, int vector) { struct IO_APIC_route_entry entry; - /* - * add it to the IO-APIC irq-routing table: - */ memset(&entry,0,sizeof(entry)); - entry.delivery_mode = dest_ExtINT; - entry.dest_mode = 0; /* physical delivery */ - entry.mask = 0; /* unmask IRQ now */ - /* - * We use physical delivery to get the timer IRQ - * to the boot CPU. 'boot_cpu_id' is the physical - * APIC ID of the boot CPU. - */ - entry.dest.physical.physical_dest = boot_cpu_id; + disable_8259A_irq(0); + + apic_readaround(APIC_LVT0); + apic_write(APIC_LVT0, 0x00010700); // mask LVT0 - entry.vector = assign_irq_vector(irq); + init_8259A(1); + /* + * We use logical delivery to get the timer IRQ + * to the first CPU. + */ + entry.dest_mode = 1; /* logical delivery */ + entry.mask = 0; /* unmask IRQ now */ + entry.dest.logical.logical_dest = APIC_ALL_CPUS; + entry.delivery_mode = dest_LowestPrio; entry.polarity = 0; entry.trigger = 0; + entry.vector = vector; + + /* + * The timer IRQ doesnt have to know that behind the + * scene we have a 8259A-master in AEOI mode ... + */ + irq_desc[0].handler = &ioapic_edge_irq_type; - io_apic_write(apic, 0x10+2*pin, *(((int *)&entry)+0)); - io_apic_write(apic, 0x11+2*pin, *(((int *)&entry)+1)); + /* + * Add it to the IO-APIC irq-routing table: + */ + io_apic_write(0, 0x10+2*pin, *(((int *)&entry)+0)); + io_apic_write(0, 0x11+2*pin, *(((int *)&entry)+1)); + + enable_8259A_irq(0); } void __init UNEXPECTED_IO_APIC(void) @@ -705,7 +734,7 @@ printk("number of MP IRQ sources: %d.\n", mp_irq_entries); for (i = 0; i < nr_ioapics; i++) - printk("number of IO-APIC #%d registers: %d.\n", mp_apics[i].mpc_apicid, nr_ioapic_registers[i]); + printk("number of IO-APIC #%d registers: %d.\n", mp_ioapics[i].mpc_apicid, nr_ioapic_registers[i]); /* * We are a bit conservative about what we expect. We have to @@ -717,8 +746,10 @@ *(int *)®_00 = io_apic_read(apic, 0); *(int *)®_01 = io_apic_read(apic, 1); - *(int *)®_02 = io_apic_read(apic, 2); - printk("\nIO APIC #%d......\n", mp_apics[apic].mpc_apicid); + if (reg_01.version >= 0x10) + *(int *)®_02 = io_apic_read(apic, 2); + + printk("\nIO APIC #%d......\n", mp_ioapics[apic].mpc_apicid); printk(".... register #00: %08X\n", *(int *)®_00); printk("....... : physical APIC id: %02X\n", reg_00.ID); if (reg_00.__reserved_1 || reg_00.__reserved_2) @@ -730,12 +761,15 @@ (reg_01.entries != 0x17) && /* typical ISA+PCI boards */ (reg_01.entries != 0x1b) && /* Compaq Proliant boards */ (reg_01.entries != 0x1f) && /* dual Xeon boards */ - (reg_01.entries != 0x3F) /* bigger Xeon boards */ + (reg_01.entries != 0x22) && /* bigger Xeon boards */ + (reg_01.entries != 0x2E) && + (reg_01.entries != 0x3F) ) UNEXPECTED_IO_APIC(); printk("....... : IO APIC version: %04X\n", reg_01.version); - if ( (reg_01.version != 0x10) && /* oldest IO-APICs */ + if ( (reg_01.version != 0x01) && /* 82489DX IO-APICs */ + (reg_01.version != 0x10) && /* oldest IO-APICs */ (reg_01.version != 0x11) && /* Pentium/Pro IO-APICs */ (reg_01.version != 0x13) /* Xeon IO-APICs */ ) @@ -743,10 +777,12 @@ if (reg_01.__reserved_1 || reg_01.__reserved_2) UNEXPECTED_IO_APIC(); - printk(".... register #02: %08X\n", *(int *)®_02); - printk("....... : arbitration: %02X\n", reg_02.arbitration); - if (reg_02.__reserved_1 || reg_02.__reserved_2) - UNEXPECTED_IO_APIC(); + if (reg_01.version >= 0x10) { + printk(".... register #02: %08X\n", *(int *)®_02); + printk("....... : arbitration: %02X\n", reg_02.arbitration); + if (reg_02.__reserved_1 || reg_02.__reserved_2) + UNEXPECTED_IO_APIC(); + } printk(".... IRQ redirection table:\n"); @@ -797,8 +833,116 @@ return; } +static void print_APIC_bitfield (int base) +{ + unsigned int v; + int i, j; + + printk("0123456789abcdef0123456789abcdef\n"); + for (i = 0; i < 8; i++) { + v = apic_read(base + i*0x10); + for (j = 0; j < 32; j++) { + if (v & (1< 3) { + apic_readaround(APIC_SPIV); // not strictly necessery + apic_write(APIC_ESR, 0); + } + v = apic_read(APIC_ESR); + printk("... APIC ESR: %08x\n", v); + } + + v = apic_read(APIC_ICR); + printk("... APIC ICR: %08x\n", v); + v = apic_read(APIC_ICR2); + printk("... APIC ICR2: %08x\n", v); + + v = apic_read(APIC_LVTT); + printk("... APIC LVTT: %08x\n", v); + + if (maxlvt > 3) { /* PC is LVT#4. */ + v = apic_read(APIC_LVTPC); + printk("... APIC LVTPC: %08x\n", v); + } + v = apic_read(APIC_LVT0); + printk("... APIC LVT0: %08x\n", v); + v = apic_read(APIC_LVT1); + printk("... APIC LVT1: %08x\n", v); + + if (maxlvt > 2) { /* ERR is LVT#3. */ + v = apic_read(APIC_LVTERR); + printk("... APIC LVTERR: %08x\n", v); + } + + v = apic_read(APIC_TMICT); + printk("... APIC TMICT: %08x\n", v); + v = apic_read(APIC_TMCCT); + printk("... APIC TMCCT: %08x\n", v); + v = apic_read(APIC_TDCR); + printk("... APIC TDCR: %08x\n", v); + printk("\n"); +} + +void print_all_local_APICs (void) +{ + smp_call_function(print_local_APIC, NULL, 1, 1); + print_local_APIC(NULL); +} + static void __init init_sym_mode(void) { + struct IO_APIC_reg_01 reg_01; int i; for (i = 0; i < PIN_MAP_SIZE; i++) { @@ -809,24 +953,21 @@ for (i = 0; i < MAX_PIRQS; i++) pirq_entries[i] =- 1; - printk("enabling symmetric IO mode... "); - - outb(0x70, 0x22); - outb(0x01, 0x23); - - printk("...done.\n"); + if (pic_mode) { + /* + * PIC mode, enable symmetric IO mode in the IMCR. + */ + printk("leaving PIC mode, enabling symmetric IO mode.\n"); + outb(0x70, 0x22); + outb(0x01, 0x23); + } /* * The number of IO-APIC IRQ registers (== #pins): */ - { - struct IO_APIC_reg_01 reg_01; - int i; - - for (i = 0; i < nr_ioapics; i++) { - *(int *)®_01 = io_apic_read(i, 1); - nr_ioapic_registers[i] = reg_01.entries+1; - } + for (i = 0; i < nr_ioapics; i++) { + *(int *)®_01 = io_apic_read(i, 1); + nr_ioapic_registers[i] = reg_01.entries+1; } /* @@ -835,24 +976,41 @@ clear_IO_APIC(); } +static void clear_lapic_ints (void * dummy) +{ + int maxlvt; + + maxlvt = get_maxlvt(); + apic_write_around(APIC_LVTT, 0x00010000); + apic_write_around(APIC_LVT0, 0x00010000); + apic_write_around(APIC_LVT1, 0x00010000); + if (maxlvt >= 3) + apic_write_around(APIC_LVTERR, 0x00010000); + if (maxlvt >= 4) + apic_write_around(APIC_LVTPC, 0x00010000); +} + /* * Not an __init, needed by the reboot code */ void init_pic_mode(void) { /* - * Clear the IO-APIC before rebooting: + * Clear the IO-APIC and local APICs before rebooting: */ clear_IO_APIC(); + smp_call_function(clear_lapic_ints, NULL, 1, 1); + clear_lapic_ints(NULL); /* * Put it back into PIC mode (has an effect only on - * certain boards) + * certain older boards) */ - printk("disabling symmetric IO mode... "); + if (pic_mode) { + printk("disabling symmetric IO mode, entering PIC mode.\n"); outb_p(0x70, 0x22); outb_p(0x00, 0x23); - printk("...done.\n"); + } } static void __init setup_ioapic_id(void) @@ -914,10 +1072,13 @@ * MP specification 1.4 defines some extra rules for default * configurations, fix them up here: */ - switch (mpc_default_type) { case 2: + /* + * IRQ0 is not connected: + */ + mp_irqs[0].mpc_irqtype = mp_ExtINT; break; default: /* @@ -942,7 +1103,7 @@ unsigned int t1 = jiffies; sti(); - mdelay(100); + mdelay(40); if (jiffies-t1>1) return 1; @@ -950,6 +1111,27 @@ return 0; } +extern atomic_t nmi_counter[NR_CPUS]; + +static int __init nmi_irq_works(void) +{ + atomic_t tmp[NR_CPUS]; + int j, cpu; + + memcpy(tmp, nmi_counter, sizeof(tmp)); + sti(); + mdelay(50); + + for (j = 0; j < smp_num_cpus; j++) { + cpu = cpu_logical_map(j); + if (atomic_read(nmi_counter+cpu) - atomic_read(tmp+cpu) <= 3) { + printk("CPU#%d NMI appears to be stuck.\n", cpu); + return 0; + } + } + return 1; +} + /* * In the SMP+IOAPIC case it might happen that there are an unspecified * number of pending IRQ events unhandled. These cases are very rare, @@ -964,12 +1146,11 @@ */ static void enable_edge_ioapic_irq(unsigned int irq) { - enable_IO_APIC_irq(irq); + unmask_IO_APIC_irq(irq); } static void disable_edge_ioapic_irq(unsigned int irq) { - disable_IO_APIC_irq(irq); } /* @@ -995,8 +1176,17 @@ } #define shutdown_edge_ioapic_irq disable_edge_ioapic_irq -void static ack_edge_ioapic_irq(unsigned int i) -{ + +/* + * Once we have recorded IRQ_PENDING already, we can mask the + * interrupt for real. This prevents IRQ storms from unhandled + * devices. + */ +void static ack_edge_ioapic_irq(unsigned int irq) +{ + if ((irq_desc[irq].status & (IRQ_PENDING | IRQ_DISABLED)) + == (IRQ_PENDING | IRQ_DISABLED)) + mask_IO_APIC_irq(irq); ack_APIC_irq(); } void static end_edge_ioapic_irq(unsigned int i){} @@ -1055,7 +1245,8 @@ static inline void init_IO_APIC_traps(void) { - int i; + int irq; + /* * NOTE! The local APIC isn't very good at handling * multiple interrupts at the same interrupt level. @@ -1067,36 +1258,62 @@ * Also, we've got to be careful not to trash gate * 0x80, because int 0x80 is hm, kind of importantish. ;) */ - for (i = 0; i < NR_IRQS ; i++) { - if (IO_APIC_VECTOR(i) > 0) { - if (IO_APIC_irq_trigger(i)) - irq_desc[i].handler = &ioapic_level_irq_type; - else - irq_desc[i].handler = &ioapic_edge_irq_type; - /* - * disable it in the 8259A: - */ - if (i < 16) - disable_8259A_irq(i); - } else { - if (!IO_APIC_IRQ(i)) - continue; - + for (irq = 0; irq < NR_IRQS ; irq++) { + if (IO_APIC_IRQ(irq) && !IO_APIC_VECTOR(irq)) { /* * Hmm.. We don't have an entry for this, * so default to an old-fashioned 8259 * interrupt if we can.. */ - if (i < 16) { - make_8259A_irq(i); - continue; - } - - /* Strange. Oh, well.. */ - irq_desc[i].handler = &no_irq_type; + if (irq < 16) + make_8259A_irq(irq); + else + /* Strange. Oh, well.. */ + irq_desc[irq].handler = &no_irq_type; } } - init_IRQ_SMP(); +} + +void static ack_lapic_irq (unsigned int irq) +{ + ack_APIC_irq(); +} + +void static end_lapic_irq (unsigned int i) { /* nothing */ } + +static struct hw_interrupt_type lapic_irq_type = { + "local-APIC-edge", + NULL, /* startup_irq() not used for IRQ0 */ + NULL, /* shutdown_irq() not used for IRQ0 */ + NULL, /* enable_irq() not used for IRQ0 */ + NULL, /* disable_irq() not used for IRQ0 */ + ack_lapic_irq, + end_lapic_irq +}; + +static void enable_NMI_through_LVT0 (void * dummy) +{ + apic_readaround(APIC_LVT0); + apic_write(APIC_LVT0, 0x00000400); // unmask and set to NMI +} + +static void setup_nmi (void) +{ + /* + * Dirty trick to enable the NMI watchdog ... + * We put the 8259A master into AEOI mode and + * unmask on all local APICs LVT0 as NMI. + * + * The idea to use the 8259A in AEOI mode ('8259A Virtual Wire') + * is from Maciej W. Rozycki - so we do not have to EOI from + * the NMI handler or the timer interrupt. + */ + printk("activating NMI Watchdog ..."); + + smp_call_function(enable_NMI_through_LVT0, NULL, 1, 1); + enable_NMI_through_LVT0(NULL); + + printk(" done.\n"); } /* @@ -1108,45 +1325,78 @@ static inline void check_timer(void) { int pin1, pin2; + int vector; + + /* + * get/set the timer IRQ vector: + */ + vector = assign_irq_vector(0); + set_intr_gate(vector, interrupt[0]); pin1 = find_timer_pin(mp_INT); pin2 = find_timer_pin(mp_ExtINT); - enable_IO_APIC_irq(0); - if (!timer_irq_works()) { - if (pin1 != -1) - printk("..MP-BIOS bug: 8254 timer not connected to IO-APIC\n"); - printk("...trying to set up timer as ExtINT... "); - - if (pin2 != -1) { - printk(".. (found pin %d) ...", pin2); - /* - * legacy devices should be connected to IO APIC #0 - */ - setup_ExtINT_pin(0, pin2, 0); - make_8259A_irq(0); + /* + * Ok, does IRQ0 through the IOAPIC work? + */ + if (timer_irq_works()) { + if (nmi_watchdog) { + disable_8259A_irq(0); + init_8259A(1); + setup_nmi(); + enable_8259A_irq(0); + if (nmi_irq_works()) + return; + } else + return; + } + + if (pin1 != -1) { + printk("..MP-BIOS bug: 8254 timer not connected to IO-APIC\n"); + clear_IO_APIC_pin(0, pin1); + } + + printk("...trying to set up timer (IRQ0) through the 8259A ... "); + if (pin2 != -1) { + printk("\n..... (found pin %d) ...", pin2); + /* + * legacy devices should be connected to IO APIC #0 + */ + setup_ExtINT_IRQ0_pin(pin2, vector); + if (timer_irq_works()) { + printk("works.\n"); + if (nmi_watchdog) { + setup_nmi(); + if (nmi_irq_works()) + return; + } else + return; } + /* + * Cleanup, just in case ... + */ + clear_IO_APIC_pin(0, pin2); + } + printk(" failed.\n"); - if (!timer_irq_works()) { - printk(" failed.\n"); - printk("...trying to set up timer as BP IRQ..."); - /* - * Just in case ... - */ - if (pin1 != -1) - clear_IO_APIC_pin(0, pin1); - if (pin2 != -1) - clear_IO_APIC_pin(0, pin2); - - make_8259A_irq(0); - - if (!timer_irq_works()) { - printk(" failed.\n"); - panic("IO-APIC + timer doesn't work!"); - } - } + if (nmi_watchdog) + printk("timer doesnt work through the IO-APIC - cannot activate NMI Watchdog!\n"); + + printk("...trying to set up timer as Virtual Wire IRQ..."); + + disable_8259A_irq(0); + irq_desc[0].handler = &lapic_irq_type; + init_8259A(1); // AEOI mode + apic_readaround(APIC_LVT0); + apic_write(APIC_LVT0, 0x00000000 | vector); // Fixed mode + enable_8259A_irq(0); + + if (timer_irq_works()) { printk(" works.\n"); + return; } + printk(" failed :(.\n"); + panic("IO-APIC + timer doesn't work! pester mingo@redhat.com"); } /* @@ -1189,6 +1439,5 @@ setup_IO_APIC_irqs(); init_IO_APIC_traps(); check_timer(); - print_IO_APIC(); } diff -u --recursive --new-file v2.3.19/linux/arch/i386/kernel/irq.c linux/arch/i386/kernel/irq.c --- v2.3.19/linux/arch/i386/kernel/irq.c Tue Aug 31 17:29:12 1999 +++ linux/arch/i386/kernel/irq.c Thu Oct 7 10:17:08 1999 @@ -22,7 +22,6 @@ #include #include -#include #include #include #include @@ -30,14 +29,13 @@ #include #include #include -#include #include #include +#include #include #include #include -#include #include #include #include @@ -48,7 +46,7 @@ unsigned int local_bh_count[NR_CPUS]; unsigned int local_irq_count[NR_CPUS]; -atomic_t nmi_counter; +extern atomic_t nmi_counter[NR_CPUS]; /* * Linux has a controller-independent x86 interrupt architecture. @@ -75,7 +73,8 @@ /* * Controller mappings for all interrupt sources: */ -irq_desc_t irq_desc[NR_IRQS] __cacheline_aligned = { [0 ... NR_IRQS-1] = { 0, &no_irq_type, }}; +irq_desc_t irq_desc[NR_IRQS] __cacheline_aligned = + { [0 ... NR_IRQS-1] = { 0, &no_irq_type, }}; /* * Special irq handlers. @@ -84,6 +83,52 @@ void no_action(int cpl, void *dev_id, struct pt_regs *regs) { } /* + * Generic no controller code + */ + +static void enable_none(unsigned int irq) { } +static unsigned int startup_none(unsigned int irq) { return 0; } +static void disable_none(unsigned int irq) { } +static void ack_none(unsigned int irq) +{ +/* + * 'what should we do if we get a hw irq event on an illegal vector'. + * each architecture has to answer this themselves, it doesnt deserve + * a generic callback i think. + */ +#if CONFIG_X86 + printk("unexpected IRQ trap at vector %02x\n", irq); +#ifdef __SMP__ + /* + * Currently unexpected vectors happen only on SMP and APIC. + * We _must_ ack these because every local APIC has only N + * irq slots per priority level, and a 'hanging, unacked' IRQ + * holds up an irq slot - in excessive cases (when multiple + * unexpected vectors occur) that might lock up the APIC + * completely. + */ + ack_APIC_irq(); +#endif +#endif +} + +/* startup is the same as "enable", shutdown is same as "disable" */ +#define shutdown_none disable_none +#define end_none enable_none + +struct hw_interrupt_type no_irq_type = { + "none", + startup_none, + shutdown_none, + enable_none, + disable_none, + ack_none, + end_none +}; + +volatile unsigned long irq_err_count; + +/* * Generic, controller-independent functions: */ @@ -106,22 +151,30 @@ #ifndef __SMP__ p += sprintf(p, "%10u ", kstat_irqs(i)); #else - for (j=0; jtypename); p += sprintf(p, " %s", action->name); - for (action=action->next; action; action = action->next) { + for (action=action->next; action; action = action->next) p += sprintf(p, ", %s", action->name); - } *p++ = '\n'; } - p += sprintf(p, "NMI: %10u\n", atomic_read(&nmi_counter)); -#ifdef __SMP__ - p += sprintf(p, "ERR: %10lu\n", ipi_count); -#endif + p += sprintf(p, "NMI: "); + for (j = 0; j < smp_num_cpus; j++) + p += sprintf(p, "%10u ", + atomic_read(nmi_counter+cpu_logical_map(j))); + p += sprintf(p, "\n"); +#if CONFIG_SMP + p += sprintf(p, "LOC: "); + for (j = 0; j < smp_num_cpus; j++) + p += sprintf(p, "%10u ", + apic_timer_irqs[cpu_logical_map(j)]); + p += sprintf(p, "\n"); +#endif + p += sprintf(p, "ERR: %10lu\n", irq_err_count); return p - buf; } @@ -520,7 +573,7 @@ kstat.irqs[cpu][irq]++; desc = irq_desc + irq; spin_lock(&irq_controller_lock); - irq_desc[irq].handler->ack(irq); + desc->handler->ack(irq); /* REPLAY is when Linux resends an IRQ that was dropped earlier WAITING is used by probe to mark irqs that are being tested @@ -570,9 +623,8 @@ spin_unlock(&irq_controller_lock); } desc->status &= ~IRQ_INPROGRESS; - if (!(desc->status & IRQ_DISABLED)){ - irq_desc[irq].handler->end(irq); - } + if (!(desc->status & IRQ_DISABLED)) + desc->handler->end(irq); spin_unlock(&irq_controller_lock); /* diff -u --recursive --new-file v2.3.19/linux/arch/i386/kernel/mtrr.c linux/arch/i386/kernel/mtrr.c --- v2.3.19/linux/arch/i386/kernel/mtrr.c Mon Oct 4 15:49:29 1999 +++ linux/arch/i386/kernel/mtrr.c Sat Oct 9 11:25:51 1999 @@ -223,6 +223,8 @@ 19990819 Alan Cox Tested Zoltan's changes on a pre production Athlon - 100% success. + 19991008 Manfred Spraul + replaced spin_lock_reschedule() with a normal semaphore. */ #include #include @@ -303,8 +305,6 @@ TRUE) #endif -#define spin_lock_reschedule(lock) while (!spin_trylock(lock)) schedule (); - #ifndef CONFIG_PROC_FS # define compute_ascii() while (0) #endif @@ -314,7 +314,7 @@ static unsigned int ascii_buf_bytes = 0; #endif static unsigned int *usage_table = NULL; -static spinlock_t main_lock = SPIN_LOCK_UNLOCKED; +static DECLARE_MUTEX(main_lock); /* Private functions */ #ifdef CONFIG_PROC_FS @@ -1172,7 +1172,7 @@ increment = increment ? 1 : 0; max = get_num_var_ranges (); /* Search for existing MTRR */ - spin_lock_reschedule (&main_lock); + down(&main_lock); for (i = 0; i < max; ++i) { (*get_mtrr) (i, &lbase, &lsize, <ype); @@ -1181,7 +1181,7 @@ /* At this point we know there is some kind of overlap/enclosure */ if ( (base < lbase) || (base + size > lbase + lsize) ) { - spin_unlock (&main_lock); + up(&main_lock); printk ("mtrr: 0x%lx,0x%lx overlaps existing 0x%lx,0x%lx\n", base, size, lbase, lsize); return -EINVAL; @@ -1190,14 +1190,14 @@ if (ltype != type) { if (type == MTRR_TYPE_UNCACHABLE) continue; - spin_unlock (&main_lock); + up(&main_lock); printk ( "mtrr: type mismatch for %lx,%lx old: %s new: %s\n", base, size, attrib_to_str (ltype), attrib_to_str (type) ); return -EINVAL; } if (increment) ++usage_table[i]; compute_ascii (); - spin_unlock (&main_lock); + up(&main_lock); return i; } /* Search for an empty MTRR */ @@ -1211,7 +1211,7 @@ set_mtrr (i, base, size, type); usage_table[i] = 1; compute_ascii (); - spin_unlock (&main_lock); + up(&main_lock); return i; } /* End Function mtrr_add */ @@ -1232,7 +1232,7 @@ if ( !(boot_cpu_data.x86_capability & X86_FEATURE_MTRR) ) return -ENODEV; max = get_num_var_ranges (); - spin_lock_reschedule (&main_lock); + down(&main_lock); if (reg < 0) { /* Search for existing MTRR */ @@ -1247,14 +1247,14 @@ } if (reg < 0) { - spin_unlock (&main_lock); + up(&main_lock); printk ("mtrr: no MTRR for %lx,%lx found\n", base, size); return -EINVAL; } } if (reg >= max) { - spin_unlock (&main_lock); + up(&main_lock); printk ("mtrr: register: %d too big\n", reg); return -EINVAL; } @@ -1262,7 +1262,7 @@ { if ((reg == 3) && arr3_protected) { - spin_unlock (&main_lock); + up(&main_lock); printk ("mtrr: ARR3 cannot be changed\n"); return -EINVAL; } @@ -1270,19 +1270,19 @@ (*get_mtrr) (reg, &lbase, &lsize, <ype); if (lsize < 1) { - spin_unlock (&main_lock); + up(&main_lock); printk ("mtrr: MTRR %d not used\n", reg); return -EINVAL; } if (usage_table[reg] < 1) { - spin_unlock (&main_lock); + up(&main_lock); printk ("mtrr: reg: %d has count=0\n", reg); return -EINVAL; } if (--usage_table[reg] < 1) set_mtrr (reg, 0, 0, 0); compute_ascii (); - spin_unlock (&main_lock); + up(&main_lock); return reg; } /* End Function mtrr_del */ diff -u --recursive --new-file v2.3.19/linux/arch/i386/kernel/pci-i386.c linux/arch/i386/kernel/pci-i386.c --- v2.3.19/linux/arch/i386/kernel/pci-i386.c Wed Dec 31 16:00:00 1969 +++ linux/arch/i386/kernel/pci-i386.c Fri Oct 8 10:06:21 1999 @@ -0,0 +1,312 @@ +/* + * Low-Level PCI Access for i386 machines + * + * Copyright 1993, 1994 Drew Eckhardt + * Visionary Computing + * (Unix and Linux consulting and custom programming) + * Drew@Colorado.EDU + * +1 (303) 786-7975 + * + * Drew's work was sponsored by: + * iX Multiuser Multitasking Magazine + * Hannover, Germany + * hm@ix.de + * + * Copyright 1997--1999 Martin Mares + * + * For more information, please consult the following manuals (look at + * http://www.pcisig.com/ for how to get them): + * + * PCI BIOS Specification + * PCI Local Bus Specification + * PCI to PCI Bridge Specification + * PCI System Design Guide + * + * + * CHANGELOG : + * Jun 17, 1994 : Modified to accommodate the broken pre-PCI BIOS SPECIFICATION + * Revision 2.0 present on 's ASUS mainboard. + * + * Jan 5, 1995 : Modified to probe PCI hardware at boot time by Frederic + * Potter, potter@cao-vlsi.ibp.fr + * + * Jan 10, 1995 : Modified to store the information about configured pci + * devices into a list, which can be accessed via /proc/pci by + * Curtis Varner, cvarner@cs.ucr.edu + * + * Jan 12, 1995 : CPU-PCI bridge optimization support by Frederic Potter. + * Alpha version. Intel & UMC chipset support only. + * + * Apr 16, 1995 : Source merge with the DEC Alpha PCI support. Most of the code + * moved to drivers/pci/pci.c. + * + * Dec 7, 1996 : Added support for direct configuration access of boards + * with Intel compatible access schemes (tsbogend@alpha.franken.de) + * + * Feb 3, 1997 : Set internal functions to static, save/restore flags + * avoid dead locks reading broken PCI BIOS, werner@suse.de + * + * Apr 26, 1997 : Fixed case when there is BIOS32, but not PCI BIOS + * (mj@atrey.karlin.mff.cuni.cz) + * + * May 7, 1997 : Added some missing cli()'s. [mj] + * + * Jun 20, 1997 : Corrected problems in "conf1" type accesses. + * (paubert@iram.es) + * + * Aug 2, 1997 : Split to PCI BIOS handling and direct PCI access parts + * and cleaned it up... Martin Mares + * + * Feb 6, 1998 : No longer using BIOS to find devices and device classes. [mj] + * + * May 1, 1998 : Support for peer host bridges. [mj] + * + * Jun 19, 1998 : Changed to use spinlocks, so that PCI configuration space + * can be accessed from interrupts even on SMP systems. [mj] + * + * August 1998 : Better support for peer host bridges and more paranoid + * checks for direct hardware access. Ugh, this file starts to look as + * a large gallery of common hardware bug workarounds (watch the comments) + * -- the PCI specs themselves are sane, but most implementors should be + * hit hard with \hammer scaled \magstep5. [mj] + * + * Jan 23, 1999 : More improvements to peer host bridge logic. i450NX fixup. [mj] + * + * Feb 8, 1999 : Added UM8886BF I/O address fixup. [mj] + * + * August 1999 : New resource management and configuration access stuff. [mj] + * + * Sep 19, 1999 : Use PCI IRQ routing tables for detection of peer host bridges. + * Based on ideas by Chris Frantz and David Hinds. [mj] + * + * Sep 28, 1999 : Handle unreported/unassigned IRQs. Thanks to Shuu Yamaguchi + * for a lot of patience during testing. [mj] + * + * Oct 8, 1999 : Split to pci-i386.c, pci-pc.c and pci-visws.c. [mj] + */ + +#include +#include +#include +#include +#include +#include + +#include "pci-i386.h" + +/* + * Assign new address to PCI resource. We hope our resource information + * is complete. On the PC, we don't re-assign resources unless we are + * forced to do so. + * + * Expects start=0, end=size-1, flags=resource type. + */ + +static int __init pcibios_assign_resource(struct pci_dev *dev, int i) +{ + struct resource *r = &dev->resource[i]; + struct resource *pr = pci_find_parent_resource(dev, r); + unsigned long size = r->end + 1; + u32 new, check; + + if (!pr) { + printk(KERN_ERR "PCI: Cannot find parent resource for device %s\n", dev->slot_name); + return -EINVAL; + } + if (r->flags & IORESOURCE_IO) { + /* + * We need to avoid collisions with `mirrored' VGA ports and other strange + * ISA hardware, so we always want the addresses kilobyte aligned. + */ + if (size > 0x100) { + printk(KERN_ERR "PCI: I/O Region %s/%d too large (%ld bytes)\n", dev->slot_name, i, size); + return -EFBIG; + } + if (allocate_resource(pr, r, size, 0x1000, ~0, 1024)) { + printk(KERN_ERR "PCI: Allocation of I/O region %s/%d (%ld bytes) failed\n", dev->slot_name, i, size); + return -EBUSY; + } + } else { + if (allocate_resource(pr, r, size, 0x10000000, ~0, size)) { + printk(KERN_ERR "PCI: Allocation of memory region %s/%d (%ld bytes) failed\n", dev->slot_name, i, size); + return -EBUSY; + } + } + if (i < 6) { + int reg = PCI_BASE_ADDRESS_0 + 4*i; + new = r->start | (r->flags & PCI_REGION_FLAG_MASK); + pci_write_config_dword(dev, reg, new); + pci_read_config_dword(dev, reg, &check); + if (new != check) + printk(KERN_ERR "PCI: Error while updating region %s/%d (%08x != %08x)\n", dev->slot_name, i, new, check); + } else if (i == PCI_ROM_RESOURCE) { + r->flags |= PCI_ROM_ADDRESS_ENABLE; + pci_write_config_dword(dev, dev->rom_base_reg, r->start | (r->flags & PCI_REGION_FLAG_MASK)); + } + printk("PCI: Assigned addresses %08lx-%08lx to region %s/%d\n", r->start, r->end, dev->slot_name, i); + return 0; +} + +/* + * Handle resources of PCI devices. If the world were perfect, we could + * just allocate all the resource regions and do nothing more. It isn't. + * On the other hand, we cannot just re-allocate all devices, as it would + * require us to know lots of host bridge internals. So we attempt to + * keep as much of the original configuration as possible, but tweak it + * when it's found to be wrong. + * + * Known BIOS problems we have to work around: + * - I/O or memory regions not configured + * - regions configured, but not enabled in the command register + * - bogus I/O addresses above 64K used + * - expansion ROMs left enabled (this may sound harmless, but given + * the fact the PCI specs explicitly allow address decoders to be + * shared between expansion ROMs and other resource regions, it's + * at least dangerous) + * + * Our solution: + * (1) Allocate resources for all buses behind PCI-to-PCI bridges. + * This gives us fixed barriers on where we can allocate. + * (2) Allocate resources for all enabled devices. If there is + * a collision, just mark the resource as unallocated. Also + * disable expansion ROMs during this step. + * (3) Try to allocate resources for disabled devices. If the + * resources were assigned correctly, everything goes well, + * if they weren't, they won't disturb allocation of other + * resources. + * (4) Assign new addresses to resources which were either + * not configured at all or misconfigured. If explicitly + * requested by the user, configure expansion ROM address + * as well. Finally enable the I/O and Memory bits. + */ + +static void __init pcibios_allocate_bus_resources(struct pci_bus *bus) +{ + struct pci_dev *dev; + int idx; + struct resource *r, *pr; + + /* Depth-First Search on bus tree */ + while (bus) { + if ((dev = bus->self)) { + for (idx = PCI_BRIDGE_RESOURCES; idx < PCI_NUM_RESOURCES; idx++) { + r = &dev->resource[idx]; + if (!r->start) + continue; + pr = pci_find_parent_resource(dev, r); + if (!pr || request_resource(pr, r) < 0) + printk(KERN_ERR "PCI: Cannot allocate resource region %d of bridge %s\n", idx, dev->slot_name); + } + } + if (bus->children) + pcibios_allocate_bus_resources(bus->children); + bus = bus->next; + } +} + +static void __init pcibios_allocate_resources(int pass) +{ + struct pci_dev *dev; + int idx, disabled; + u16 command; + struct resource *r, *pr; + + for(dev=pci_devices; dev; dev=dev->next) { + pci_read_config_word(dev, PCI_COMMAND, &command); + for(idx = 0; idx < 6; idx++) { + r = &dev->resource[idx]; + if (r->parent) /* Already allocated */ + continue; + if (!r->start) /* Address not assigned at all */ + continue; + if (r->flags & IORESOURCE_IO) + disabled = !(command & PCI_COMMAND_IO); + else + disabled = !(command & PCI_COMMAND_MEMORY); + if (pass == disabled) { + DBG("PCI: Resource %08lx-%08lx (f=%lx, d=%d, p=%d)\n", + r->start, r->end, r->flags, disabled, pass); + pr = pci_find_parent_resource(dev, r); + if (!pr || request_resource(pr, r) < 0) { + printk(KERN_ERR "PCI: Cannot allocate resource region %d of device %s\n", idx, dev->slot_name); + /* We'll assign a new address later */ + r->start -= r->end; + r->start = 0; + } + } + } + if (!pass) { + r = &dev->resource[PCI_ROM_RESOURCE]; + if (r->flags & PCI_ROM_ADDRESS_ENABLE) { + /* Turn the ROM off, leave the resource region, but keep it unregistered. */ + u32 reg; + DBG("PCI: Switching off ROM of %s\n", dev->slot_name); + r->flags &= ~PCI_ROM_ADDRESS_ENABLE; + pci_read_config_dword(dev, dev->rom_base_reg, ®); + pci_write_config_dword(dev, dev->rom_base_reg, reg & ~PCI_ROM_ADDRESS_ENABLE); + } + } + } +} + +static void __init pcibios_assign_resources(void) +{ + struct pci_dev *dev; + u16 cmd, old_cmd; + int idx; + int fault = 0; + struct resource *r; + + for(dev=pci_devices; dev; dev=dev->next) { + pci_read_config_word(dev, PCI_COMMAND, &cmd); + old_cmd = cmd; + for(idx=0; idx<6; idx++) { + r = &dev->resource[idx]; + if (((dev->class >> 8) == PCI_CLASS_STORAGE_IDE && idx < 4) || + ((dev->class >> 8) == PCI_CLASS_DISPLAY_VGA && (r->flags & IORESOURCE_IO))) + /* + * Don't touch IDE controllers and I/O ports of video cards! + * Neither enable anything in their command registers. + */ + continue; + if (!r->start && r->end) { + /* + * We shall assign a new address to this resource, either because + * the BIOS forgot to do so or because we have decided the old + * address was unusable for some reason. + */ + if (pcibios_assign_resource(dev, idx) < 0) + fault = 1; + } + if (r->flags & IORESOURCE_IO) + cmd |= PCI_COMMAND_IO; + if (r->flags & IORESOURCE_MEM) + cmd |= PCI_COMMAND_MEMORY; + } + + if (cmd != old_cmd) { + if (fault) + printk("PCI: Not enabling device %s because of resource collisions\n", dev->slot_name); + else { + printk("PCI: Enabling device %s (%04x -> %04x)\n", dev->slot_name, old_cmd, cmd); + pci_write_config_word(dev, PCI_COMMAND, cmd); + } + } + + if (pci_probe & PCI_ASSIGN_ROMS) { + r = &dev->resource[PCI_ROM_RESOURCE]; + r->end -= r->start; + r->start = 0; + if (r->end) + pcibios_assign_resource(dev, PCI_ROM_RESOURCE); + } + } +} + +void __init pcibios_resource_survey(void) +{ + pcibios_allocate_bus_resources(pci_root); + pcibios_allocate_resources(0); + pcibios_allocate_resources(1); + pcibios_assign_resources(); +} diff -u --recursive --new-file v2.3.19/linux/arch/i386/kernel/pci-i386.h linux/arch/i386/kernel/pci-i386.h --- v2.3.19/linux/arch/i386/kernel/pci-i386.h Wed Dec 31 16:00:00 1969 +++ linux/arch/i386/kernel/pci-i386.h Fri Oct 8 10:06:21 1999 @@ -0,0 +1,29 @@ +/* + * Low-Level PCI Access for i386 machines. + * + * (c) 1999 Martin Mares + */ + +#undef DEBUG + +#ifdef DEBUG +#define DBG(x...) printk(x) +#else +#define DBG(x...) +#endif + +#define PCI_PROBE_BIOS 1 +#define PCI_PROBE_CONF1 2 +#define PCI_PROBE_CONF2 4 +#define PCI_NO_SORT 0x100 +#define PCI_BIOS_SORT 0x200 +#define PCI_NO_CHECKS 0x400 +#define PCI_NO_PEER_FIXUP 0x800 +#define PCI_ASSIGN_ROMS 0x1000 +#define PCI_NO_IRQ_SCAN 0x2000 + +extern unsigned int pci_probe; + +/* pci-i386.c */ + +void pcibios_resource_survey(void); diff -u --recursive --new-file v2.3.19/linux/arch/i386/kernel/pci-pc.c linux/arch/i386/kernel/pci-pc.c --- v2.3.19/linux/arch/i386/kernel/pci-pc.c Wed Dec 31 16:00:00 1969 +++ linux/arch/i386/kernel/pci-pc.c Fri Oct 8 10:33:53 1999 @@ -0,0 +1,1225 @@ +/* + * Low-Level PCI Support for PC + * + * (c) 1999 Martin Mares + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include + +#include "pci-i386.h" + +unsigned int pci_probe = PCI_PROBE_BIOS | PCI_PROBE_CONF1 | PCI_PROBE_CONF2; + +/* + * IRQ routing table provided by the BIOS + */ + +struct irq_info { + u8 bus, devfn; /* Bus, device and function */ + struct { + u8 link; /* IRQ line ID, chipset dependent, 0=not routed */ + u16 bitmap; /* Available IRQs */ + } __attribute__((packed)) irq[4]; + u8 slot; /* Slot number, 0=onboard */ + u8 rfu; +} __attribute__((packed)); + +struct irq_routing_table { + u32 signature; /* PIRQ_SIGNATURE should be here */ + u16 version; /* PIRQ_VERSION */ + u16 size; /* Table size in bytes */ + u8 rtr_bus, rtr_devfn; /* Where the interrupt router lies */ + u16 exclusive_irqs; /* IRQs devoted exclusively to PCI usage */ + u16 rtr_vendor, rtr_device; /* Vendor and device ID of interrupt router */ + u32 miniport_data; /* Crap */ + u8 rfu[11]; + u8 checksum; /* Modulo 256 checksum must give zero */ + struct irq_info slots[0]; +} __attribute__((packed)); + +/* + * Direct access to PCI hardware... + */ + +#ifdef CONFIG_PCI_DIRECT + +/* + * Functions for accessing PCI configuration space with type 1 accesses + */ + +#define CONFIG_CMD(dev, where) (0x80000000 | (dev->bus->number << 16) | (dev->devfn << 8) | (where & ~3)) + +static int pci_conf1_read_config_byte(struct pci_dev *dev, int where, u8 *value) +{ + outl(CONFIG_CMD(dev,where), 0xCF8); + *value = inb(0xCFC + (where&3)); + return PCIBIOS_SUCCESSFUL; +} + +static int pci_conf1_read_config_word(struct pci_dev *dev, int where, u16 *value) +{ + outl(CONFIG_CMD(dev,where), 0xCF8); + *value = inw(0xCFC + (where&2)); + return PCIBIOS_SUCCESSFUL; +} + +static int pci_conf1_read_config_dword(struct pci_dev *dev, int where, u32 *value) +{ + outl(CONFIG_CMD(dev,where), 0xCF8); + *value = inl(0xCFC); + return PCIBIOS_SUCCESSFUL; +} + +static int pci_conf1_write_config_byte(struct pci_dev *dev, int where, u8 value) +{ + outl(CONFIG_CMD(dev,where), 0xCF8); + outb(value, 0xCFC + (where&3)); + return PCIBIOS_SUCCESSFUL; +} + +static int pci_conf1_write_config_word(struct pci_dev *dev, int where, u16 value) +{ + outl(CONFIG_CMD(dev,where), 0xCF8); + outw(value, 0xCFC + (where&2)); + return PCIBIOS_SUCCESSFUL; +} + +static int pci_conf1_write_config_dword(struct pci_dev *dev, int where, u32 value) +{ + outl(CONFIG_CMD(dev,where), 0xCF8); + outl(value, 0xCFC); + return PCIBIOS_SUCCESSFUL; +} + +#undef CONFIG_CMD + +static struct pci_ops pci_direct_conf1 = { + pci_conf1_read_config_byte, + pci_conf1_read_config_word, + pci_conf1_read_config_dword, + pci_conf1_write_config_byte, + pci_conf1_write_config_word, + pci_conf1_write_config_dword +}; + +/* + * Functions for accessing PCI configuration space with type 2 accesses + */ + +#define IOADDR(devfn, where) ((0xC000 | ((devfn & 0x78) << 5)) + where) +#define FUNC(devfn) (((devfn & 7) << 1) | 0xf0) +#define SET(dev) if (dev->devfn) return PCIBIOS_DEVICE_NOT_FOUND; \ + outb(FUNC(dev->devfn), 0xCF8); \ + outb(dev->bus->number, 0xCFA); + +static int pci_conf2_read_config_byte(struct pci_dev *dev, int where, u8 *value) +{ + SET(dev); + *value = inb(IOADDR(dev->devfn,where)); + outb (0, 0xCF8); + return PCIBIOS_SUCCESSFUL; +} + +static int pci_conf2_read_config_word(struct pci_dev *dev, int where, u16 *value) +{ + SET(dev); + *value = inw(IOADDR(dev->devfn,where)); + outb (0, 0xCF8); + return PCIBIOS_SUCCESSFUL; +} + +static int pci_conf2_read_config_dword(struct pci_dev *dev, int where, u32 *value) +{ + SET(dev); + *value = inl (IOADDR(dev->devfn,where)); + outb (0, 0xCF8); + return PCIBIOS_SUCCESSFUL; +} + +static int pci_conf2_write_config_byte(struct pci_dev *dev, int where, u8 value) +{ + SET(dev); + outb (value, IOADDR(dev->devfn,where)); + outb (0, 0xCF8); + return PCIBIOS_SUCCESSFUL; +} + +static int pci_conf2_write_config_word(struct pci_dev *dev, int where, u16 value) +{ + SET(dev); + outw (value, IOADDR(dev->devfn,where)); + outb (0, 0xCF8); + return PCIBIOS_SUCCESSFUL; +} + +static int pci_conf2_write_config_dword(struct pci_dev *dev, int where, u32 value) +{ + SET(dev); + outl (value, IOADDR(dev->devfn,where)); + outb (0, 0xCF8); + return PCIBIOS_SUCCESSFUL; +} + +#undef SET +#undef IOADDR +#undef FUNC + +static struct pci_ops pci_direct_conf2 = { + pci_conf2_read_config_byte, + pci_conf2_read_config_word, + pci_conf2_read_config_dword, + pci_conf2_write_config_byte, + pci_conf2_write_config_word, + pci_conf2_write_config_dword +}; + +/* + * Before we decide to use direct hardware access mechanisms, we try to do some + * trivial checks to ensure it at least _seems_ to be working -- we just test + * whether bus 00 contains a host bridge (this is similar to checking + * techniques used in XFree86, but ours should be more reliable since we + * attempt to make use of direct access hints provided by the PCI BIOS). + * + * This should be close to trivial, but it isn't, because there are buggy + * chipsets (yes, you guessed it, by Intel and Compaq) that have no class ID. + */ +static int __init pci_sanity_check(struct pci_ops *o) +{ + u16 x; + struct pci_bus bus; /* Fake bus and device */ + struct pci_dev dev; + + if (pci_probe & PCI_NO_CHECKS) + return 1; + bus.number = 0; + dev.bus = &bus; + for(dev.devfn=0; dev.devfn < 0x100; dev.devfn++) + if ((!o->read_word(&dev, PCI_CLASS_DEVICE, &x) && + (x == PCI_CLASS_BRIDGE_HOST || x == PCI_CLASS_DISPLAY_VGA)) || + (!o->read_word(&dev, PCI_VENDOR_ID, &x) && + (x == PCI_VENDOR_ID_INTEL || x == PCI_VENDOR_ID_COMPAQ))) + return 1; + DBG("PCI: Sanity check failed\n"); + return 0; +} + +static struct pci_ops * __init pci_check_direct(void) +{ + unsigned int tmp; + unsigned long flags; + + __save_flags(flags); __cli(); + + /* + * Check if configuration type 1 works. + */ + if (pci_probe & PCI_PROBE_CONF1) { + outb (0x01, 0xCFB); + tmp = inl (0xCF8); + outl (0x80000000, 0xCF8); + if (inl (0xCF8) == 0x80000000 && + pci_sanity_check(&pci_direct_conf1)) { + outl (tmp, 0xCF8); + __restore_flags(flags); + printk("PCI: Using configuration type 1\n"); + return &pci_direct_conf1; + } + outl (tmp, 0xCF8); + } + + /* + * Check if configuration type 2 works. + */ + if (pci_probe & PCI_PROBE_CONF2) { + outb (0x00, 0xCFB); + outb (0x00, 0xCF8); + outb (0x00, 0xCFA); + if (inb (0xCF8) == 0x00 && inb (0xCFA) == 0x00 && + pci_sanity_check(&pci_direct_conf2)) { + __restore_flags(flags); + printk("PCI: Using configuration type 2\n"); + return &pci_direct_conf2; + } + } + + __restore_flags(flags); + return NULL; +} + +#endif + +/* + * BIOS32 and PCI BIOS handling. + */ + +#ifdef CONFIG_PCI_BIOS + +#define PCIBIOS_PCI_FUNCTION_ID 0xb1XX +#define PCIBIOS_PCI_BIOS_PRESENT 0xb101 +#define PCIBIOS_FIND_PCI_DEVICE 0xb102 +#define PCIBIOS_FIND_PCI_CLASS_CODE 0xb103 +#define PCIBIOS_GENERATE_SPECIAL_CYCLE 0xb106 +#define PCIBIOS_READ_CONFIG_BYTE 0xb108 +#define PCIBIOS_READ_CONFIG_WORD 0xb109 +#define PCIBIOS_READ_CONFIG_DWORD 0xb10a +#define PCIBIOS_WRITE_CONFIG_BYTE 0xb10b +#define PCIBIOS_WRITE_CONFIG_WORD 0xb10c +#define PCIBIOS_WRITE_CONFIG_DWORD 0xb10d +#define PCIBIOS_GET_ROUTING_OPTIONS 0xb10e +#define PCIBIOS_SET_PCI_HW_INT 0xb10f + +/* BIOS32 signature: "_32_" */ +#define BIOS32_SIGNATURE (('_' << 0) + ('3' << 8) + ('2' << 16) + ('_' << 24)) + +/* PCI signature: "PCI " */ +#define PCI_SIGNATURE (('P' << 0) + ('C' << 8) + ('I' << 16) + (' ' << 24)) + +/* PCI service signature: "$PCI" */ +#define PCI_SERVICE (('$' << 0) + ('P' << 8) + ('C' << 16) + ('I' << 24)) + +/* PCI BIOS hardware mechanism flags */ +#define PCIBIOS_HW_TYPE1 0x01 +#define PCIBIOS_HW_TYPE2 0x02 +#define PCIBIOS_HW_TYPE1_SPEC 0x10 +#define PCIBIOS_HW_TYPE2_SPEC 0x20 + +/* + * This is the standard structure used to identify the entry point + * to the BIOS32 Service Directory, as documented in + * Standard BIOS 32-bit Service Directory Proposal + * Revision 0.4 May 24, 1993 + * Phoenix Technologies Ltd. + * Norwood, MA + * and the PCI BIOS specification. + */ + +union bios32 { + struct { + unsigned long signature; /* _32_ */ + unsigned long entry; /* 32 bit physical address */ + unsigned char revision; /* Revision level, 0 */ + unsigned char length; /* Length in paragraphs should be 01 */ + unsigned char checksum; /* All bytes must add up to zero */ + unsigned char reserved[5]; /* Must be zero */ + } fields; + char chars[16]; +}; + +/* + * Physical address of the service directory. I don't know if we're + * allowed to have more than one of these or not, so just in case + * we'll make pcibios_present() take a memory start parameter and store + * the array there. + */ + +static struct { + unsigned long address; + unsigned short segment; +} bios32_indirect = { 0, __KERNEL_CS }; + +/* + * Returns the entry point for the given service, NULL on error + */ + +static unsigned long bios32_service(unsigned long service) +{ + unsigned char return_code; /* %al */ + unsigned long address; /* %ebx */ + unsigned long length; /* %ecx */ + unsigned long entry; /* %edx */ + unsigned long flags; + + __save_flags(flags); __cli(); + __asm__("lcall (%%edi)" + : "=a" (return_code), + "=b" (address), + "=c" (length), + "=d" (entry) + : "0" (service), + "1" (0), + "D" (&bios32_indirect)); + __restore_flags(flags); + + switch (return_code) { + case 0: + return address + entry; + case 0x80: /* Not present */ + printk("bios32_service(0x%lx): not present\n", service); + return 0; + default: /* Shouldn't happen */ + printk("bios32_service(0x%lx): returned 0x%x -- BIOS bug!\n", + service, return_code); + return 0; + } +} + +static struct { + unsigned long address; + unsigned short segment; +} pci_indirect = { 0, __KERNEL_CS }; + +static int pci_bios_present; + +static int __init check_pcibios(void) +{ + u32 signature, eax, ebx, ecx; + u8 status, major_ver, minor_ver, hw_mech, last_bus; + unsigned long flags, pcibios_entry; + + if ((pcibios_entry = bios32_service(PCI_SERVICE))) { + pci_indirect.address = pcibios_entry + PAGE_OFFSET; + + __save_flags(flags); __cli(); + __asm__( + "lcall (%%edi)\n\t" + "jc 1f\n\t" + "xor %%ah, %%ah\n" + "1:" + : "=d" (signature), + "=a" (eax), + "=b" (ebx), + "=c" (ecx) + : "1" (PCIBIOS_PCI_BIOS_PRESENT), + "D" (&pci_indirect) + : "memory"); + __restore_flags(flags); + + status = (eax >> 8) & 0xff; + hw_mech = eax & 0xff; + major_ver = (ebx >> 8) & 0xff; + minor_ver = ebx & 0xff; + last_bus = ecx & 0xff; + DBG("PCI: BIOS probe returned s=%02x hw=%02x ver=%02x.%02x l=%02x\n", + status, hw_mech, major_ver, minor_ver, last_bus); + if (status || signature != PCI_SIGNATURE) { + printk (KERN_ERR "PCI: BIOS BUG #%x[%08x] found, report to \n", + status, signature); + return 0; + } + printk("PCI: PCI BIOS revision %x.%02x entry at 0x%lx\n", + major_ver, minor_ver, pcibios_entry); +#ifdef CONFIG_PCI_DIRECT + if (!(hw_mech & PCIBIOS_HW_TYPE1)) + pci_probe &= ~PCI_PROBE_CONF1; + if (!(hw_mech & PCIBIOS_HW_TYPE2)) + pci_probe &= ~PCI_PROBE_CONF2; +#endif + return 1; + } + return 0; +} + +static int __init pci_bios_find_device (unsigned short vendor, unsigned short device_id, + unsigned short index, unsigned char *bus, unsigned char *device_fn) +{ + unsigned short bx; + unsigned short ret; + + __asm__("lcall (%%edi)\n\t" + "jc 1f\n\t" + "xor %%ah, %%ah\n" + "1:" + : "=b" (bx), + "=a" (ret) + : "1" (PCIBIOS_FIND_PCI_DEVICE), + "c" (device_id), + "d" (vendor), + "S" ((int) index), + "D" (&pci_indirect)); + *bus = (bx >> 8) & 0xff; + *device_fn = bx & 0xff; + return (int) (ret & 0xff00) >> 8; +} + +static int pci_bios_read_config_byte(struct pci_dev *dev, int where, u8 *value) +{ + unsigned long ret; + unsigned long bx = (dev->bus->number << 8) | dev->devfn; + + __asm__("lcall (%%esi)\n\t" + "jc 1f\n\t" + "xor %%ah, %%ah\n" + "1:" + : "=c" (*value), + "=a" (ret) + : "1" (PCIBIOS_READ_CONFIG_BYTE), + "b" (bx), + "D" ((long) where), + "S" (&pci_indirect)); + return (int) (ret & 0xff00) >> 8; +} + +static int pci_bios_read_config_word(struct pci_dev *dev, int where, u16 *value) +{ + unsigned long ret; + unsigned long bx = (dev->bus->number << 8) | dev->devfn; + + __asm__("lcall (%%esi)\n\t" + "jc 1f\n\t" + "xor %%ah, %%ah\n" + "1:" + : "=c" (*value), + "=a" (ret) + : "1" (PCIBIOS_READ_CONFIG_WORD), + "b" (bx), + "D" ((long) where), + "S" (&pci_indirect)); + return (int) (ret & 0xff00) >> 8; +} + +static int pci_bios_read_config_dword(struct pci_dev *dev, int where, u32 *value) +{ + unsigned long ret; + unsigned long bx = (dev->bus->number << 8) | dev->devfn; + + __asm__("lcall (%%esi)\n\t" + "jc 1f\n\t" + "xor %%ah, %%ah\n" + "1:" + : "=c" (*value), + "=a" (ret) + : "1" (PCIBIOS_READ_CONFIG_DWORD), + "b" (bx), + "D" ((long) where), + "S" (&pci_indirect)); + return (int) (ret & 0xff00) >> 8; +} + +static int pci_bios_write_config_byte(struct pci_dev *dev, int where, u8 value) +{ + unsigned long ret; + unsigned long bx = (dev->bus->number << 8) | dev->devfn; + + __asm__("lcall (%%esi)\n\t" + "jc 1f\n\t" + "xor %%ah, %%ah\n" + "1:" + : "=a" (ret) + : "0" (PCIBIOS_WRITE_CONFIG_BYTE), + "c" (value), + "b" (bx), + "D" ((long) where), + "S" (&pci_indirect)); + return (int) (ret & 0xff00) >> 8; +} + +static int pci_bios_write_config_word(struct pci_dev *dev, int where, u16 value) +{ + unsigned long ret; + unsigned long bx = (dev->bus->number << 8) | dev->devfn; + + __asm__("lcall (%%esi)\n\t" + "jc 1f\n\t" + "xor %%ah, %%ah\n" + "1:" + : "=a" (ret) + : "0" (PCIBIOS_WRITE_CONFIG_WORD), + "c" (value), + "b" (bx), + "D" ((long) where), + "S" (&pci_indirect)); + return (int) (ret & 0xff00) >> 8; +} + +static int pci_bios_write_config_dword(struct pci_dev *dev, int where, u32 value) +{ + unsigned long ret; + unsigned long bx = (dev->bus->number << 8) | dev->devfn; + + __asm__("lcall (%%esi)\n\t" + "jc 1f\n\t" + "xor %%ah, %%ah\n" + "1:" + : "=a" (ret) + : "0" (PCIBIOS_WRITE_CONFIG_DWORD), + "c" (value), + "b" (bx), + "D" ((long) where), + "S" (&pci_indirect)); + return (int) (ret & 0xff00) >> 8; +} + +/* + * Function table for BIOS32 access + */ + +static struct pci_ops pci_bios_access = { + pci_bios_read_config_byte, + pci_bios_read_config_word, + pci_bios_read_config_dword, + pci_bios_write_config_byte, + pci_bios_write_config_word, + pci_bios_write_config_dword +}; + +/* + * Try to find PCI BIOS. + */ + +static struct pci_ops * __init pci_find_bios(void) +{ + union bios32 *check; + unsigned char sum; + int i, length; + + /* + * Follow the standard procedure for locating the BIOS32 Service + * directory by scanning the permissible address range from + * 0xe0000 through 0xfffff for a valid BIOS32 structure. + */ + + for (check = (union bios32 *) __va(0xe0000); + check <= (union bios32 *) __va(0xffff0); + ++check) { + if (check->fields.signature != BIOS32_SIGNATURE) + continue; + length = check->fields.length * 16; + if (!length) + continue; + sum = 0; + for (i = 0; i < length ; ++i) + sum += check->chars[i]; + if (sum != 0) + continue; + if (check->fields.revision != 0) { + printk("PCI: unsupported BIOS32 revision %d at 0x%p, report to \n", + check->fields.revision, check); + continue; + } + DBG("PCI: BIOS32 Service Directory structure at 0x%p\n", check); + if (check->fields.entry >= 0x100000) { + printk("PCI: BIOS32 entry (0x%p) in high memory, cannot use.\n", check); + return NULL; + } else { + unsigned long bios32_entry = check->fields.entry; + DBG("PCI: BIOS32 Service Directory entry at 0x%lx\n", bios32_entry); + bios32_indirect.address = bios32_entry + PAGE_OFFSET; + if (check_pcibios()) + return &pci_bios_access; + } + break; /* Hopefully more than one BIOS32 cannot happen... */ + } + + return NULL; +} + +/* + * Sort the device list according to PCI BIOS. Nasty hack, but since some + * fool forgot to define the `correct' device order in the PCI BIOS specs + * and we want to be (possibly bug-to-bug ;-]) compatible with older kernels + * which used BIOS ordering, we are bound to do this... + */ + +static void __init pcibios_sort(void) +{ + struct pci_dev *dev = pci_devices; + struct pci_dev **last = &pci_devices; + struct pci_dev *d, **dd, *e; + int idx; + unsigned char bus, devfn; + + DBG("PCI: Sorting device list...\n"); + while ((e = dev)) { + idx = 0; + while (pci_bios_find_device(e->vendor, e->device, idx, &bus, &devfn) == PCIBIOS_SUCCESSFUL) { + idx++; + for(dd=&dev; (d = *dd); dd = &d->next) { + if (d->bus->number == bus && d->devfn == devfn) { + *dd = d->next; + *last = d; + last = &d->next; + break; + } + } + if (!d) { + printk("PCI: BIOS reporting unknown device %02x:%02x\n", bus, devfn); + /* + * We must not continue scanning as several buggy BIOSes + * return garbage after the last device. Grr. + */ + break; + } + } + if (e == dev) { + printk("PCI: Device %02x:%02x not found by BIOS\n", + dev->bus->number, dev->devfn); + d = dev; + dev = dev->next; + *last = d; + last = &d->next; + } + } + *last = NULL; +} + +/* + * Ask BIOS for IRQ Routing Table + */ + +struct irq_routing_options { + u16 size; + struct irq_info *table; + u16 segment; +} __attribute__((packed)); + +static unsigned long pcibios_irq_page __initdata = 0; + +static inline void __init pcibios_free_irq_routing_table(void) +{ + if (pcibios_irq_page) + free_page(pcibios_irq_page); +} + +static struct irq_routing_table * __init pcibios_get_irq_routing_table(void) +{ + struct irq_routing_options opt; + struct irq_routing_table *rt; + int ret, map; + + if (pci_probe & PCI_NO_IRQ_SCAN) + return NULL; + pcibios_irq_page = __get_free_page(GFP_KERNEL); + if (!pcibios_irq_page) + return 0; + rt = (void *) pcibios_irq_page; + opt.table = rt->slots; + opt.size = PAGE_SIZE - sizeof(struct irq_routing_table); + opt.segment = __KERNEL_DS; + + DBG("PCI: Fetching IRQ routing table... "); + __asm__("push %%es\n\t" + "push %%ds\n\t" + "pop %%es\n\t" + "lcall (%%esi)\n\t" + "pop %%es\n\t" + "jc 1f\n\t" + "xor %%ah, %%ah\n" + "1:" + : "=a" (ret), + "=b" (map) + : "0" (PCIBIOS_GET_ROUTING_OPTIONS), + "1" (0), + "D" ((long) &opt), + "S" (&pci_indirect)); + DBG("OK ret=%d, size=%d, map=%x\n", ret, opt.size, map); + if (ret & 0xff00) { + printk(KERN_ERR "PCI: Error %02x when fetching IRQ routing table.\n", (ret >> 8) & 0xff); + return 0; + } + + memset(rt, 0, sizeof(struct irq_routing_table)); + rt->size = opt.size + sizeof(struct irq_routing_table); + printk("PCI: Using BIOS Interrupt Routing Table\n"); + return rt; +} + +#endif + +/* + * Several buggy motherboards address only 16 devices and mirror + * them to next 16 IDs. We try to detect this `feature' on all + * primary buses (those containing host bridges as they are + * expected to be unique) and remove the ghost devices. + */ + +static void __init pcibios_fixup_ghosts(struct pci_bus *b) +{ + struct pci_dev *d, *e, **z; + int mirror = PCI_DEVFN(16,0); + int seen_host_bridge = 0; + int i; + + DBG("PCI: Scanning for ghost devices on bus %d\n", b->number); + for(d=b->devices; d && d->devfn < mirror; d=d->sibling) { + if ((d->class >> 8) == PCI_CLASS_BRIDGE_HOST) + seen_host_bridge++; + for(e=d->next; e; e=e->sibling) { + if (e->devfn != d->devfn + mirror || + e->vendor != d->vendor || + e->device != d->device || + e->class != d->class) + continue; + for(i=0; iresource[i].start != d->resource[i].start || + e->resource[i].end != d->resource[i].end || + e->resource[i].flags != d->resource[i].flags) + continue; + break; + } + if (!e) + return; + } + if (!seen_host_bridge) + return; + printk("PCI: Ignoring ghost devices on bus %02x\n", b->number); + for(e=b->devices; e->sibling != d; e=e->sibling); + e->sibling = NULL; + for(z=&pci_devices; (d=*z);) + if (d->bus == b && d->devfn >= mirror) { + *z = d->next; + kfree_s(d, sizeof(*d)); + } else + z = &d->next; +} + +/* + * In case there are peer host bridges, scan bus behind each of them. + * Although several sources claim that the host bridges should have + * header type 1 and be assigned a bus number as for PCI2PCI bridges, + * the reality doesn't pass this test and the bus number is usually + * set by BIOS to the first free value. + */ +static void __init pcibios_fixup_peer_bridges(void) +{ + struct pci_bus *b = pci_root; + int n, cnt=-1; + struct pci_dev *d; + struct pci_ops *ops = pci_root->ops; + +#ifdef CONFIG_PCI_DIRECT + /* + * Don't search for peer host bridges if we use config type 2 + * since it reads bogus values for non-existent buses and + * chipsets supporting multiple primary buses use conf1 anyway. + */ + if (ops == &pci_direct_conf2) + return; +#endif + + for(d=b->devices; d; d=d->sibling) + if ((d->class >> 8) == PCI_CLASS_BRIDGE_HOST) + cnt++; + n = b->subordinate + 1; + while (n <= 0xff) { + int found = 0; + u16 l; + struct pci_bus bus; + struct pci_dev dev; + bus.number = n; + bus.ops = ops; + dev.bus = &bus; + for(dev.devfn=0; dev.devfn<256; dev.devfn += 8) + if (!pci_read_config_word(&dev, PCI_VENDOR_ID, &l) && + l != 0x0000 && l != 0xffff) { +#ifdef CONFIG_PCI_BIOS + if (pci_bios_present) { + int err, idx = 0; + u8 bios_bus, bios_dfn; + u16 d; + pci_read_config_word(&dev, PCI_DEVICE_ID, &d); + DBG("BIOS test for %02x:%02x (%04x:%04x)\n", n, dev.devfn, l, d); + while (!(err = pci_bios_find_device(l, d, idx, &bios_bus, &bios_dfn)) && + (bios_bus != n || bios_dfn != dev.devfn)) + idx++; + if (err) + break; + } +#endif + DBG("Found device at %02x:%02x\n", n, dev.devfn); + found++; + if (!pci_read_config_word(&dev, PCI_CLASS_DEVICE, &l) && + l == PCI_CLASS_BRIDGE_HOST) + cnt++; + } + if (cnt-- <= 0) + break; + if (found) { + printk("PCI: Discovered primary peer bus %02x\n", n); + b = pci_scan_bus(n, ops, NULL); + if (b) + n = b->subordinate; + } + n++; + } +} + +/* + * Exceptions for specific devices. Usually work-arounds for fatal design flaws. + */ + +static void __init pci_fixup_i450nx(struct pci_dev *d) +{ + /* + * i450NX -- Find and scan all secondary buses on all PXB's. + */ + int pxb, reg; + u8 busno, suba, subb; + printk("PCI: Searching for i450NX host bridges on %s\n", d->slot_name); + reg = 0xd0; + for(pxb=0; pxb<2; pxb++) { + pci_read_config_byte(d, reg++, &busno); + pci_read_config_byte(d, reg++, &suba); + pci_read_config_byte(d, reg++, &subb); + DBG("i450NX PXB %d: %02x/%02x/%02x\n", pxb, busno, suba, subb); + if (busno) + pci_scan_bus(busno, pci_root->ops, NULL); /* Bus A */ + if (suba < subb) + pci_scan_bus(suba+1, pci_root->ops, NULL); /* Bus B */ + } + pci_probe |= PCI_NO_PEER_FIXUP; +} + +static void __init pci_fixup_umc_ide(struct pci_dev *d) +{ + /* + * UM8886BF IDE controller sets region type bits incorrectly, + * therefore they look like memory despite of them being I/O. + */ + int i; + + printk("PCI: Fixing base address flags for device %s\n", d->slot_name); + for(i=0; i<4; i++) + d->resource[i].flags |= PCI_BASE_ADDRESS_SPACE_IO; +} + +static void __init pci_fixup_ide_bases(struct pci_dev *d) +{ + int i; + + /* + * PCI IDE controllers use non-standard I/O port decoding, respect it. + */ + if ((d->class >> 8) != PCI_CLASS_STORAGE_IDE) + return; + DBG("PCI: IDE base address fixup for %s\n", d->slot_name); + for(i=0; i<4; i++) { + struct resource *r = &d->resource[i]; + if ((r->start & ~0x80) == 0x374) { + r->start |= 2; + r->end = r->start; + } + } +} + +struct pci_fixup pcibios_fixups[] = { + { PCI_FIXUP_HEADER, PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_82451NX, pci_fixup_i450nx }, + { PCI_FIXUP_HEADER, PCI_VENDOR_ID_UMC, PCI_DEVICE_ID_UMC_UM8886BF, pci_fixup_umc_ide }, + { PCI_FIXUP_HEADER, PCI_ANY_ID, PCI_ANY_ID, pci_fixup_ide_bases }, + { 0 } +}; + +/* + * Fix up IRQs of all PCI devices. + */ + +extern int skip_ioapic_setup; + +#define PIRQ_SIGNATURE (('$' << 0) + ('P' << 8) + ('I' << 16) + ('R' << 24)) +#define PIRQ_VERSION 0x0100 + +/* + * Search 0xf0000 -- 0xfffff for the PCI IRQ Routing Table. + */ + +static struct irq_routing_table * __init pcibios_find_irq_routing_table(void) +{ + u8 *addr; + struct irq_routing_table *rt; + int i; + u8 sum; + + for(addr = (u8 *) __va(0xf0000); addr < (u8 *) __va(0x100000); addr += 16) { + rt = (struct irq_routing_table *) addr; + if (rt->signature != PIRQ_SIGNATURE || + rt->version != PIRQ_VERSION || + rt->size % 16 || + rt->size < sizeof(struct irq_routing_table)) + continue; + sum = 0; + for(i=0; isize; i++) + sum += addr[i]; + if (!sum) { + printk("PCI: Interrupt Routing Table found at 0x%p [router type %04x/%04x]\n", + rt, rt->rtr_vendor, rt->rtr_device); + return rt; + } + } + return NULL; +} + +/* + * If we have a IRQ routing table, use it to search for peer host + * bridges. It's a gross hack, but since there are no other known + * ways how to get a list of buses, we have to go this way. + */ + +static void __init pcibios_irq_peer_trick(struct irq_routing_table *rt) +{ + u8 busmap[256]; + int i; + struct irq_info *e; + + memset(busmap, 0, sizeof(busmap)); + for(i=0; i < (rt->size - sizeof(struct irq_routing_table)) / sizeof(struct irq_info); i++) { + e = &rt->slots[i]; + DBG("b=%02x d=%02x s=%02x\n", e->bus, e->devfn, e->slot); + busmap[e->bus] = 1; + } + for(i=1; i<256; i++) + /* + * It might be a secondary bus, but in this case its parent is already + * known (ascending bus order) and therefore pci_scan_bus returns immediately. + */ + if (busmap[i] && pci_scan_bus(i, pci_root->ops, NULL)) + printk("PCI: Discovered primary peer bus %02x [IRQ]\n", i); + pci_probe |= PCI_NO_PEER_FIXUP; +} + +/* + * In case BIOS forgets to tell us about IRQ, we try to look it up in the routing + * table, but unfortunately we have to know the interrupt router chip. + */ + +static char * __init pcibios_lookup_irq(struct pci_dev *dev, struct irq_routing_table *rt, int pin) +{ + struct irq_info *q; + struct pci_dev *router; + int i, pirq, newirq; + u32 rtrid, mask; + u8 x; + + pin--; + DBG("IRQ for %s(%d)", dev->slot_name, pin); + while (dev->bus->self) { + pin = (pin + PCI_SLOT(dev->devfn)) % 4; + dev = dev->bus->self; + DBG(" -> %s(%d)", dev->slot_name, pin); + } + for(q = rt->slots, i = rt->size - sizeof(struct irq_routing_table); + i && (q->bus != dev->bus->number || PCI_SLOT(q->devfn) != PCI_SLOT(dev->devfn)); + i -= sizeof(struct irq_info), q++) + ; + if (!i) { + DBG(" -> not found in routing table\n"); + return NULL; + } + pirq = q->irq[pin].link; + mask = q->irq[pin].bitmap; + if (!pirq) { + DBG(" -> not routed\n"); + return NULL; + } + DBG(" -> PIRQ %02x, mask %04x", pirq, mask); + if ((dev->class >> 8) == PCI_CLASS_DISPLAY_VGA) + newirq = 0; + else for(newirq = 15; newirq && !(mask & (1 << newirq)); newirq--) + ; + if (!(router = pci_find_slot(rt->rtr_bus, rt->rtr_devfn))) { + DBG(" -> router not found\n"); + return NULL; + } +#define ID(x,y) ((x << 16) | y) + rtrid = ID(rt->rtr_vendor, rt->rtr_device); + if (!rtrid) { + /* + * Several BIOSes forget to set the router type. In such cases, we + * use chip vendor/device. This doesn't guarantee us semantics of + * PIRQ values, but was found to work in practice and it's still + * better than not trying. + */ + DBG(" [%s]", router->slot_name); + rtrid = ID(router->vendor, router->device); + } + switch (rtrid) { + case ID(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_82371FB_0): + case ID(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_82371SB_0): + case ID(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_82371AB_0): + /* Intel PIIX: PIRQ holds configuration register address */ + pci_read_config_byte(router, pirq, &x); + if (x < 16) { + DBG(" -> [PIIX] %02x\n", x); + dev->irq = x; + return "PIIX"; + } else if (newirq) { + DBG(" -> [PIIX] set to %02x\n", newirq); + pci_write_config_byte(router, pirq, newirq); + dev->irq = newirq; + return "PIIX-NEW"; + } + DBG(" -> [PIIX] sink\n"); + return NULL; + default: + DBG(" -> unknown router %04x/%04x\n", rt->rtr_vendor, rt->rtr_device); + if (newirq && mask == (1 << newirq)) { + /* Only one IRQ available -> use it */ + dev->irq = newirq; + return "guess"; + } + return NULL; + } +#undef ID +} + +static void __init pcibios_fixup_irqs(void) +{ + struct irq_routing_table *rtable; + struct pci_dev *dev; + u8 pin; + + rtable = pcibios_find_irq_routing_table(); +#ifdef CONFIG_PCI_BIOS + if (!rtable && pci_bios_present) + rtable = pcibios_get_irq_routing_table(); +#endif + + if (rtable) + pcibios_irq_peer_trick(rtable); + + for(dev=pci_devices; dev; dev=dev->next) { + pci_read_config_byte(dev, PCI_INTERRUPT_PIN, &pin); +#if defined(CONFIG_X86_IO_APIC) + /* + * Recalculate IRQ numbers if we use the I/O APIC. + */ + if(!skip_ioapic_setup) + { + int irq; + + if (pin) { + pin--; /* interrupt pins are numbered starting from 1 */ + irq = IO_APIC_get_PCI_irq_vector(dev->bus->number, PCI_SLOT(dev->devfn), pin); + if (irq < 0 && dev->bus->parent) { /* go back to the bridge */ + struct pci_dev * bridge = dev->bus->self; + + pin = (pin + PCI_SLOT(dev->devfn)) % 4; + irq = IO_APIC_get_PCI_irq_vector(bridge->bus->number, + PCI_SLOT(bridge->devfn), pin); + if (irq >= 0) + printk(KERN_WARNING "PCI: using PPB(B%d,I%d,P%d) to get irq %d\n", + bridge->bus->number, PCI_SLOT(bridge->devfn), pin, irq); + } + if (irq >= 0) { + printk("PCI->APIC IRQ transform: (B%d,I%d,P%d) -> %d\n", + dev->bus->number, PCI_SLOT(dev->devfn), pin, irq); + dev->irq = irq; + } + } + rtable = NULL; /* Avoid IRQ assignment below */ + } +#endif + /* + * Fix out-of-range IRQ numbers and missing IRQs. + */ + if (dev->irq >= NR_IRQS) + dev->irq = 0; + if (pin && !dev->irq && rtable && rtable->version) { + char *msg = pcibios_lookup_irq(dev, rtable, pin); + if (msg) + printk("PCI: Assigned IRQ %d to device %s [%s]\n", dev->irq, dev->slot_name, msg); + } + } + +#ifdef CONFIG_PCI_BIOS + pcibios_free_irq_routing_table(); +#endif +} + +/* + * Called after each bus is probed, but before its children + * are examined. + */ + +void __init pcibios_fixup_bus(struct pci_bus *b) +{ + pcibios_fixup_ghosts(b); + pci_read_bridge_bases(b); +} + +/* + * Initialization. Try all known PCI access methods. Note that we support + * using both PCI BIOS and direct access: in such cases, we use I/O ports + * to access config space, but we still keep BIOS order of cards to be + * compatible with 2.0.X. This should go away some day. + */ + +void __init pcibios_init(void) +{ + struct pci_ops *bios = NULL; + struct pci_ops *dir = NULL; + struct pci_ops *ops; + +#ifdef CONFIG_PCI_BIOS + if ((pci_probe & PCI_PROBE_BIOS) && ((bios = pci_find_bios()))) { + pci_probe |= PCI_BIOS_SORT; + pci_bios_present = 1; + } +#endif +#ifdef CONFIG_PCI_DIRECT + if (pci_probe & (PCI_PROBE_CONF1 | PCI_PROBE_CONF2)) + dir = pci_check_direct(); +#endif + if (dir) + ops = dir; + else if (bios) + ops = bios; + else { + printk("PCI: No PCI bus detected\n"); + return; + } + + printk("PCI: Probing PCI hardware\n"); + pci_scan_bus(0, ops, NULL); + + pcibios_fixup_irqs(); + if (!(pci_probe & PCI_NO_PEER_FIXUP)) + pcibios_fixup_peer_bridges(); + pcibios_resource_survey(); + +#ifdef CONFIG_PCI_BIOS + if ((pci_probe & PCI_BIOS_SORT) && !(pci_probe & PCI_NO_SORT)) + pcibios_sort(); +#endif +} + +char * __init pcibios_setup(char *str) +{ + if (!strcmp(str, "off")) { + pci_probe = 0; + return NULL; + } +#ifdef CONFIG_PCI_BIOS + else if (!strcmp(str, "bios")) { + pci_probe = PCI_PROBE_BIOS; + return NULL; + } else if (!strcmp(str, "nobios")) { + pci_probe &= ~PCI_PROBE_BIOS; + return NULL; + } else if (!strcmp(str, "nosort")) { + pci_probe |= PCI_NO_SORT; + return NULL; + } else if (!strcmp(str, "noirq")) { + pci_probe |= PCI_NO_IRQ_SCAN; + return NULL; + } +#endif +#ifdef CONFIG_PCI_DIRECT + else if (!strcmp(str, "conf1")) { + pci_probe = PCI_PROBE_CONF1 | PCI_NO_CHECKS; + return NULL; + } + else if (!strcmp(str, "conf2")) { + pci_probe = PCI_PROBE_CONF2 | PCI_NO_CHECKS; + return NULL; + } +#endif + else if (!strcmp(str, "nopeer")) { + pci_probe |= PCI_NO_PEER_FIXUP; + return NULL; + } else if (!strcmp(str, "rom")) { + pci_probe |= PCI_ASSIGN_ROMS; + return NULL; + } + return str; +} diff -u --recursive --new-file v2.3.19/linux/arch/i386/kernel/pci-visws.c linux/arch/i386/kernel/pci-visws.c --- v2.3.19/linux/arch/i386/kernel/pci-visws.c Wed Dec 31 16:00:00 1969 +++ linux/arch/i386/kernel/pci-visws.c Fri Oct 8 10:06:21 1999 @@ -0,0 +1,131 @@ +/* + * Low-Level PCI Support for SGI Visual Workstation + * + * (c) 1999 Martin Mares + */ + +#include +#include +#include +#include +#include +#include +#include + +#include +#include + +#include "pci-i386.h" + +unsigned int pci_probe = 0; + +/* + * The VISWS uses configuration access type 1 only. + */ + +#define CONFIG_CMD(dev, where) (0x80000000 | (dev->bus->number << 16) | (dev->devfn << 8) | (where & ~3)) + +static int pci_conf1_read_config_byte(struct pci_dev *dev, int where, u8 *value) +{ + outl(CONFIG_CMD(dev,where), 0xCF8); + *value = inb(0xCFC + (where&3)); + return PCIBIOS_SUCCESSFUL; +} + +static int pci_conf1_read_config_word(struct pci_dev *dev, int where, u16 *value) +{ + outl(CONFIG_CMD(dev,where), 0xCF8); + *value = inw(0xCFC + (where&2)); + return PCIBIOS_SUCCESSFUL; +} + +static int pci_conf1_read_config_dword(struct pci_dev *dev, int where, u32 *value) +{ + outl(CONFIG_CMD(dev,where), 0xCF8); + *value = inl(0xCFC); + return PCIBIOS_SUCCESSFUL; +} + +static int pci_conf1_write_config_byte(struct pci_dev *dev, int where, u8 value) +{ + outl(CONFIG_CMD(dev,where), 0xCF8); + outb(value, 0xCFC + (where&3)); + return PCIBIOS_SUCCESSFUL; +} + +static int pci_conf1_write_config_word(struct pci_dev *dev, int where, u16 value) +{ + outl(CONFIG_CMD(dev,where), 0xCF8); + outw(value, 0xCFC + (where&2)); + return PCIBIOS_SUCCESSFUL; +} + +static int pci_conf1_write_config_dword(struct pci_dev *dev, int where, u32 value) +{ + outl(CONFIG_CMD(dev,where), 0xCF8); + outl(value, 0xCFC); + return PCIBIOS_SUCCESSFUL; +} + +#undef CONFIG_CMD + +static struct pci_ops visws_pci_ops = { + pci_conf1_read_config_byte, + pci_conf1_read_config_word, + pci_conf1_read_config_dword, + pci_conf1_write_config_byte, + pci_conf1_write_config_word, + pci_conf1_write_config_dword +}; + +static void __init pcibios_fixup_irqs(void) +{ + struct pci_dev *dev, *p; + u8 pin; + int irq; + + for(dev=pci_devices; dev; dev=dev->next) { + pci_read_config_byte(dev, PCI_INTERRUPT_PIN, &pin); + dev->irq = 0; + if (!pin) + continue; + pin--; + if (dev->bus->parent) { + p = dev->bus->parent->self; + pin = (pin + PCI_SLOT(dev->devfn)) % 4; + } else + p = dev; + irq = visws_get_PCI_irq_vector(p->bus->number, PCI_SLOT(p->devfn), pin+1); + if (irq >= 0) + dev->irq = irq; + DBG("PCI IRQ: %s pin %d -> %d\n", dev->slot_name, pin, irq); + } +} + +void __init pcibios_fixup_bus(struct pci_bus *b) +{ + pci_read_bridge_bases(b); +} + +#if 0 +static struct resource visws_pci_bus_resources[2] = { + { "Host bus 1", 0xf4000000, 0xf7ffffff, 0 }, + { "Host bus 2", 0xf0000000, 0xf3ffffff, 0 } +}; +#endif + +void __init pcibios_init(void) +{ + unsigned int sec_bus = li_pcib_read16(LI_PCI_BUSNUM) & 0xff; + + printk("PCI: Probing PCI hardware on host buses 00 and %02x\n", sec_bus); + pci_scan_bus(0, &visws_pci_ops, NULL); + pci_scan_bus(sec_bus, &visws_pci_ops, NULL); + pcibios_fixup_irqs(); + pcibios_resource_survey(); +} + +char * __init pcibios_setup(char *str) +{ + return str; +} diff -u --recursive --new-file v2.3.19/linux/arch/i386/kernel/smp.c linux/arch/i386/kernel/smp.c --- v2.3.19/linux/arch/i386/kernel/smp.c Tue Sep 7 12:14:06 1999 +++ linux/arch/i386/kernel/smp.c Thu Oct 7 10:17:08 1999 @@ -1,1427 +1,108 @@ /* - * Intel MP v1.1/v1.4 specification support routines for multi-pentium - * hosts. + * Intel SMP support routines. * * (c) 1995 Alan Cox, Building #3 - * (c) 1998 Ingo Molnar + * (c) 1998-99 Ingo Molnar * - * Supported by Caldera http://www.caldera.com. - * Much of the core SMP work is based on previous work by Thomas Radke, to - * whom a great many thanks are extended. - * - * Thanks to Intel for making available several different Pentium, - * Pentium Pro and Pentium-II/Xeon MP machines. - * - * This code is released under the GNU public license version 2 or - * later. - * - * Fixes - * Felix Koop : NR_CPUS used properly - * Jose Renau : Handle single CPU case. - * Alan Cox : By repeated request 8) - Total BogoMIP report. - * Greg Wright : Fix for kernel stacks panic. - * Erich Boleyn : MP v1.4 and additional changes. - * Matthias Sattler : Changes for 2.1 kernel map. - * Michel Lespinasse : Changes for 2.1 kernel map. - * Michael Chastain : Change trampoline.S to gnu as. - * Alan Cox : Dumb bug: 'B' step PPro's are fine - * Ingo Molnar : Added APIC timers, based on code - * from Jose Renau - * Alan Cox : Added EBDA scanning - * Ingo Molnar : various cleanups and rewrites - * Tigran Aivazian : fixed "0.00 in /proc/uptime on SMP" bug. - */ - -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include - -#define JIFFIE_TIMEOUT 100 - -extern void update_one_process( struct task_struct *p, - unsigned long ticks, unsigned long user, - unsigned long system, int cpu); -/* - * Some notes on processor bugs: - * - * Pentium and Pentium Pro (and all CPUs) have bugs. The Linux issues - * for SMP are handled as follows. - * - * Pentium Pro - * Occasional delivery of 'spurious interrupt' as trap #16. This - * is very rare. The kernel logs the event and recovers - * - * Pentium - * There is a marginal case where REP MOVS on 100MHz SMP - * machines with B stepping processors can fail. XXX should provide - * an L1cache=Writethrough or L1cache=off option. - * - * B stepping CPUs may hang. There are hardware work arounds - * for this. We warn about it in case your board doesnt have the work - * arounds. Basically thats so I can tell anyone with a B stepping - * CPU and SMP problems "tough". - * - * Specific items [From Pentium Processor Specification Update] - * - * 1AP. Linux doesn't use remote read - * 2AP. Linux doesn't trust APIC errors - * 3AP. We work around this - * 4AP. Linux never generated 3 interrupts of the same priority - * to cause a lost local interrupt. - * 5AP. Remote read is never used - * 9AP. XXX NEED TO CHECK WE HANDLE THIS XXX - * 10AP. XXX NEED TO CHECK WE HANDLE THIS XXX - * 11AP. Linux reads the APIC between writes to avoid this, as per - * the documentation. Make sure you preserve this as it affects - * the C stepping chips too. - * - * If this sounds worrying believe me these bugs are ___RARE___ and - * there's about nothing of note with C stepping upwards. - */ - - -/* Kernel spinlock */ -spinlock_t kernel_flag = SPIN_LOCK_UNLOCKED; - -/* - * function prototypes: - */ -static void cache_APIC_registers (void); -static void stop_this_cpu (void); - -static int smp_b_stepping = 0; /* Set if we find a B stepping CPU */ - -static int max_cpus = -1; /* Setup configured maximum number of CPUs to activate */ -int smp_found_config=0; /* Have we found an SMP box */ - -unsigned long cpu_present_map = 0; /* Bitmask of physically existing CPUs */ -unsigned long cpu_online_map = 0; /* Bitmask of currently online CPUs */ -int smp_num_cpus = 0; /* Total count of live CPUs */ -int smp_threads_ready=0; /* Set when the idlers are all forked */ -volatile int cpu_number_map[NR_CPUS]; /* which CPU maps to which logical number */ -volatile int __cpu_logical_map[NR_CPUS]; /* which logical number maps to which CPU */ -static volatile unsigned long cpu_callin_map[NR_CPUS] = {0,}; /* We always use 0 the rest is ready for parallel delivery */ -static volatile unsigned long cpu_callout_map[NR_CPUS] = {0,}; /* We always use 0 the rest is ready for parallel delivery */ -volatile unsigned long smp_invalidate_needed; /* Used for the invalidate map that's also checked in the spinlock */ -volatile unsigned long kstack_ptr; /* Stack vector for booting CPUs */ -struct cpuinfo_x86 cpu_data[NR_CPUS]; /* Per CPU bogomips and other parameters */ -static unsigned int num_processors = 1; /* Internal processor count */ -unsigned long mp_ioapic_addr = 0xFEC00000; /* Address of the I/O apic (not yet used) */ -unsigned char boot_cpu_id = 0; /* Processor that is doing the boot up */ -static int smp_activated = 0; /* Tripped once we need to start cross invalidating */ -int apic_version[NR_CPUS]; /* APIC version number */ -unsigned long apic_retval; /* Just debugging the assembler.. */ - -volatile unsigned long kernel_counter=0; /* Number of times the processor holds the lock */ -volatile unsigned long syscall_count=0; /* Number of times the processor holds the syscall lock */ - -volatile unsigned long ipi_count; /* Number of IPIs delivered */ - -const char lk_lockmsg[] = "lock from interrupt context at %p\n"; - -int mp_bus_id_to_type [MAX_MP_BUSSES] = { -1, }; -extern int nr_ioapics; -extern struct mpc_config_ioapic mp_apics [MAX_IO_APICS]; -extern int mp_irq_entries; -extern struct mpc_config_intsrc mp_irqs [MAX_IRQ_SOURCES]; -extern int mpc_default_type; -int mp_bus_id_to_pci_bus [MAX_MP_BUSSES] = { -1, }; -int mp_current_pci_id = 0; -unsigned long mp_lapic_addr = 0; -int skip_ioapic_setup = 0; /* 1 if "noapic" boot option passed */ - -/* #define SMP_DEBUG */ - -#ifdef SMP_DEBUG -#define SMP_PRINTK(x) printk x -#else -#define SMP_PRINTK(x) -#endif - -/* - * IA s/w dev Vol 3, Section 7.4 - */ -#define APIC_DEFAULT_PHYS_BASE 0xfee00000 - -#define CLEAR_TSC wrmsr(0x10, 0x00001000, 0x00001000) - -/* - * Setup routine for controlling SMP activation - * - * Command-line option of "nosmp" or "maxcpus=0" will disable SMP - * activation entirely (the MPS table probe still happens, though). - * - * Command-line option of "maxcpus=", where is an integer - * greater than 0, limits the maximum number of CPUs activated in - * SMP mode to . - */ - -static int __init nosmp(char *str) -{ - max_cpus = 0; - return 1; -} - -__setup("nosmp", nosmp); - -static int __init maxcpus(char *str) -{ - get_option(&str, &max_cpus); - return 1; -} - -__setup("maxcpus=", maxcpus); - -void ack_APIC_irq(void) -{ - /* Clear the IPI */ - - /* Dummy read */ - apic_read(APIC_SPIV); - - /* Docs say use 0 for future compatibility */ - apic_write(APIC_EOI, 0); -} - -/* - * Intel MP BIOS table parsing routines: - */ - -#ifndef CONFIG_X86_VISWS_APIC -/* - * Checksum an MP configuration block. - */ - -static int mpf_checksum(unsigned char *mp, int len) -{ - int sum=0; - while(len--) - sum+=*mp++; - return sum&0xFF; -} - -/* - * Processor encoding in an MP configuration block - */ - -static char *mpc_family(int family,int model) -{ - static char n[32]; - static char *model_defs[]= - { - "80486DX","80486DX", - "80486SX","80486DX/2 or 80487", - "80486SL","Intel5X2(tm)", - "Unknown","Unknown", - "80486DX/4" - }; - if (family==0x6) - return("Pentium(tm) Pro"); - if (family==0x5) - return("Pentium(tm)"); - if (family==0x0F && model==0x0F) - return("Special controller"); - if (family==0x04 && model<9) - return model_defs[model]; - sprintf(n,"Unknown CPU [%d:%d]",family, model); - return n; -} - - -/* - * Read the MPC - */ - -static int __init smp_read_mpc(struct mp_config_table *mpc) -{ - char str[16]; - int count=sizeof(*mpc); - int ioapics = 0; - unsigned char *mpt=((unsigned char *)mpc)+count; - - if (memcmp(mpc->mpc_signature,MPC_SIGNATURE,4)) - { - panic("SMP mptable: bad signature [%c%c%c%c]!\n", - mpc->mpc_signature[0], - mpc->mpc_signature[1], - mpc->mpc_signature[2], - mpc->mpc_signature[3]); - return 1; - } - if (mpf_checksum((unsigned char *)mpc,mpc->mpc_length)) - { - panic("SMP mptable: checksum error!\n"); - return 1; - } - if (mpc->mpc_spec!=0x01 && mpc->mpc_spec!=0x04) - { - printk("Bad Config Table version (%d)!!\n",mpc->mpc_spec); - return 1; - } - memcpy(str,mpc->mpc_oem,8); - str[8]=0; - printk("OEM ID: %s ",str); - - memcpy(str,mpc->mpc_productid,12); - str[12]=0; - printk("Product ID: %s ",str); - - printk("APIC at: 0x%lX\n",mpc->mpc_lapic); - - /* save the local APIC address, it might be non-default */ - mp_lapic_addr = mpc->mpc_lapic; - - /* - * Now process the configuration blocks. - */ - - while(countmpc_length) - { - switch(*mpt) - { - case MP_PROCESSOR: - { - struct mpc_config_processor *m= - (struct mpc_config_processor *)mpt; - if (m->mpc_cpuflag&CPU_ENABLED) - { - printk("Processor #%d %s APIC version %d\n", - m->mpc_apicid, - mpc_family((m->mpc_cpufeature& - CPU_FAMILY_MASK)>>8, - (m->mpc_cpufeature& - CPU_MODEL_MASK)>>4), - m->mpc_apicver); -#ifdef SMP_DEBUG - if (m->mpc_featureflag&(1<<0)) - printk(" Floating point unit present.\n"); - if (m->mpc_featureflag&(1<<7)) - printk(" Machine Exception supported.\n"); - if (m->mpc_featureflag&(1<<8)) - printk(" 64 bit compare & exchange supported.\n"); - if (m->mpc_featureflag&(1<<9)) - printk(" Internal APIC present.\n"); -#endif - if (m->mpc_cpuflag&CPU_BOOTPROCESSOR) - { - SMP_PRINTK((" Bootup CPU\n")); - boot_cpu_id=m->mpc_apicid; - } - else /* Boot CPU already counted */ - num_processors++; - - if (m->mpc_apicid>NR_CPUS) - printk("Processor #%d unused. (Max %d processors).\n",m->mpc_apicid, NR_CPUS); - else - { - int ver = m->mpc_apicver; - - cpu_present_map|=(1<mpc_apicid); - /* - * Validate version - */ - if (ver == 0x0) { - printk("BIOS bug, APIC version is 0 for CPU#%d! fixing up to 0x10. (tell your hw vendor)\n", m->mpc_apicid); - ver = 0x10; - } - apic_version[m->mpc_apicid] = ver; - } - } - mpt+=sizeof(*m); - count+=sizeof(*m); - break; - } - case MP_BUS: - { - struct mpc_config_bus *m= - (struct mpc_config_bus *)mpt; - memcpy(str,m->mpc_bustype,6); - str[6]=0; - SMP_PRINTK(("Bus #%d is %s\n", - m->mpc_busid, - str)); - if (strncmp(m->mpc_bustype,"ISA",3) == 0) - mp_bus_id_to_type[m->mpc_busid] = - MP_BUS_ISA; - else - if (strncmp(m->mpc_bustype,"EISA",4) == 0) - mp_bus_id_to_type[m->mpc_busid] = - MP_BUS_EISA; - if (strncmp(m->mpc_bustype,"PCI",3) == 0) { - mp_bus_id_to_type[m->mpc_busid] = - MP_BUS_PCI; - mp_bus_id_to_pci_bus[m->mpc_busid] = - mp_current_pci_id; - mp_current_pci_id++; - } - mpt+=sizeof(*m); - count+=sizeof(*m); - break; - } - case MP_IOAPIC: - { - struct mpc_config_ioapic *m= - (struct mpc_config_ioapic *)mpt; - if (m->mpc_flags&MPC_APIC_USABLE) - { - ioapics++; - printk("I/O APIC #%d Version %d at 0x%lX.\n", - m->mpc_apicid,m->mpc_apicver, - m->mpc_apicaddr); - mp_apics [nr_ioapics] = *m; - if (++nr_ioapics > MAX_IO_APICS) - --nr_ioapics; - } - mpt+=sizeof(*m); - count+=sizeof(*m); - break; - } - case MP_INTSRC: - { - struct mpc_config_intsrc *m= - (struct mpc_config_intsrc *)mpt; - - mp_irqs [mp_irq_entries] = *m; - if (++mp_irq_entries == MAX_IRQ_SOURCES) { - printk("Max irq sources exceeded!!\n"); - printk("Skipping remaining sources.\n"); - --mp_irq_entries; - } - - mpt+=sizeof(*m); - count+=sizeof(*m); - break; - } - case MP_LINTSRC: - { - struct mpc_config_intlocal *m= - (struct mpc_config_intlocal *)mpt; - mpt+=sizeof(*m); - count+=sizeof(*m); - break; - } - } - } - if (ioapics > MAX_IO_APICS) - { - printk("Warning: Max I/O APICs exceeded (max %d, found %d).\n", MAX_IO_APICS, ioapics); - printk("Warning: switching to non APIC mode.\n"); - skip_ioapic_setup=1; - } - return num_processors; -} - -/* - * Scan the memory blocks for an SMP configuration block. - */ - -static int __init smp_scan_config(unsigned long base, unsigned long length) -{ - unsigned long *bp=phys_to_virt(base); - struct intel_mp_floating *mpf; - - SMP_PRINTK(("Scan SMP from %p for %ld bytes.\n", - bp,length)); - if (sizeof(*mpf)!=16) - printk("Error: MPF size\n"); - - while (length>0) - { - if (*bp==SMP_MAGIC_IDENT) - { - mpf=(struct intel_mp_floating *)bp; - if (mpf->mpf_length==1 && - !mpf_checksum((unsigned char *)bp,16) && - (mpf->mpf_specification == 1 - || mpf->mpf_specification == 4) ) - { - printk("Intel MultiProcessor Specification v1.%d\n", mpf->mpf_specification); - if (mpf->mpf_feature2&(1<<7)) - printk(" IMCR and PIC compatibility mode.\n"); - else - printk(" Virtual Wire compatibility mode.\n"); - smp_found_config=1; - /* - * Now see if we need to read further. - */ - if (mpf->mpf_feature1!=0) - { - unsigned long cfg; - - /* local APIC has default address */ - mp_lapic_addr = APIC_DEFAULT_PHYS_BASE; - /* - * We need to know what the local - * APIC id of the boot CPU is! - */ - -/* - * - * HACK HACK HACK HACK HACK HACK HACK HACK HACK HACK HACK HACK HACK - * - * It's not just a crazy hack. ;-) - */ - /* - * Standard page mapping - * functions don't work yet. - * We know that page 0 is not - * used. Steal it for now! - */ - - cfg=pg0[0]; - pg0[0] = (mp_lapic_addr | _PAGE_RW | _PAGE_PRESENT); - local_flush_tlb(); - - boot_cpu_id = GET_APIC_ID(*((volatile unsigned long *) APIC_ID)); - - /* - * Give it back - */ - - pg0[0]= cfg; - local_flush_tlb(); - -/* - * - * END OF HACK END OF HACK END OF HACK END OF HACK END OF HACK - * - */ - /* - * 2 CPUs, numbered 0 & 1. - */ - cpu_present_map=3; - num_processors=2; - printk("I/O APIC at 0xFEC00000.\n"); - - /* - * Save the default type number, we - * need it later to set the IO-APIC - * up properly: - */ - mpc_default_type = mpf->mpf_feature1; - - printk("Bus #0 is "); - } - switch(mpf->mpf_feature1) - { - case 1: - case 5: - printk("ISA\n"); - break; - case 2: - printk("EISA with no IRQ8 chaining\n"); - break; - case 6: - case 3: - printk("EISA\n"); - break; - case 4: - case 7: - printk("MCA\n"); - break; - case 0: - break; - default: - printk("???\nUnknown standard configuration %d\n", - mpf->mpf_feature1); - return 1; - } - if (mpf->mpf_feature1>4) - { - printk("Bus #1 is PCI\n"); - - /* - * Set local APIC version to - * the integrated form. - * It's initialized to zero - * otherwise, representing - * a discrete 82489DX. - */ - apic_version[0] = 0x10; - apic_version[1] = 0x10; - } - /* - * Read the physical hardware table. - * Anything here will override the - * defaults. - */ - if (mpf->mpf_physptr) - smp_read_mpc((void *)mpf->mpf_physptr); - - __cpu_logical_map[0] = boot_cpu_id; - global_irq_holder = boot_cpu_id; - current->processor = boot_cpu_id; - - printk("Processors: %d\n", num_processors); - /* - * Only use the first configuration found. - */ - return 1; - } - } - bp+=4; - length-=16; - } - - return 0; -} - -void __init init_intel_smp (void) -{ - /* - * FIXME: Linux assumes you have 640K of base ram.. - * this continues the error... - * - * 1) Scan the bottom 1K for a signature - * 2) Scan the top 1K of base RAM - * 3) Scan the 64K of bios - */ - if (!smp_scan_config(0x0,0x400) && - !smp_scan_config(639*0x400,0x400) && - !smp_scan_config(0xF0000,0x10000)) { - /* - * If it is an SMP machine we should know now, unless the - * configuration is in an EISA/MCA bus machine with an - * extended bios data area. - * - * there is a real-mode segmented pointer pointing to the - * 4K EBDA area at 0x40E, calculate and scan it here. - * - * 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. These loaders are buggy and - * should be fixed. - */ - unsigned int address; - - address = *(unsigned short *)phys_to_virt(0x40E); - address<<=4; - smp_scan_config(address, 0x1000); - if (smp_found_config) - printk(KERN_WARNING "WARNING: MP table in the EBDA can be UNSAFE, contact linux-smp@vger.rutgers.edu if you experience SMP problems!\n"); - } -} - -#else - -/* - * The Visual Workstation is Intel MP compliant in the hardware - * sense, but it doesnt have a BIOS(-configuration table). - * No problem for Linux. - */ -void __init init_visws_smp(void) -{ - smp_found_config = 1; - - cpu_present_map |= 2; /* or in id 1 */ - apic_version[1] |= 0x10; /* integrated APIC */ - apic_version[0] |= 0x10; - - mp_lapic_addr = APIC_DEFAULT_PHYS_BASE; -} - -#endif - -/* - * - Intel MP Configuration Table - * - or SGI Visual Workstation configuration - */ -void __init init_smp_config (void) -{ -#ifndef CONFIG_VISWS - init_intel_smp(); -#else - init_visws_smp(); -#endif -} - - - -/* - * Trampoline 80x86 program as an array. - */ - -extern unsigned char trampoline_data []; -extern unsigned char trampoline_end []; -static unsigned char *trampoline_base; - -/* - * Currently trivial. Write the real->protected mode - * bootstrap into the page concerned. The caller - * has made sure it's suitably aligned. - */ - -static unsigned long __init setup_trampoline(void) -{ - memcpy(trampoline_base, trampoline_data, trampoline_end - trampoline_data); - return virt_to_phys(trampoline_base); -} - -/* - * We are called very early to get the low memory for the - * SMP bootup trampoline page. - */ -unsigned long __init smp_alloc_memory(unsigned long mem_base) -{ - if (virt_to_phys((void *)mem_base) >= 0x9F000) - panic("smp_alloc_memory: Insufficient low memory for kernel trampoline 0x%lx.", mem_base); - trampoline_base = (void *)mem_base; - return mem_base + PAGE_SIZE; -} - -/* - * The bootstrap kernel entry code has set these up. Save them for - * a given CPU - */ - -void __init smp_store_cpu_info(int id) -{ - struct cpuinfo_x86 *c=&cpu_data[id]; - - *c = boot_cpu_data; - c->pte_quick = 0; - c->pgd_quick = 0; - c->pgtable_cache_sz = 0; - identify_cpu(c); - /* - * Mask B, Pentium, but not Pentium MMX - */ - if (c->x86_vendor == X86_VENDOR_INTEL && - c->x86 == 5 && - c->x86_mask >= 1 && c->x86_mask <= 4 && - c->x86_model <= 3) - smp_b_stepping=1; /* Remember we have B step Pentia with bugs */ -} - -/* - * Architecture specific routine called by the kernel just before init is - * fired off. This allows the BP to have everything in order [we hope]. - * At the end of this all the APs will hit the system scheduling and off - * we go. Each AP will load the system gdt's and jump through the kernel - * init into idle(). At this point the scheduler will one day take over - * and give them jobs to do. smp_callin is a standard routine - * we use to track CPUs as they power up. - */ - -static atomic_t smp_commenced = ATOMIC_INIT(0); - -void __init smp_commence(void) -{ - /* - * Lets the callins below out of their loop. - */ - SMP_PRINTK(("Setting commenced=1, go go go\n")); - - wmb(); - atomic_set(&smp_commenced,1); -} - -void __init enable_local_APIC(void) -{ - unsigned long value; - - value = apic_read(APIC_SPIV); - value |= (1<<8); /* Enable APIC (bit==1) */ -#if 0 - value &= ~(1<<9); /* Enable focus processor (bit==0) */ -#else - value |= (1<<9); /* Disable focus processor (bit==1) */ -#endif - value |= 0xff; /* Set spurious IRQ vector to 0xff */ - apic_write(APIC_SPIV,value); - - /* - * Set Task Priority to 'accept all' - */ - value = apic_read(APIC_TASKPRI); - value &= ~APIC_TPRI_MASK; - apic_write(APIC_TASKPRI,value); - - /* - * Clear the logical destination ID, just to be safe. - * also, put the APIC into flat delivery mode. - */ - value = apic_read(APIC_LDR); - value &= ~APIC_LDR_MASK; - apic_write(APIC_LDR,value); - - value = apic_read(APIC_DFR); - value |= SET_APIC_DFR(0xf); - apic_write(APIC_DFR, value); - - udelay(100); /* B safe */ -} - -unsigned long __init init_smp_mappings(unsigned long memory_start) -{ - unsigned long apic_phys; - - memory_start = PAGE_ALIGN(memory_start); - if (smp_found_config) { - apic_phys = mp_lapic_addr; - } else { - /* - * set up a fake all zeroes page to simulate the - * local APIC and another one for the IO-APIC. We - * could use the real zero-page, but it's safer - * this way if some buggy code writes to this page ... - */ - apic_phys = __pa(memory_start); - memset((void *)memory_start, 0, PAGE_SIZE); - memory_start += PAGE_SIZE; - } - set_fixmap(FIX_APIC_BASE,apic_phys); - printk("mapped APIC to %08lx (%08lx)\n", APIC_BASE, apic_phys); - -#ifdef CONFIG_X86_IO_APIC - { - unsigned long ioapic_phys, idx = FIX_IO_APIC_BASE_0; - int i; - - for (i = 0; i < nr_ioapics; i++) { - if (smp_found_config) { - ioapic_phys = mp_apics[i].mpc_apicaddr; - } else { - ioapic_phys = __pa(memory_start); - memset((void *)memory_start, 0, PAGE_SIZE); - memory_start += PAGE_SIZE; - } - set_fixmap(idx,ioapic_phys); - printk("mapped IOAPIC to %08lx (%08lx)\n", - __fix_to_virt(idx), ioapic_phys); - idx++; - } - } -#endif - - return memory_start; -} - -extern void calibrate_delay(void); - -void __init smp_callin(void) -{ - int cpuid; - unsigned long timeout; - - /* - * (This works even if the APIC is not enabled.) - */ - cpuid = GET_APIC_ID(apic_read(APIC_ID)); - - SMP_PRINTK(("CPU#%d waiting for CALLOUT\n", cpuid)); - - /* - * STARTUP IPIs are fragile beasts as they might sometimes - * trigger some glue motherboard logic. Complete APIC bus - * silence for 1 second, this overestimates the time the - * boot CPU is spending to send the up to 2 STARTUP IPIs - * by a factor of two. This should be enough. - */ - - /* - * Waiting 2s total for startup (udelay is not yet working) - */ - timeout = jiffies + 2*HZ; - while (time_before(jiffies,timeout)) - { - /* - * Has the boot CPU finished it's STARTUP sequence? - */ - if (test_bit(cpuid, (unsigned long *)&cpu_callout_map[0])) - break; - } - - while (!time_before(jiffies,timeout)) { - printk("BUG: CPU%d started up but did not get a callout!\n", - cpuid); - stop_this_cpu(); - } - - /* - * the boot CPU has finished the init stage and is spinning - * on callin_map until we finish. We are free to set up this - * CPU, first the APIC. (this is probably redundant on most - * boards) - */ - - SMP_PRINTK(("CALLIN, before enable_local_APIC().\n")); - enable_local_APIC(); - - /* - * Set up our APIC timer. - */ - setup_APIC_clock(); - - __sti(); - -#ifdef CONFIG_MTRR - /* Must be done before calibration delay is computed */ - mtrr_init_secondary_cpu (); -#endif - /* - * Get our bogomips. - */ - calibrate_delay(); - SMP_PRINTK(("Stack at about %p\n",&cpuid)); - - /* - * Save our processor parameters - */ - smp_store_cpu_info(cpuid); - - /* - * Allow the master to continue. - */ - set_bit(cpuid, (unsigned long *)&cpu_callin_map[0]); -} - -int cpucount = 0; - -extern int cpu_idle(void); - -/* - * Activate a secondary processor. - */ -int __init start_secondary(void *unused) -{ - /* - * Dont put anything before smp_callin(), SMP - * booting is too fragile that we want to limit the - * things done here to the most necessary things. - */ - cpu_init(); - smp_callin(); - while (!atomic_read(&smp_commenced)) - /* nothing */ ; - return cpu_idle(); -} - -/* - * Everything has been set up for the secondary - * CPUs - they just need to reload everything - * from the task structure - * This function must not return. - */ -void __init initialize_secondary(void) -{ - /* - * We don't actually need to load the full TSS, - * basically just the stack pointer and the eip. - */ - - asm volatile( - "movl %0,%%esp\n\t" - "jmp *%1" - : - :"r" (current->thread.esp),"r" (current->thread.eip)); -} - -extern struct { - void * esp; - unsigned short ss; -} stack_start; - -static int __init fork_by_hand(void) -{ - struct pt_regs regs; - /* don't care about the eip and regs settings since we'll never - reschedule the forked task. */ - return do_fork(CLONE_VM|CLONE_PID, 0, ®s); -} - -static void __init do_boot_cpu(int i) -{ - unsigned long cfg; - pgd_t maincfg; - struct task_struct *idle; - unsigned long send_status, accept_status; - int timeout, num_starts, j; - unsigned long start_eip; - - cpucount++; - /* We can't use kernel_thread since we must _avoid_ to reschedule - the child. */ - if (fork_by_hand() < 0) - panic("failed fork for CPU %d", i); - - /* - * We remove it from the pidhash and the runqueue - * once we got the process: - */ - idle = init_task.prev_task; - if (!idle) - panic("No idle process for CPU %d", i); - - idle->processor = i; - __cpu_logical_map[cpucount] = i; - cpu_number_map[i] = cpucount; - idle->has_cpu = 1; /* we schedule the first task manually */ - idle->thread.eip = (unsigned long) start_secondary; - - del_from_runqueue(idle); - unhash_process(idle); - init_tasks[cpucount] = idle; - - /* start_eip had better be page-aligned! */ - start_eip = setup_trampoline(); - - printk("Booting processor %d eip %lx\n", i, start_eip); /* So we see what's up */ - stack_start.esp = (void *) (1024 + PAGE_SIZE + (char *)idle); - - /* - * This grunge runs the startup process for - * the targeted processor. - */ - - SMP_PRINTK(("Setting warm reset code and vector.\n")); - - CMOS_WRITE(0xa, 0xf); - local_flush_tlb(); - SMP_PRINTK(("1.\n")); - *((volatile unsigned short *) phys_to_virt(0x469)) = start_eip >> 4; - SMP_PRINTK(("2.\n")); - *((volatile unsigned short *) phys_to_virt(0x467)) = start_eip & 0xf; - SMP_PRINTK(("3.\n")); - - maincfg=swapper_pg_dir[0]; - ((unsigned long *)swapper_pg_dir)[0]=0x102007; - - /* - * Be paranoid about clearing APIC errors. - */ - - if ( apic_version[i] & 0xF0 ) - { - apic_write(APIC_ESR, 0); - accept_status = (apic_read(APIC_ESR) & 0xEF); - } - - /* - * Status is now clean - */ - - send_status = 0; - accept_status = 0; - - /* - * Starting actual IPI sequence... - */ - - SMP_PRINTK(("Asserting INIT.\n")); - - /* - * Turn INIT on - */ - - cfg=apic_read(APIC_ICR2); - cfg&=0x00FFFFFF; - apic_write(APIC_ICR2, cfg|SET_APIC_DEST_FIELD(i)); /* Target chip */ - cfg=apic_read(APIC_ICR); - cfg&=~0xCDFFF; /* Clear bits */ - cfg |= (APIC_DEST_LEVELTRIG | APIC_DEST_ASSERT | APIC_DEST_DM_INIT); - apic_write(APIC_ICR, cfg); /* Send IPI */ - - udelay(200); - SMP_PRINTK(("Deasserting INIT.\n")); - - cfg=apic_read(APIC_ICR2); - cfg&=0x00FFFFFF; - apic_write(APIC_ICR2, cfg|SET_APIC_DEST_FIELD(i)); /* Target chip */ - cfg=apic_read(APIC_ICR); - cfg&=~0xCDFFF; /* Clear bits */ - cfg |= (APIC_DEST_LEVELTRIG | APIC_DEST_DM_INIT); - apic_write(APIC_ICR, cfg); /* Send IPI */ - - /* - * Should we send STARTUP IPIs ? - * - * Determine this based on the APIC version. - * If we don't have an integrated APIC, don't - * send the STARTUP IPIs. - */ - - if ( apic_version[i] & 0xF0 ) - num_starts = 2; - else - num_starts = 0; - - /* - * Run STARTUP IPI loop. - */ - - for (j = 1; !(send_status || accept_status) - && (j <= num_starts) ; j++) - { - SMP_PRINTK(("Sending STARTUP #%d.\n",j)); - apic_write(APIC_ESR, 0); - SMP_PRINTK(("After apic_write.\n")); - - /* - * STARTUP IPI - */ - - cfg=apic_read(APIC_ICR2); - cfg&=0x00FFFFFF; - apic_write(APIC_ICR2, cfg|SET_APIC_DEST_FIELD(i)); /* Target chip */ - cfg=apic_read(APIC_ICR); - cfg&=~0xCDFFF; /* Clear bits */ - cfg |= (APIC_DEST_DM_STARTUP | (start_eip >> 12)); /* Boot on the stack */ - SMP_PRINTK(("Before start apic_write.\n")); - apic_write(APIC_ICR, cfg); /* Kick the second */ - - SMP_PRINTK(("Startup point 1.\n")); - - timeout = 0; - SMP_PRINTK(("Waiting for send to finish...\n")); - do { - SMP_PRINTK(("+")); - udelay(100); - send_status = apic_read(APIC_ICR) & 0x1000; - } while (send_status && (timeout++ < 1000)); - - /* - * Give the other CPU some time to accept the IPI. - */ - udelay(200); - accept_status = (apic_read(APIC_ESR) & 0xEF); - } - SMP_PRINTK(("After Startup.\n")); - - if (send_status) /* APIC never delivered?? */ - printk("APIC never delivered???\n"); - if (accept_status) /* Send accept error */ - printk("APIC delivery error (%lx).\n", accept_status); - - if ( !(send_status || accept_status) ) - { - /* - * allow APs to start initializing. - */ - SMP_PRINTK(("Before Callout %d.\n", i)); - set_bit(i, (unsigned long *)&cpu_callout_map[0]); - SMP_PRINTK(("After Callout %d.\n", i)); - - for(timeout=0;timeout<50000;timeout++) - { - if (cpu_callin_map[0]&(1< +#include - printk("per-CPU timeslice cutoff: %ld.%02ld usecs.\n", - (long)cacheflush_time/(cpu_hz/1000000), - ((long)cacheflush_time*100/(cpu_hz/1000000)) % 100); -} +#include +#include +#include +#include -unsigned int prof_multiplier[NR_CPUS]; -unsigned int prof_old_multiplier[NR_CPUS]; -unsigned int prof_counter[NR_CPUS]; +#include +#include +#include /* - * Cycle through the processors sending APIC IPIs to boot each. + * Some notes on processor bugs: + * + * Pentium, Pentium Pro, II, III (and all CPUs) have bugs. + * The Linux implications for SMP are handled as follows: + * + * Pentium III / [Xeon] + * None of the E1AP-E3AP erratas are visible to the user. + * + * E1AP. see PII A1AP + * E2AP. see PII A2AP + * E3AP. see PII A3AP + * + * Pentium II / [Xeon] + * None of the A1AP-A3AP erratas are visible to the user. + * + * A1AP. see PPro 1AP + * A2AP. see PPro 2AP + * A3AP. see PPro 7AP + * + * Pentium Pro + * None of 1AP-9AP erratas are visible to the normal user, + * except occasional delivery of 'spurious interrupt' as trap #15. + * This is very rare and a non-problem. + * + * 1AP. Linux maps APIC as non-cacheable + * 2AP. worked around in hardware + * 3AP. fixed in C0 and above steppings microcode update. + * Linux does not use excessive STARTUP_IPIs. + * 4AP. worked around in hardware + * 5AP. symmetric IO mode (normal Linux operation) not affected. + * 'noapic' mode has vector 0xf filled out properly. + * 6AP. 'noapic' mode might be affected - fixed in later steppings + * 7AP. We do not assume writes to the LVT deassering IRQs + * 8AP. We do not enable low power mode (deep sleep) during MP bootup + * 9AP. We do not use mixed mode + * + * Pentium + * There is a marginal case where REP MOVS on 100MHz SMP + * machines with B stepping processors can fail. XXX should provide + * an L1cache=Writethrough or L1cache=off option. + * + * B stepping CPUs may hang. There are hardware work arounds + * for this. We warn about it in case your board doesnt have the work + * arounds. Basically thats so I can tell anyone with a B stepping + * CPU and SMP problems "tough". + * + * Specific items [From Pentium Processor Specification Update] + * + * 1AP. Linux doesn't use remote read + * 2AP. Linux doesn't trust APIC errors + * 3AP. We work around this + * 4AP. Linux never generated 3 interrupts of the same priority + * to cause a lost local interrupt. + * 5AP. Remote read is never used + * 6AP. not affected - worked around in hardware + * 7AP. not affected - worked around in hardware + * 8AP. worked around in hardware - we get explicit CS errors if not + * 9AP. only 'noapic' mode affected. Might generate spurious + * interrupts, we log only the first one and count the + * rest silently. + * 10AP. not affected - worked around in hardware + * 11AP. Linux reads the APIC between writes to avoid this, as per + * the documentation. Make sure you preserve this as it affects + * the C stepping chips too. + * 12AP. not affected - worked around in hardware + * 13AP. not affected - worked around in hardware + * 14AP. we always deassert INIT during bootup + * 15AP. not affected - worked around in hardware + * 16AP. not affected - worked around in hardware + * 17AP. not affected - worked around in hardware + * 18AP. not affected - worked around in hardware + * 19AP. not affected - worked around in BIOS + * + * If this sounds worrying believe me these bugs are either ___RARE___, + * or are signal timing bugs worked around in hardware and there's + * about nothing of note with C stepping upwards. */ -void __init smp_boot_cpus(void) -{ - int i; - -#ifdef CONFIG_MTRR - /* Must be done before other processors booted */ - mtrr_init_boot_cpu (); -#endif - /* - * Initialize the logical to physical CPU number mapping - * and the per-CPU profiling counter/multiplier - */ - - for (i = 0; i < NR_CPUS; i++) { - cpu_number_map[i] = -1; - prof_counter[i] = 1; - prof_old_multiplier[i] = 1; - prof_multiplier[i] = 1; - } - - /* - * Setup boot CPU information - */ - - smp_store_cpu_info(boot_cpu_id); /* Final full version of the data */ - smp_tune_scheduling(); - printk("CPU%d: ", boot_cpu_id); - print_cpu_info(&cpu_data[boot_cpu_id]); - - /* - * not necessary because the MP table should list the boot - * CPU too, but we do it for the sake of robustness anyway. - * (and for the case when a non-SMP board boots an SMP kernel) - */ - cpu_present_map |= (1 << hard_smp_processor_id()); - - cpu_number_map[boot_cpu_id] = 0; - - init_idle(); - - /* - * If we couldnt find an SMP configuration at boot time, - * get out of here now! - */ - - if (!smp_found_config) - { - printk(KERN_NOTICE "SMP motherboard not detected. Using dummy APIC emulation.\n"); -#ifndef CONFIG_VISWS - io_apic_irqs = 0; -#endif - cpu_online_map = cpu_present_map; - smp_num_cpus = 1; - goto smp_done; - } - - /* - * If SMP should be disabled, then really disable it! - */ - - if (!max_cpus) - { - smp_found_config = 0; - printk(KERN_INFO "SMP mode deactivated, forcing use of dummy APIC emulation.\n"); - } - -#ifdef SMP_DEBUG - { - int reg; - - /* - * This is to verify that we're looking at - * a real local APIC. Check these against - * your board if the CPUs aren't getting - * started for no apparent reason. - */ - - reg = apic_read(APIC_VERSION); - SMP_PRINTK(("Getting VERSION: %x\n", reg)); - - apic_write(APIC_VERSION, 0); - reg = apic_read(APIC_VERSION); - SMP_PRINTK(("Getting VERSION: %x\n", reg)); - - /* - * The two version reads above should print the same - * NON-ZERO!!! numbers. If the second one is zero, - * there is a problem with the APIC write/read - * definitions. - * - * The next two are just to see if we have sane values. - * They're only really relevant if we're in Virtual Wire - * compatibility mode, but most boxes are anymore. - */ - - - reg = apic_read(APIC_LVT0); - SMP_PRINTK(("Getting LVT0: %x\n", reg)); - - reg = apic_read(APIC_LVT1); - SMP_PRINTK(("Getting LVT1: %x\n", reg)); - } -#endif - - enable_local_APIC(); - - /* - * Set up our local APIC timer: - */ - setup_APIC_clock (); - - /* - * Now scan the CPU present map and fire up the other CPUs. - */ - - /* - * Add all detected CPUs. (later on we can down individual - * CPUs which will change cpu_online_map but not necessarily - * cpu_present_map. We are pretty much ready for hot-swap CPUs.) - */ - cpu_online_map = cpu_present_map; - mb(); - - SMP_PRINTK(("CPU map: %lx\n", cpu_present_map)); - - for(i=0;i cpucount+1)) - { - do_boot_cpu(i); - } - - /* - * Make sure we unmap all failed CPUs - */ - - if (cpu_number_map[i] == -1 && (cpu_online_map & (1 << i))) { - printk("CPU #%d not responding. Removing from cpu_online_map.\n",i); - cpu_online_map &= ~(1 << i); - } - } - - /* - * Cleanup possible dangling ends... - */ - -#ifndef CONFIG_VISWS - { - unsigned long cfg; - - /* - * Install writable page 0 entry. - */ - cfg = pg0[0]; - pg0[0] = _PAGE_RW | _PAGE_PRESENT; /* writeable, present, addr 0 */ - local_flush_tlb(); - - /* - * Paranoid: Set warm reset code and vector here back - * to default values. - */ - - CMOS_WRITE(0, 0xf); - - *((volatile long *) phys_to_virt(0x467)) = 0; - - /* - * Restore old page 0 entry. - */ - - pg0[0] = cfg; - local_flush_tlb(); - } -#endif - - /* - * Allow the user to impress friends. - */ - - SMP_PRINTK(("Before bogomips.\n")); - if (!cpucount) { - printk(KERN_ERR "Error: only one processor found.\n"); - cpu_online_map = (1<CPU IPIs and self-IPIs too. */ - -/* - * Silly serialization to work around CPU bug in P5s. - * We can safely turn it off on a 686. - */ -#ifdef CONFIG_X86_GOOD_APIC -# define FORCE_APIC_SERIALIZATION 0 -#else -# define FORCE_APIC_SERIALIZATION 1 -#endif - static unsigned int cached_APIC_ICR; static unsigned int cached_APIC_ICR2; @@ -1462,7 +132,7 @@ static inline unsigned int __get_ICR (void) { -#if FORCE_APIC_SERIALIZATION +#if FORCE_READ_AROUND_WRITE /* * Wait for the APIC to become ready - this should never occur. It's * a debugging check really. @@ -1473,11 +143,11 @@ while (count < 1000) { cfg = slow_ICR; - if (!(cfg&(1<<12))) { - if (count) - atomic_add(count, (atomic_t*)&ipi_count); + if (!(cfg&(1<<12))) return cfg; - } + printk("CPU #%d: ICR still busy [%08x]\n", + smp_processor_id(), cfg); + irq_err_count++; count++; udelay(10); } @@ -1491,19 +161,25 @@ static inline unsigned int __get_ICR2 (void) { -#if FORCE_APIC_SERIALIZATION +#if FORCE_READ_AROUND_WRITE return slow_ICR2; #else return cached_APIC_ICR2; #endif } +#define LOGICAL_DELIVERY 1 + static inline int __prepare_ICR (unsigned int shortcut, int vector) { unsigned int cfg; cfg = __get_ICR(); - cfg |= APIC_DEST_DM_FIXED|shortcut|vector; + cfg |= APIC_DEST_DM_FIXED|shortcut|vector +#if LOGICAL_DELIVERY + |APIC_DEST_LOGICAL +#endif + ; return cfg; } @@ -1513,7 +189,11 @@ unsigned int cfg; cfg = __get_ICR2(); +#if LOGICAL_DELIVERY + cfg |= SET_APIC_DEST_FIELD((1< 1) + __send_IPI_shortcut(APIC_DEST_ALLBUT, vector); } static inline void send_IPI_all(int vector) @@ -1566,7 +251,7 @@ static inline void send_IPI_single(int dest, int vector) { unsigned long cfg; -#if FORCE_APIC_SERIALIZATION +#if FORCE_READ_AROUND_WRITE unsigned long flags; __save_flags(flags); @@ -1589,7 +274,7 @@ * Send the IPI. The write to APIC_ICR fires this off. */ apic_write(APIC_ICR, cfg); -#if FORCE_APIC_SERIALIZATION +#if FORCE_READ_AROUND_WRITE __restore_flags(flags); #endif } @@ -1715,200 +400,97 @@ } /* - * this function sends a 'stop' IPI to all other CPUs in the system. - * it goes straight through. - */ - -void smp_send_stop(void) -{ - send_IPI_allbutself(STOP_CPU_VECTOR); -} - -/* Structure and data for smp_call_function(). This is designed to minimise + * Structure and data for smp_call_function(). This is designed to minimise * static memory requirements. It also looks cleaner. */ -struct smp_call_function_struct { +static volatile struct call_data_struct { void (*func) (void *info); void *info; - atomic_t unstarted_count; - atomic_t unfinished_count; + atomic_t started; + atomic_t finished; int wait; -}; -static volatile struct smp_call_function_struct *smp_call_function_data = NULL; +} *call_data = NULL; /* * this function sends a 'generic call function' IPI to all other CPUs * in the system. */ -int smp_call_function (void (*func) (void *info), void *info, int retry, - int wait) -/* [SUMMARY] Run a function on all other CPUs. - The function to run. This must be fast and non-blocking. - An arbitrary pointer to pass to the function. - If true, keep retrying until ready. - If true, wait until function has completed on other CPUs. - [RETURNS] 0 on success, else a negative status code. Does not return until - remote CPUs are nearly ready to execute <> or are or have executed. -*/ -{ - unsigned long timeout; - struct smp_call_function_struct data; - static spinlock_t lock = SPIN_LOCK_UNLOCKED; - - if (retry) { - while (1) { - if (smp_call_function_data) { - schedule (); /* Give a mate a go */ - continue; - } - spin_lock (&lock); - if (smp_call_function_data) { - spin_unlock (&lock); /* Bad luck */ - continue; - } - /* Mine, all mine! */ - break; - } - } - else { - if (smp_call_function_data) return -EBUSY; - spin_lock (&lock); - if (smp_call_function_data) { - spin_unlock (&lock); - return -EBUSY; - } - } - smp_call_function_data = &data; - spin_unlock (&lock); - data.func = func; - data.info = info; - atomic_set (&data.unstarted_count, smp_num_cpus - 1); - data.wait = wait; - if (wait) atomic_set (&data.unfinished_count, smp_num_cpus - 1); - /* Send a message to all other CPUs and wait for them to respond */ - send_IPI_allbutself (CALL_FUNCTION_VECTOR); - /* Wait for response */ - timeout = jiffies + JIFFIE_TIMEOUT; - while ( (atomic_read (&data.unstarted_count) > 0) && - time_before (jiffies, timeout) ) - barrier (); - if (atomic_read (&data.unstarted_count) > 0) { - smp_call_function_data = NULL; - return -ETIMEDOUT; - } - if (wait) - while (atomic_read (&data.unfinished_count) > 0) - barrier (); - smp_call_function_data = NULL; - return 0; -} - -static unsigned int calibration_result; - -void setup_APIC_timer(unsigned int clocks); - +int smp_call_function (void (*func) (void *info), void *info, int nonatomic, + int wait) /* - * Local timer interrupt handler. It does both profiling and - * process statistics/rescheduling. - * - * We do profiling in every local tick, statistics/rescheduling - * happen only every 'profiling multiplier' ticks. The default - * multiplier is 1 and it can be changed by writing the new multiplier - * value into /proc/profile. + * [SUMMARY] Run a function on all other CPUs. + * The function to run. This must be fast and non-blocking. + * An arbitrary pointer to pass to the function. + * If true, we might schedule away to lock the mutex + * If true, wait (atomically) until function has completed on other CPUs. + * [RETURNS] 0 on success, else a negative status code. Does not return until + * remote CPUs are nearly ready to execute <> or are or have executed. */ - -void smp_local_timer_interrupt(struct pt_regs * regs) { - int user = (user_mode(regs) != 0); - int cpu = smp_processor_id(); - - /* - * The profiling function is SMP safe. (nothing can mess - * around with "current", and the profiling counters are - * updated with atomic operations). This is especially - * useful with a profiling multiplier != 1 - */ - if (!user) - x86_do_profile(regs->eip); + struct call_data_struct data; + int ret, cpus = smp_num_cpus-1; + static DECLARE_MUTEX(lock); + unsigned long timeout; - if (!--prof_counter[cpu]) { - int system = 1 - user; - struct task_struct * p = current; + if (nonatomic) + down(&lock); + else + if (down_trylock(&lock)) + return -EBUSY; - /* - * The multiplier may have changed since the last time we got - * to this point as a result of the user writing to - * /proc/profile. In this case we need to adjust the APIC - * timer accordingly. - * - * Interrupts are already masked off at this point. - */ - prof_counter[cpu] = prof_multiplier[cpu]; - if (prof_counter[cpu] != prof_old_multiplier[cpu]) { - setup_APIC_timer(calibration_result/prof_counter[cpu]); - prof_old_multiplier[cpu] = prof_counter[cpu]; - } + if (call_data) // temporary debugging check + BUG(); - /* - * After doing the above, we need to make like - * a normal interrupt - otherwise timer interrupts - * ignore the global interrupt lock, which is the - * WrongThing (tm) to do. - */ + call_data = &data; + data.func = func; + data.info = info; + atomic_set(&data.started, 0); + data.wait = wait; + if (wait) + atomic_set(&data.finished, 0); + mb(); - irq_enter(cpu, 0); - update_one_process(p, 1, user, system, cpu); - if (p->pid) { - p->counter -= 1; - if (p->counter <= 0) { - p->counter = 0; - p->need_resched = 1; - } - if (p->priority < DEF_PRIORITY) { - kstat.cpu_nice += user; - kstat.per_cpu_nice[cpu] += user; - } else { - kstat.cpu_user += user; - kstat.per_cpu_user[cpu] += user; - } - kstat.cpu_system += system; - kstat.per_cpu_system[cpu] += system; + /* Send a message to all other CPUs and wait for them to respond */ + send_IPI_allbutself(CALL_FUNCTION_VECTOR); - } - irq_exit(cpu, 0); - } + /* Wait for response */ + timeout = jiffies + HZ; + while ((atomic_read(&data.started) != cpus) + && time_before(jiffies, timeout)) + barrier(); + ret = -ETIMEDOUT; + if (atomic_read(&data.started) != cpus) + goto out; + ret = 0; + if (wait) + while (atomic_read(&data.finished) != cpus) + barrier(); +out: + call_data = NULL; + up(&lock); + return 0; +} +static void stop_this_cpu (void * dummy) +{ /* - * We take the 'long' return path, and there every subsystem - * grabs the apropriate locks (kernel lock/ irq lock). - * - * we might want to decouple profiling from the 'long path', - * and do the profiling totally in assembly. - * - * Currently this isn't too much of an issue (performance wise), - * we can take more than 100K local irqs per second on a 100 MHz P5. + * Remove this CPU: */ + clear_bit(smp_processor_id(), &cpu_online_map); + + if (cpu_data[smp_processor_id()].hlt_works_ok) + for(;;) __asm__("hlt"); + for (;;); } /* - * Local APIC timer interrupt. This is the most natural way for doing - * local interrupts, but local timer interrupts can be emulated by - * broadcast interrupts too. [in case the hw doesnt support APIC timers] - * - * [ if a single-CPU system runs an SMP kernel then we call the local - * interrupt as well. Thus we cannot inline the local irq ... ] + * this function calls the 'stop' function on all other CPUs in the system. */ -void smp_apic_timer_interrupt(struct pt_regs * regs) + +void smp_send_stop(void) { - /* - * NOTE! We'd better ACK the irq immediately, - * because timer handling can be slow, and we - * want to be able to accept NMI tlb invalidates - * during this time. - */ - ack_APIC_irq(); - smp_local_timer_interrupt(regs); + smp_call_function(stop_this_cpu, NULL, 1, 0); } /* @@ -1944,39 +526,24 @@ } -static void stop_this_cpu (void) +asmlinkage void smp_call_function_interrupt(void) { + void (*func) (void *info) = call_data->func; + void *info = call_data->info; + int wait = call_data->wait; + + ack_APIC_irq(); /* - * Remove this CPU: + * Notify initiating CPU that I've grabbed the data and am + * about to execute the function */ - clear_bit(smp_processor_id(), &cpu_online_map); - - if (cpu_data[smp_processor_id()].hlt_works_ok) - for(;;) __asm__("hlt"); - for (;;); -} - -/* - * CPU halt call-back - */ -asmlinkage void smp_stop_cpu_interrupt(void) -{ - stop_this_cpu(); -} - -asmlinkage void smp_call_function_interrupt(void) -{ - void (*func) (void *info) = smp_call_function_data->func; - void *info = smp_call_function_data->info; - int wait = smp_call_function_data->wait; - - ack_APIC_irq (); - /* Notify initiating CPU that I've grabbed the data and am about to - execute the function */ - atomic_dec (&smp_call_function_data->unstarted_count); - /* At this point the structure may be out of scope unless wait==1 */ - (*func) (info); - if (wait) atomic_dec (&smp_call_function_data->unfinished_count); + atomic_inc(&call_data->started); + /* + * At this point the structure may be out of scope unless wait==1 + */ + (*func)(info); + if (wait) + atomic_inc(&call_data->finished); } /* @@ -1991,6 +558,34 @@ } /* + * This interrupt should never happen with our APIC/SMP architecture + */ + +static spinlock_t err_lock; + +asmlinkage void smp_error_interrupt(void) +{ + unsigned long v; + + spin_lock(&err_lock); + + v = apic_read(APIC_ESR); + printk("APIC error interrupt on CPU#%d, should never happen.\n", + smp_processor_id()); + printk("... APIC ESR0: %08lx\n", v); + + apic_write(APIC_ESR, 0); + v = apic_read(APIC_ESR); + printk("... APIC ESR1: %08lx\n", v); + + ack_APIC_irq(); + + irq_err_count++; + + spin_unlock(&err_lock); +} + +/* * This part sets up the APIC 32 bit clock in LVTT1, with HZ interrupts * per second. We assume that the caller has already set up the local * APIC. @@ -1999,6 +594,10 @@ * closely follows bus clocks. */ +int prof_multiplier[NR_CPUS] = { 1, }; +int prof_old_multiplier[NR_CPUS] = { 1, }; +int prof_counter[NR_CPUS] = { 1, }; + /* * The timer chip is already set up at HZ interrupts per second here, * but we do not accept timer interrupts yet. We only allow the BP @@ -2015,66 +614,102 @@ return count; } +void __init wait_8254_wraparound(void) +{ + unsigned int curr_count, prev_count=~0; + int delta; + + curr_count = get_8254_timer_count(); + + do { + prev_count = curr_count; + curr_count = get_8254_timer_count(); + delta = curr_count-prev_count; + + /* + * This limit for delta seems arbitrary, but it isn't, it's + * slightly above the level of error a buggy Mercury/Neptune + * chipset timer can cause. + */ + + } while (delta<300); +} + /* * This function sets up the local APIC timer, with a timeout of * 'clocks' APIC bus clock. During calibration we actually call - * this function twice, once with a bogus timeout value, second - * time for real. The other (noncalibrating) CPUs call this - * function only once, with the real value. - * - * We are strictly in irqs off mode here, as we do not want to - * get an APIC interrupt go off accidentally. + * this function twice on the boot CPU, once with a bogus timeout + * value, second time for real. The other (noncalibrating) CPUs + * call this function only once, with the real, calibrated value. * * We do reads before writes even if unnecessary, to get around the - * APIC double write bug. + * P5 APIC double write bug. */ #define APIC_DIVISOR 16 -void setup_APIC_timer(unsigned int clocks) +void __setup_APIC_LVTT(unsigned int clocks) { - unsigned long lvtt1_value; - unsigned int tmp_value; + unsigned int lvtt1_value, tmp_value; - /* - * Unfortunately the local APIC timer cannot be set up into NMI - * mode. With the IO APIC we can re-route the external timer - * interrupt and broadcast it as an NMI to all CPUs, so no pain. - */ tmp_value = apic_read(APIC_LVTT); - lvtt1_value = APIC_LVT_TIMER_PERIODIC | LOCAL_TIMER_VECTOR; - apic_write(APIC_LVTT , lvtt1_value); + lvtt1_value = SET_APIC_TIMER_BASE(APIC_TIMER_BASE_DIV) | + APIC_LVT_TIMER_PERIODIC | LOCAL_TIMER_VECTOR; + apic_write(APIC_LVTT, lvtt1_value); /* * Divide PICLK by 16 */ tmp_value = apic_read(APIC_TDCR); - apic_write(APIC_TDCR , (tmp_value & ~APIC_TDR_DIV_1 ) - | APIC_TDR_DIV_16); + apic_write(APIC_TDCR, (tmp_value + & ~(APIC_TDR_DIV_1 | APIC_TDR_DIV_TMBASE)) + | APIC_TDR_DIV_16); tmp_value = apic_read(APIC_TMICT); apic_write(APIC_TMICT, clocks/APIC_DIVISOR); } -void __init wait_8254_wraparound(void) +void setup_APIC_timer(void * data) { - unsigned int curr_count, prev_count=~0; + unsigned int clocks = (unsigned int) data, slice, t0, t1, nr; + unsigned long flags; int delta; - curr_count = get_8254_timer_count(); - - do { - prev_count = curr_count; - curr_count = get_8254_timer_count(); - delta = curr_count-prev_count; + __save_flags(flags); + __sti(); + /* + * ok, Intel has some smart code in their APIC that knows + * if a CPU was in 'hlt' lowpower mode, and this increases + * its APIC arbitration priority. To avoid the external timer + * IRQ APIC event being in synchron with the APIC clock we + * introduce an interrupt skew to spread out timer events. + * + * The number of slices within a 'big' timeslice is smp_num_cpus+1 + */ + slice = clocks / (smp_num_cpus+1); + nr = cpu_number_map[smp_processor_id()] + 1; + printk("cpu: %d, clocks: %d, slice: %d, nr: %d.\n", + smp_processor_id(), clocks, slice, nr); /* - * This limit for delta seems arbitrary, but it isn't, it's - * slightly above the level of error a buggy Mercury/Neptune - * chipset timer can cause. + * Wait for IRQ0's slice: */ + wait_8254_wraparound(); - } while (delta<300); + __setup_APIC_LVTT(clocks); + + t0 = apic_read(APIC_TMCCT)*APIC_DIVISOR; + do { + t1 = apic_read(APIC_TMCCT)*APIC_DIVISOR; + delta = (int)(t0 - t1 - slice*nr); + } while (delta < 0); + + __setup_APIC_LVTT(clocks); + + printk("CPU%d\n", + smp_processor_id(), t0, t1, delta, slice, clocks); + + __restore_flags(flags); } /* @@ -2092,10 +727,11 @@ int __init calibrate_APIC_clock(void) { - unsigned long long t1,t2; - long tt1,tt2; - long calibration_result; + unsigned long long t1 = 0, t2 = 0; + long tt1, tt2; + long result; int i; + const int LOOPS = HZ/10; printk("calibrating APIC timer ... "); @@ -2104,7 +740,7 @@ * value into the APIC clock, we just want to get the * counter running for calibration. */ - setup_APIC_timer(1000000000); + __setup_APIC_LVTT(1000000000); /* * The timer chip counts down to zero. Let's wait @@ -2112,23 +748,24 @@ * (the current tick might have been already half done) */ - wait_8254_wraparound (); + wait_8254_wraparound(); /* * We wrapped around just now. Let's start: */ - rdtscll(t1); - tt1=apic_read(APIC_TMCCT); + if (cpu_has_tsc) + rdtscll(t1); + tt1 = apic_read(APIC_TMCCT); -#define LOOPS (HZ/10) /* * Let's wait LOOPS wraprounds: */ - for (i=0; ieip); + + if (--prof_counter[cpu] <= 0) { + int system = 1 - user; + struct task_struct * p = current; + + /* + * The multiplier may have changed since the last time we got + * to this point as a result of the user writing to + * /proc/profile. In this case we need to adjust the APIC + * timer accordingly. + * + * Interrupts are already masked off at this point. + */ + prof_counter[cpu] = prof_multiplier[cpu]; + if (prof_counter[cpu] != prof_old_multiplier[cpu]) { + __setup_APIC_LVTT(calibration_result/prof_counter[cpu]); + prof_old_multiplier[cpu] = prof_counter[cpu]; + } + + /* + * After doing the above, we need to make like + * a normal interrupt - otherwise timer interrupts + * ignore the global interrupt lock, which is the + * WrongThing (tm) to do. + */ + + irq_enter(cpu, 0); + update_one_process(p, 1, user, system, cpu); + if (p->pid) { + p->counter -= 1; + if (p->counter <= 0) { + p->counter = 0; + p->need_resched = 1; + } + if (p->priority < DEF_PRIORITY) { + kstat.cpu_nice += user; + kstat.per_cpu_nice[cpu] += user; + } else { + kstat.cpu_user += user; + kstat.per_cpu_user[cpu] += user; + } + kstat.cpu_system += system; + kstat.per_cpu_system[cpu] += system; + + } + irq_exit(cpu, 0); + } + + /* + * We take the 'long' return path, and there every subsystem + * grabs the apropriate locks (kernel lock/ irq lock). + * + * we might want to decouple profiling from the 'long path', + * and do the profiling totally in assembly. + * + * Currently this isn't too much of an issue (performance wise), + * we can take more than 100K local irqs per second on a 100 MHz P5. + */ +} + +/* + * Local APIC timer interrupt. This is the most natural way for doing + * local interrupts, but local timer interrupts can be emulated by + * broadcast interrupts too. [in case the hw doesnt support APIC timers] + * + * [ if a single-CPU system runs an SMP kernel then we call the local + * interrupt as well. Thus we cannot inline the local irq ... ] + */ +unsigned int apic_timer_irqs [NR_CPUS] = { 0, }; + +void smp_apic_timer_interrupt(struct pt_regs * regs) +{ + /* + * the NMI deadlock-detector uses this. + */ + apic_timer_irqs[smp_processor_id()]++; + + /* + * NOTE! We'd better ACK the irq immediately, + * because timer handling can be slow. + */ + ack_APIC_irq(); + smp_local_timer_interrupt(regs); +} diff -u --recursive --new-file v2.3.19/linux/arch/i386/kernel/smpboot.c linux/arch/i386/kernel/smpboot.c --- v2.3.19/linux/arch/i386/kernel/smpboot.c Wed Dec 31 16:00:00 1969 +++ linux/arch/i386/kernel/smpboot.c Thu Oct 7 10:17:08 1999 @@ -0,0 +1,1650 @@ +/* + * Intel MP v1.1/v1.4 specification compliant parsing routines. + * + * (c) 1995 Alan Cox, Building #3 + * (c) 1998, 1999 Ingo Molnar + * + * Much of the core SMP work is based on previous work by Thomas Radke, to + * whom a great many thanks are extended. + * + * Thanks to Intel for making available several different Pentium, + * Pentium Pro and Pentium-II/Xeon MP machines. + * Original development of Linux SMP code supported by Caldera. + * + * This code is released under the GNU public license version 2 or + * later. + * + * Fixes + * Felix Koop : NR_CPUS used properly + * Jose Renau : Handle single CPU case. + * Alan Cox : By repeated request 8) - Total BogoMIP report. + * Greg Wright : Fix for kernel stacks panic. + * Erich Boleyn : MP v1.4 and additional changes. + * Matthias Sattler : Changes for 2.1 kernel map. + * Michel Lespinasse : Changes for 2.1 kernel map. + * Michael Chastain : Change trampoline.S to gnu as. + * Alan Cox : Dumb bug: 'B' step PPro's are fine + * Ingo Molnar : Added APIC timers, based on code + * from Jose Renau + * Alan Cox : Added EBDA scanning + * Ingo Molnar : various cleanups and rewrites + * Tigran Aivazian : fixed "0.00 in /proc/uptime on SMP" bug. + * Maciej W. Rozycki : Bits for genuine 82489DX timers + */ + +#include +#include + +#include +#include +#include +#include + +#include +#include +#include + +/* Set if we find a B stepping CPU */ +static int smp_b_stepping = 0; + +/* Setup configured maximum number of CPUs to activate */ +static int max_cpus = -1; +/* 1 if "noapic" boot option passed */ +int skip_ioapic_setup = 0; + +/* Total count of live CPUs */ +int smp_num_cpus = 0; +/* Internal processor count */ +static unsigned int num_processors = 1; + +/* Have we found an SMP box */ +int smp_found_config = 0; + +/* Bitmask of physically existing CPUs */ +unsigned long cpu_present_map = 0; +/* Bitmask of currently online CPUs */ +unsigned long cpu_online_map = 0; + +/* which CPU maps to which logical number */ +volatile int cpu_number_map[NR_CPUS]; +/* which logical number maps to which CPU */ +volatile int __cpu_logical_map[NR_CPUS]; + +static volatile unsigned long cpu_callin_map = 0; +static volatile unsigned long cpu_callout_map = 0; + +/* Per CPU bogomips and other parameters */ +struct cpuinfo_x86 cpu_data[NR_CPUS]; +/* Processor that is doing the boot up */ +static unsigned int boot_cpu_id = 0; + +/* Tripped once we need to start cross invalidating */ +static int smp_activated = 0; +/* Set when the idlers are all forked */ +int smp_threads_ready = 0; + +/* + * Various Linux-internal data structures created from the + * MP-table. + */ +int apic_version [NR_CPUS]; +int mp_bus_id_to_type [MAX_MP_BUSSES] = { -1, }; +extern int nr_ioapics; +extern struct mpc_config_ioapic mp_ioapics [MAX_IO_APICS]; +extern int mp_irq_entries; +extern struct mpc_config_intsrc mp_irqs [MAX_IRQ_SOURCES]; +extern int mpc_default_type; +int mp_bus_id_to_pci_bus [MAX_MP_BUSSES] = { -1, }; +int mp_current_pci_id = 0; +unsigned long mp_lapic_addr = 0; +int pic_mode; + +extern void cache_APIC_registers (void); + +#define SMP_DEBUG 1 + +#if SMP_DEBUG +#define dprintk(x...) printk(##x) +#else +#define dprintk(x...) +#endif + +/* + * IA s/w dev Vol 3, Section 7.4 + */ +#define APIC_DEFAULT_PHYS_BASE 0xfee00000 + +/* + * Setup routine for controlling SMP activation + * + * Command-line option of "nosmp" or "maxcpus=0" will disable SMP + * activation entirely (the MPS table probe still happens, though). + * + * Command-line option of "maxcpus=", where is an integer + * greater than 0, limits the maximum number of CPUs activated in + * SMP mode to . + */ + +static int __init nosmp(char *str) +{ + max_cpus = 0; + return 1; +} + +__setup("nosmp", nosmp); + +static int __init maxcpus(char *str) +{ + get_option(&str, &max_cpus); + return 1; +} + +__setup("maxcpus=", maxcpus); + +/* + * Intel MP BIOS table parsing routines: + */ + +#ifndef CONFIG_X86_VISWS_APIC +/* + * Checksum an MP configuration block. + */ + +static int __init mpf_checksum(unsigned char *mp, int len) +{ + int sum=0; + while(len--) + sum+=*mp++; + return sum&0xFF; +} + +/* + * Processor encoding in an MP configuration block + */ + +static char __init *mpc_family(int family,int model) +{ + static char n[32]; + static char *model_defs[]= + { + "80486DX","80486DX", + "80486SX","80486DX/2 or 80487", + "80486SL","80486SX/2", + "Unknown","80486DX/2-WB", + "80486DX/4","80486DX/4-WB" + }; + + switch (family) { + case 0x04: + if (model < 10) + return model_defs[model]; + break; + + case 0x05: + return("Pentium(tm)"); + + case 0x06: + return("Pentium(tm) Pro"); + + case 0x0F: + if (model == 0x0F) + return("Special controller"); + } + sprintf(n,"Unknown CPU [%d:%d]",family, model); + return n; +} + +static void __init MP_processor_info (struct mpc_config_processor *m) +{ + int ver; + + if (!(m->mpc_cpuflag & CPU_ENABLED)) + return; + + printk("Processor #%d %s APIC version %d\n", + m->mpc_apicid, + mpc_family( (m->mpc_cpufeature & CPU_FAMILY_MASK)>>8 , + (m->mpc_cpufeature & CPU_MODEL_MASK)>>4), + m->mpc_apicver); + +#ifdef SMP_DEBUG + if (m->mpc_featureflag&(1<<0)) + printk(" Floating point unit present.\n"); + if (m->mpc_featureflag&(1<<7)) + printk(" Machine Exception supported.\n"); + if (m->mpc_featureflag&(1<<8)) + printk(" 64 bit compare & exchange supported.\n"); + if (m->mpc_featureflag&(1<<9)) + printk(" Internal APIC present.\n"); +#endif + + if (m->mpc_cpuflag & CPU_BOOTPROCESSOR) { + dprintk(" Bootup CPU\n"); + boot_cpu_id = m->mpc_apicid; + } else + /* Boot CPU already counted */ + num_processors++; + + if (m->mpc_apicid > NR_CPUS) { + printk("Processor #%d unused. (Max %d processors).\n", + m->mpc_apicid, NR_CPUS); + return; + } + ver = m->mpc_apicver; + + cpu_present_map |= (1<mpc_apicid); + /* + * Validate version + */ + if (ver == 0x0) { + printk("BIOS bug, APIC version is 0 for CPU#%d! fixing up to 0x10. (tell your hw vendor)\n", m->mpc_apicid); + ver = 0x10; + } + apic_version[m->mpc_apicid] = ver; +} + +static void __init MP_bus_info (struct mpc_config_bus *m) +{ + char str[7]; + + memcpy(str, m->mpc_bustype, 6); + str[6] = 0; + dprintk("Bus #%d is %s\n", m->mpc_busid, str); + + if (strncmp(str, "ISA", 3) == 0) { + mp_bus_id_to_type[m->mpc_busid] = MP_BUS_ISA; + } else { + if (strncmp(str, "EISA", 4) == 0) { + mp_bus_id_to_type[m->mpc_busid] = MP_BUS_EISA; + } else { + if (strncmp(str, "PCI", 3) == 0) { + mp_bus_id_to_type[m->mpc_busid] = MP_BUS_PCI; + mp_bus_id_to_pci_bus[m->mpc_busid] = mp_current_pci_id; + mp_current_pci_id++; + } else { + printk("Unknown bustype %s\n", str); + panic("cannot handle bus - mail to linux-smp@vger.rutgers.edu"); + } } } +} + +static void __init MP_ioapic_info (struct mpc_config_ioapic *m) +{ + if (!(m->mpc_flags & MPC_APIC_USABLE)) + return; + + printk("I/O APIC #%d Version %d at 0x%lX.\n", + m->mpc_apicid, m->mpc_apicver, m->mpc_apicaddr); + if (nr_ioapics >= MAX_IO_APICS) { + printk("Max # of I/O APICs (%d) exceeded (found %d).\n", + MAX_IO_APICS, nr_ioapics); + panic("Recompile kernel with bigger MAX_IO_APICS!.\n"); + } + mp_ioapics[nr_ioapics] = *m; + nr_ioapics++; +} + +static void __init MP_intsrc_info (struct mpc_config_intsrc *m) +{ + mp_irqs [mp_irq_entries] = *m; + if (++mp_irq_entries == MAX_IRQ_SOURCES) + panic("Max # of irq sources exceeded!!\n"); +} + +static void __init MP_lintsrc_info (struct mpc_config_lintsrc *m) +{ + /* + * Well it seems all SMP boards in existence + * use ExtINT/LVT1 == LINT0 and + * NMI/LVT2 == LINT1 - the following check + * will show us if this assumptions is false. + * Until then we do not have to add baggage. + */ + if ((m->mpc_irqtype == mp_ExtINT) && + (m->mpc_destapiclint != 0)) + BUG(); + if ((m->mpc_irqtype == mp_NMI) && + (m->mpc_destapiclint != 1)) + BUG(); +} + +/* + * Read/parse the MPC + */ + +static int __init smp_read_mpc(struct mp_config_table *mpc) +{ + char str[16]; + int count=sizeof(*mpc); + unsigned char *mpt=((unsigned char *)mpc)+count; + + if (memcmp(mpc->mpc_signature,MPC_SIGNATURE,4)) + { + panic("SMP mptable: bad signature [%c%c%c%c]!\n", + mpc->mpc_signature[0], + mpc->mpc_signature[1], + mpc->mpc_signature[2], + mpc->mpc_signature[3]); + return 1; + } + if (mpf_checksum((unsigned char *)mpc,mpc->mpc_length)) + { + panic("SMP mptable: checksum error!\n"); + return 1; + } + if (mpc->mpc_spec!=0x01 && mpc->mpc_spec!=0x04) + { + printk("Bad Config Table version (%d)!!\n",mpc->mpc_spec); + return 1; + } + memcpy(str,mpc->mpc_oem,8); + str[8]=0; + printk("OEM ID: %s ",str); + + memcpy(str,mpc->mpc_productid,12); + str[12]=0; + printk("Product ID: %s ",str); + + printk("APIC at: 0x%lX\n",mpc->mpc_lapic); + + /* save the local APIC address, it might be non-default */ + mp_lapic_addr = mpc->mpc_lapic; + + /* + * Now process the configuration blocks. + */ + while (count < mpc->mpc_length) { + switch(*mpt) { + case MP_PROCESSOR: + { + struct mpc_config_processor *m= + (struct mpc_config_processor *)mpt; + MP_processor_info(m); + mpt += sizeof(*m); + count += sizeof(*m); + break; + } + case MP_BUS: + { + struct mpc_config_bus *m= + (struct mpc_config_bus *)mpt; + MP_bus_info(m); + mpt += sizeof(*m); + count += sizeof(*m); + break; + } + case MP_IOAPIC: + { + struct mpc_config_ioapic *m= + (struct mpc_config_ioapic *)mpt; + MP_ioapic_info(m); + mpt+=sizeof(*m); + count+=sizeof(*m); + break; + } + case MP_INTSRC: + { + struct mpc_config_intsrc *m= + (struct mpc_config_intsrc *)mpt; + + MP_intsrc_info(m); + mpt+=sizeof(*m); + count+=sizeof(*m); + break; + } + case MP_LINTSRC: + { + struct mpc_config_lintsrc *m= + (struct mpc_config_lintsrc *)mpt; + MP_lintsrc_info(m); + mpt+=sizeof(*m); + count+=sizeof(*m); + break; + } + } + } + return num_processors; +} + +/* + * Scan the memory blocks for an SMP configuration block. + */ +static int __init smp_get_mpf(struct intel_mp_floating *mpf) +{ + printk("Intel MultiProcessor Specification v1.%d\n", mpf->mpf_specification); + if (mpf->mpf_feature2 & (1<<7)) { + printk(" IMCR and PIC compatibility mode.\n"); + pic_mode = 1; + } else { + printk(" Virtual Wire compatibility mode.\n"); + pic_mode = 0; + } + smp_found_config = 1; + /* + * default CPU id - if it's different in the mptable + * then we change it before first using it. + */ + boot_cpu_id = 0; + /* + * Now see if we need to read further. + */ + if (mpf->mpf_feature1 != 0) { + /* + * local APIC has default address + */ + mp_lapic_addr = APIC_DEFAULT_PHYS_BASE; + + /* + * 2 CPUs, numbered 0 & 1. + */ + cpu_present_map = 3; + num_processors = 2; + + nr_ioapics = 1; + mp_ioapics[0].mpc_apicaddr = 0xFEC00000; + /* + * Save the default type number, we + * need it later to set the IO-APIC + * up properly: + */ + mpc_default_type = mpf->mpf_feature1; + + printk("Bus #0 is "); + } + + switch (mpf->mpf_feature1) { + case 1: + case 5: + printk("ISA\n"); + break; + case 2: + printk("EISA with no IRQ0 and no IRQ13 DMA chaining\n"); + break; + case 6: + case 3: + printk("EISA\n"); + break; + case 4: + case 7: + printk("MCA\n"); + break; + case 0: + if (!mpf->mpf_physptr) + BUG(); + break; + default: + printk("???\nUnknown standard configuration %d\n", + mpf->mpf_feature1); + return 1; + } + if (mpf->mpf_feature1 > 4) { + printk("Bus #1 is PCI\n"); + + /* + * Set local APIC version to the integrated form. + * It's initialized to zero otherwise, representing + * a discrete 82489DX. + */ + apic_version[0] = 0x10; + apic_version[1] = 0x10; + } + /* + * Read the physical hardware table. Anything here will override the + * defaults. + */ + if (mpf->mpf_physptr) + smp_read_mpc((void *)mpf->mpf_physptr); + + __cpu_logical_map[0] = boot_cpu_id; + global_irq_holder = boot_cpu_id; + current->processor = boot_cpu_id; + + printk("Processors: %d\n", num_processors); + /* + * Only use the first configuration found. + */ + return 1; +} + +static int __init smp_scan_config(unsigned long base, unsigned long length) +{ + unsigned long *bp = phys_to_virt(base); + struct intel_mp_floating *mpf; + + dprintk("Scan SMP from %p for %ld bytes.\n", bp,length); + if (sizeof(*mpf) != 16) + printk("Error: MPF size\n"); + + while (length > 0) { + mpf = (struct intel_mp_floating *)bp; + if ((*bp == SMP_MAGIC_IDENT) && + (mpf->mpf_length == 1) && + !mpf_checksum((unsigned char *)bp, 16) && + ((mpf->mpf_specification == 1) + || (mpf->mpf_specification == 4)) ) { + + printk("found SMP MP-table at %08ld\n", + virt_to_phys(mpf)); + smp_get_mpf(mpf); + return 1; + } + bp += 4; + length -= 16; + } + return 0; +} + +void __init init_intel_smp (void) +{ + unsigned int address; + + /* + * FIXME: Linux assumes you have 640K of base ram.. + * this continues the error... + * + * 1) Scan the bottom 1K for a signature + * 2) Scan the top 1K of base RAM + * 3) Scan the 64K of bios + */ + if (smp_scan_config(0x0,0x400) || + smp_scan_config(639*0x400,0x400) || + smp_scan_config(0xF0000,0x10000)) + return; + /* + * If it is an SMP machine we should know now, unless the + * configuration is in an EISA/MCA bus machine with an + * extended bios data area. + * + * there is a real-mode segmented pointer pointing to the + * 4K EBDA area at 0x40E, calculate and scan it here. + * + * 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. These loaders are buggy and + * should be fixed. + */ + + address = *(unsigned short *)phys_to_virt(0x40E); + address <<= 4; + smp_scan_config(address, 0x1000); + if (smp_found_config) + printk(KERN_WARNING "WARNING: MP table in the EBDA can be UNSAFE, contact linux-smp@vger.rutgers.edu if you experience SMP problems!\n"); +} + +#else + +/* + * The Visual Workstation is Intel MP compliant in the hardware + * sense, but it doesnt have a BIOS(-configuration table). + * No problem for Linux. + */ +void __init init_visws_smp(void) +{ + smp_found_config = 1; + + cpu_present_map |= 2; /* or in id 1 */ + apic_version[1] |= 0x10; /* integrated APIC */ + apic_version[0] |= 0x10; + + mp_lapic_addr = APIC_DEFAULT_PHYS_BASE; +} + +#endif + +/* + * - Intel MP Configuration Table + * - or SGI Visual Workstation configuration + */ +void __init init_smp_config (void) +{ +#ifndef CONFIG_VISWS + init_intel_smp(); +#else + init_visws_smp(); +#endif +} + + + +/* + * Trampoline 80x86 program as an array. + */ + +extern unsigned char trampoline_data []; +extern unsigned char trampoline_end []; +static unsigned char *trampoline_base; + +/* + * Currently trivial. Write the real->protected mode + * bootstrap into the page concerned. The caller + * has made sure it's suitably aligned. + */ + +static unsigned long __init setup_trampoline(void) +{ + memcpy(trampoline_base, trampoline_data, trampoline_end - trampoline_data); + return virt_to_phys(trampoline_base); +} + +/* + * We are called very early to get the low memory for the + * SMP bootup trampoline page. + */ +unsigned long __init smp_alloc_memory(unsigned long mem_base) +{ + if (virt_to_phys((void *)mem_base) >= 0x9F000) + BUG(); + trampoline_base = (void *)mem_base; + return mem_base + PAGE_SIZE; +} + +/* + * The bootstrap kernel entry code has set these up. Save them for + * a given CPU + */ + +void __init smp_store_cpu_info(int id) +{ + struct cpuinfo_x86 *c=&cpu_data[id]; + + *c = boot_cpu_data; + c->pte_quick = 0; + c->pgd_quick = 0; + c->pgtable_cache_sz = 0; + identify_cpu(c); + /* + * Mask B, Pentium, but not Pentium MMX + */ + if (c->x86_vendor == X86_VENDOR_INTEL && + c->x86 == 5 && + c->x86_mask >= 1 && c->x86_mask <= 4 && + c->x86_model <= 3) + /* + * Remember we have B step Pentia with bugs + */ + smp_b_stepping = 1; +} + +/* + * Architecture specific routine called by the kernel just before init is + * fired off. This allows the BP to have everything in order [we hope]. + * At the end of this all the APs will hit the system scheduling and off + * we go. Each AP will load the system gdt's and jump through the kernel + * init into idle(). At this point the scheduler will one day take over + * and give them jobs to do. smp_callin is a standard routine + * we use to track CPUs as they power up. + */ + +static atomic_t smp_commenced = ATOMIC_INIT(0); + +void __init smp_commence(void) +{ + /* + * Lets the callins below out of their loop. + */ + dprintk("Setting commenced=1, go go go\n"); + + wmb(); + atomic_set(&smp_commenced,1); +} + +extern void __error_in_io_apic_c(void); + + +int get_maxlvt(void) +{ + unsigned int v, ver, maxlvt; + + v = apic_read(APIC_LVR); + ver = GET_APIC_VERSION(v); + /* 82489DXs do not report # of LVT entries. */ + maxlvt = APIC_INTEGRATED(ver) ? GET_APIC_MAXLVT(v) : 2; + return maxlvt; +} + +void __init setup_local_APIC(void) +{ + unsigned long value, ver, maxlvt; + + if ((SPURIOUS_APIC_VECTOR & 0x0f) != 0x0f) + __error_in_io_apic_c(); + + value = apic_read(APIC_SPIV); + value = 0xf; + /* + * Enable APIC + */ + value |= (1<<8); +#if 0 + /* Enable focus processor (bit==0) */ + value &= ~(1<<9); +#else + /* Disable focus processor (bit==1) */ + value |= (1<<9); +#endif + /* + * Set spurious IRQ vector + */ + value |= SPURIOUS_APIC_VECTOR; + apic_write(APIC_SPIV,value); + + /* + * Set up LVT0, LVT1: + * + * set up through-local-APIC on the BP's LINT0. This is not + * strictly necessery in pure symmetric-IO mode, but sometimes + * we delegate interrupts to the 8259A. + */ + if (hard_smp_processor_id() == boot_cpu_id) { + value = 0x00000700; + printk("enabled ExtINT on CPU#%d\n", hard_smp_processor_id()); + } else { + value = 0x00010700; + printk("masked ExtINT on CPU#%d\n", hard_smp_processor_id()); + } + apic_write_around(APIC_LVT0,value); + + /* + * only the BP should see the LINT1 NMI signal, obviously. + */ + if (hard_smp_processor_id() == boot_cpu_id) + value = 0x00000400; // unmask NMI + else + value = 0x00010400; // mask NMI + apic_write_around(APIC_LVT1,value); + + value = apic_read(APIC_LVR); + ver = GET_APIC_VERSION(value); + if (APIC_INTEGRATED(ver)) { /* !82489DX */ + maxlvt = get_maxlvt(); + /* + * Due to the Pentium erratum 3AP. + */ + if (maxlvt > 3) { + apic_readaround(APIC_SPIV); // not strictly necessery + apic_write(APIC_ESR, 0); + } + value = apic_read(APIC_ESR); + printk("ESR value before enabling vector: %08lx\n", value); + + value = apic_read(APIC_LVTERR); + value = ERROR_APIC_VECTOR; // enables sending errors + apic_write(APIC_LVTERR,value); + /* + * spec says clear errors after enabling vector. + */ + if (maxlvt != 3) { + apic_readaround(APIC_SPIV); + apic_write(APIC_ESR, 0); + } + value = apic_read(APIC_ESR); + printk("ESR value after enabling vector: %08lx\n", value); + } else + printk("No ESR for 82489DX.\n"); + + /* + * Set Task Priority to 'accept all'. We never change this + * later on. + */ + value = apic_read(APIC_TASKPRI); + value &= ~APIC_TPRI_MASK; + apic_write(APIC_TASKPRI,value); + + /* + * Set up the logical destination ID and put the + * APIC into flat delivery mode. + */ + value = apic_read(APIC_LDR); + value &= ~APIC_LDR_MASK; + value |= (1<<(smp_processor_id()+24)); + apic_write(APIC_LDR,value); + + value = apic_read(APIC_DFR); + value |= SET_APIC_DFR(0xf); + apic_write(APIC_DFR, value); +} + +unsigned long __init init_smp_mappings(unsigned long memory_start) +{ + unsigned long apic_phys; + + memory_start = PAGE_ALIGN(memory_start); + if (smp_found_config) { + apic_phys = mp_lapic_addr; + } else { + /* + * set up a fake all zeroes page to simulate the + * local APIC and another one for the IO-APIC. We + * could use the real zero-page, but it's safer + * this way if some buggy code writes to this page ... + */ + apic_phys = __pa(memory_start); + memset((void *)memory_start, 0, PAGE_SIZE); + memory_start += PAGE_SIZE; + } + set_fixmap(FIX_APIC_BASE,apic_phys); + dprintk("mapped APIC to %08lx (%08lx)\n", APIC_BASE, apic_phys); + +#ifdef CONFIG_X86_IO_APIC + { + unsigned long ioapic_phys, idx = FIX_IO_APIC_BASE_0; + int i; + + for (i = 0; i < nr_ioapics; i++) { + if (smp_found_config) { + ioapic_phys = mp_ioapics[i].mpc_apicaddr; + } else { + ioapic_phys = __pa(memory_start); + memset((void *)memory_start, 0, PAGE_SIZE); + memory_start += PAGE_SIZE; + } + set_fixmap(idx,ioapic_phys); + dprintk("mapped IOAPIC to %08lx (%08lx)\n", + __fix_to_virt(idx), ioapic_phys); + idx++; + } + } +#endif + + return memory_start; +} + +/* + * TSC synchronization. + * + * We first check wether all CPUs have their TSC's synchronized, + * then we print a warning if not, and always resync. + */ + +static atomic_t tsc_start_flag = ATOMIC_INIT(0); +static atomic_t tsc_count_start = ATOMIC_INIT(0); +static atomic_t tsc_count_stop = ATOMIC_INIT(0); +static unsigned long long tsc_values[NR_CPUS] = { 0, }; + +#define NR_LOOPS 5 + +extern unsigned long fast_gettimeoffset_quotient; + +/* + * accurate 64-bit/32-bit division, expanded to 32-bit divisions and 64-bit + * multiplication. Not terribly optimized but we need it at boot time only + * anyway. + * + * result == a / b + * == (a1 + a2*(2^32)) / b + * == a1/b + a2*(2^32/b) + * == a1/b + a2*((2^32-1)/b) + a2/b + (a2*((2^32-1) % b))/b + * ^---- (this multiplication can overflow) + */ + +static unsigned long long div64 (unsigned long long a, unsigned long b0) +{ + unsigned int a1, a2; + unsigned long long res; + + a1 = ((unsigned int*)&a)[0]; + a2 = ((unsigned int*)&a)[1]; + + res = a1/b0 + + (unsigned long long)a2 * (unsigned long long)(0xffffffff/b0) + + a2 / b0 + + (a2 * (0xffffffff % b0)) / b0; + + return res; +} + +static void __init synchronize_tsc_bp (void) +{ + int i; + unsigned long long t0; + unsigned long long sum, avg; + long long delta; + unsigned long one_usec; + int buggy = 0; + + printk("checking TSC synchronization across CPUs: "); + + one_usec = ((1<<30)/fast_gettimeoffset_quotient)*(1<<2); + + atomic_set(&tsc_start_flag, 1); + wmb(); + + /* + * We loop a few times to get a primed instruction cache, + * then the last pass is more or less synchronized and + * the BP and APs set their cycle counters to zero all at + * once. This reduces the chance of having random offsets + * between the processors, and guarantees that the maximum + * delay between the cycle counters is never bigger than + * the latency of information-passing (cachelines) between + * two CPUs. + */ + for (i = 0; i < NR_LOOPS; i++) { + /* + * all APs synchronize but they loop on '== num_cpus' + */ + while (atomic_read(&tsc_count_start) != smp_num_cpus-1) mb(); + atomic_set(&tsc_count_stop, 0); + wmb(); + /* + * this lets the APs save their current TSC: + */ + atomic_inc(&tsc_count_start); + + rdtscll(tsc_values[smp_processor_id()]); + /* + * We clear the TSC in the last loop: + */ + if (i == NR_LOOPS-1) + write_tsc(0, 0); + + /* + * Wait for all APs to leave the synchronization point: + */ + while (atomic_read(&tsc_count_stop) != smp_num_cpus-1) mb(); + atomic_set(&tsc_count_start, 0); + wmb(); + atomic_inc(&tsc_count_stop); + } + + sum = 0; + for (i = 0; i < NR_CPUS; i++) { + if (!(cpu_online_map & (1 << i))) + continue; + + t0 = tsc_values[i]; + sum += t0; + } + avg = div64(sum, smp_num_cpus); + + sum = 0; + for (i = 0; i < NR_CPUS; i++) { + if (!(cpu_online_map & (1 << i))) + continue; + + delta = tsc_values[i] - avg; + if (delta < 0) + delta = -delta; + /* + * We report bigger than 2 microseconds clock differences. + */ + if (delta > 2*one_usec) { + long realdelta; + if (!buggy) { + buggy = 1; + printk("\n"); + } + realdelta = div64(delta, one_usec); + if (tsc_values[i] < avg) + realdelta = -realdelta; + + printk("BIOS BUG: CPU#%d improperly initialized, has %ld usecs TSC skew! FIXED.\n", + i, realdelta); + } + + sum += delta; + } + if (!buggy) + printk("passed.\n"); +} + +static void __init synchronize_tsc_ap (void) +{ + int i; + + /* + * smp_num_cpus is not necessarily known at the time + * this gets called, so we first wait for the BP to + * finish SMP initialization: + */ + while (!atomic_read(&tsc_start_flag)) mb(); + + for (i = 0; i < NR_LOOPS; i++) { + atomic_inc(&tsc_count_start); + while (atomic_read(&tsc_count_start) != smp_num_cpus) mb(); + + rdtscll(tsc_values[smp_processor_id()]); + if (i == NR_LOOPS-1) + write_tsc(0, 0); + + atomic_inc(&tsc_count_stop); + while (atomic_read(&tsc_count_stop) != smp_num_cpus) mb(); + } +} +#undef NR_LOOPS + +extern void calibrate_delay(void); + +void __init smp_callin(void) +{ + int cpuid; + unsigned long timeout; + + /* + * (This works even if the APIC is not enabled.) + */ + cpuid = GET_APIC_ID(apic_read(APIC_ID)); + + dprintk("CPU#%d waiting for CALLOUT\n", cpuid); + + /* + * STARTUP IPIs are fragile beasts as they might sometimes + * trigger some glue motherboard logic. Complete APIC bus + * silence for 1 second, this overestimates the time the + * boot CPU is spending to send the up to 2 STARTUP IPIs + * by a factor of two. This should be enough. + */ + + /* + * Waiting 2s total for startup (udelay is not yet working) + */ + timeout = jiffies + 2*HZ; + while (time_before(jiffies, timeout)) { + /* + * Has the boot CPU finished it's STARTUP sequence? + */ + if (test_bit(cpuid, &cpu_callout_map)) + break; + } + + if (!time_before(jiffies, timeout)) { + printk("BUG: CPU%d started up but did not get a callout!\n", + cpuid); + BUG(); + } + + /* + * the boot CPU has finished the init stage and is spinning + * on callin_map until we finish. We are free to set up this + * CPU, first the APIC. (this is probably redundant on most + * boards) + */ + + dprintk("CALLIN, before setup_local_APIC().\n"); + setup_local_APIC(); + + sti(); + +#ifdef CONFIG_MTRR + /* + * Must be done before calibration delay is computed + */ + mtrr_init_secondary_cpu (); +#endif + /* + * Get our bogomips. + */ + calibrate_delay(); + dprintk("Stack at about %p\n",&cpuid); + + /* + * Save our processor parameters + */ + smp_store_cpu_info(cpuid); + + /* + * Allow the master to continue. + */ + set_bit(cpuid, &cpu_callin_map); + + /* + * Synchronize the TSC with the BP + */ + if (cpu_has_tsc) + synchronize_tsc_ap (); +} + +int cpucount = 0; + +extern int cpu_idle(void); + +/* + * Activate a secondary processor. + */ +int __init start_secondary(void *unused) +{ + /* + * Dont put anything before smp_callin(), SMP + * booting is too fragile that we want to limit the + * things done here to the most necessary things. + */ + cpu_init(); + smp_callin(); + while (!atomic_read(&smp_commenced)) + /* nothing */ ; + return cpu_idle(); +} + +/* + * Everything has been set up for the secondary + * CPUs - they just need to reload everything + * from the task structure + * This function must not return. + */ +void __init initialize_secondary(void) +{ + /* + * We don't actually need to load the full TSS, + * basically just the stack pointer and the eip. + */ + + asm volatile( + "movl %0,%%esp\n\t" + "jmp *%1" + : + :"r" (current->thread.esp),"r" (current->thread.eip)); +} + +extern struct { + void * esp; + unsigned short ss; +} stack_start; + +static int __init fork_by_hand(void) +{ + struct pt_regs regs; + /* + * don't care about the eip and regs settings since + * we'll never reschedule the forked task. + */ + return do_fork(CLONE_VM|CLONE_PID, 0, ®s); +} + +static void __init do_boot_cpu(int i) +{ + unsigned long cfg; + pgd_t maincfg; + struct task_struct *idle; + unsigned long send_status, accept_status; + int timeout, num_starts, j; + unsigned long start_eip; + + cpucount++; + /* + * We can't use kernel_thread since we must avoid to + * reschedule the child. + */ + if (fork_by_hand() < 0) + panic("failed fork for CPU %d", i); + + /* + * We remove it from the pidhash and the runqueue + * once we got the process: + */ + idle = init_task.prev_task; + if (!idle) + panic("No idle process for CPU %d", i); + + idle->processor = i; + __cpu_logical_map[cpucount] = i; + cpu_number_map[i] = cpucount; + idle->has_cpu = 1; /* we schedule the first task manually */ + idle->thread.eip = (unsigned long) start_secondary; + + del_from_runqueue(idle); + unhash_process(idle); + init_tasks[cpucount] = idle; + + /* start_eip had better be page-aligned! */ + start_eip = setup_trampoline(); + + /* So we see what's up */ + printk("Booting processor %d eip %lx\n", i, start_eip); + stack_start.esp = (void *) (1024 + PAGE_SIZE + (char *)idle); + + /* + * This grunge runs the startup process for + * the targeted processor. + */ + + dprintk("Setting warm reset code and vector.\n"); + + CMOS_WRITE(0xa, 0xf); + local_flush_tlb(); + dprintk("1.\n"); + *((volatile unsigned short *) phys_to_virt(0x469)) = start_eip >> 4; + dprintk("2.\n"); + *((volatile unsigned short *) phys_to_virt(0x467)) = start_eip & 0xf; + dprintk("3.\n"); + + maincfg=swapper_pg_dir[0]; + ((unsigned long *)swapper_pg_dir)[0]=0x102007; + + /* + * Be paranoid about clearing APIC errors. + */ + + if (APIC_INTEGRATED(apic_version[i])) { + apic_readaround(APIC_SPIV); + apic_write(APIC_ESR, 0); + accept_status = (apic_read(APIC_ESR) & 0xEF); + } + + /* + * Status is now clean + */ + send_status = 0; + accept_status = 0; + + /* + * Starting actual IPI sequence... + */ + + dprintk("Asserting INIT.\n"); + + /* + * Turn INIT on + */ + cfg = apic_read(APIC_ICR2); + cfg &= 0x00FFFFFF; + + /* + * Target chip + */ + apic_write(APIC_ICR2, cfg | SET_APIC_DEST_FIELD(i)); + + /* + * Send IPI + */ + cfg = apic_read(APIC_ICR); + cfg &= ~0xCDFFF; + cfg |= (APIC_DEST_LEVELTRIG | APIC_DEST_ASSERT | APIC_DEST_DM_INIT); + apic_write(APIC_ICR, cfg); + + udelay(200); + dprintk("Deasserting INIT.\n"); + + /* Target chip */ + cfg = apic_read(APIC_ICR2); + cfg &= 0x00FFFFFF; + apic_write(APIC_ICR2, cfg|SET_APIC_DEST_FIELD(i)); + + /* Send IPI */ + cfg = apic_read(APIC_ICR); + cfg &= ~0xCDFFF; + cfg |= (APIC_DEST_LEVELTRIG | APIC_DEST_DM_INIT); + apic_write(APIC_ICR, cfg); + + /* + * Should we send STARTUP IPIs ? + * + * Determine this based on the APIC version. + * If we don't have an integrated APIC, don't + * send the STARTUP IPIs. + */ + + if (APIC_INTEGRATED(apic_version[i])) + num_starts = 2; + else + num_starts = 0; + + /* + * Run STARTUP IPI loop. + */ + + for (j = 1; j <= num_starts; j++) { + dprintk("Sending STARTUP #%d.\n",j); + apic_readaround(APIC_SPIV); + apic_write(APIC_ESR, 0); + apic_read(APIC_ESR); + dprintk("After apic_write.\n"); + + /* + * STARTUP IPI + */ + + /* Target chip */ + cfg = apic_read(APIC_ICR2); + cfg &= 0x00FFFFFF; + apic_write(APIC_ICR2, cfg|SET_APIC_DEST_FIELD(i)); + + /* Boot on the stack */ + cfg = apic_read(APIC_ICR); + cfg &= ~0xCDFFF; + cfg |= (APIC_DEST_DM_STARTUP | (start_eip >> 12)); + + /* Kick the second */ + apic_write(APIC_ICR, cfg); + + dprintk("Startup point 1.\n"); + + dprintk("Waiting for send to finish...\n"); + timeout = 0; + do { + dprintk("+"); + udelay(100); + send_status = apic_read(APIC_ICR) & 0x1000; + } while (send_status && (timeout++ < 1000)); + + /* + * Give the other CPU some time to accept the IPI. + */ + udelay(200); + accept_status = (apic_read(APIC_ESR) & 0xEF); + if (send_status || accept_status) + break; + } + dprintk("After Startup.\n"); + + if (send_status) + printk("APIC never delivered???\n"); + if (accept_status) + printk("APIC delivery error (%lx).\n", accept_status); + + if (!send_status && !accept_status) { + /* + * allow APs to start initializing. + */ + dprintk("Before Callout %d.\n", i); + set_bit(i, &cpu_callout_map); + dprintk("After Callout %d.\n", i); + + /* + * Wait 5s total for a response + */ + for (timeout = 0; timeout < 50000; timeout++) { + if (test_bit(i, &cpu_callin_map)) + break; /* It has booted */ + udelay(100); + } + + if (test_bit(i, &cpu_callin_map)) { + /* number CPUs logically, starting from 1 (BSP is 0) */ + printk("OK.\n"); + printk("CPU%d: ", i); + print_cpu_info(&cpu_data[i]); + } else { + if (*((volatile unsigned char *)phys_to_virt(8192)) + == 0xA5) /* trampoline code not run */ + printk("Stuck ??\n"); + else + printk("CPU booted but not responding.\n"); + } + dprintk("CPU has booted.\n"); + } else { + __cpu_logical_map[cpucount] = -1; + cpu_number_map[i] = -1; + cpucount--; + } + + swapper_pg_dir[0]=maincfg; + local_flush_tlb(); + + /* mark "stuck" area as not stuck */ + *((volatile unsigned long *)phys_to_virt(8192)) = 0; +} + +cycles_t cacheflush_time; +extern unsigned long cpu_hz; + +static void smp_tune_scheduling (void) +{ + unsigned long cachesize; + /* + * Rough estimation for SMP scheduling, this is the number of + * cycles it takes for a fully memory-limited process to flush + * the SMP-local cache. + * + * (For a P5 this pretty much means we will choose another idle + * CPU almost always at wakeup time (this is due to the small + * L1 cache), on PIIs it's around 50-100 usecs, depending on + * the cache size) + */ + + if (!cpu_hz) { + /* + * this basically disables processor-affinity + * scheduling on SMP without a TSC. + */ + cacheflush_time = 0; + return; + } else { + cachesize = boot_cpu_data.x86_cache_size; + if (cachesize == -1) + cachesize = 8; /* Pentiums */ + + cacheflush_time = cpu_hz/1024*cachesize/5000; + } + + printk("per-CPU timeslice cutoff: %ld.%02ld usecs.\n", + (long)cacheflush_time/(cpu_hz/1000000), + ((long)cacheflush_time*100/(cpu_hz/1000000)) % 100); +} + +/* + * Cycle through the processors sending APIC IPIs to boot each. + */ + +extern int prof_multiplier[NR_CPUS]; +extern int prof_old_multiplier[NR_CPUS]; +extern int prof_counter[NR_CPUS]; + +void __init smp_boot_cpus(void) +{ + int i; + +#ifdef CONFIG_MTRR + /* Must be done before other processors booted */ + mtrr_init_boot_cpu (); +#endif + /* + * Initialize the logical to physical CPU number mapping + * and the per-CPU profiling counter/multiplier + */ + + for (i = 0; i < NR_CPUS; i++) { + cpu_number_map[i] = -1; + prof_counter[i] = 1; + prof_old_multiplier[i] = 1; + prof_multiplier[i] = 1; + } + + /* + * Setup boot CPU information + */ + + smp_store_cpu_info(boot_cpu_id); /* Final full version of the data */ + smp_tune_scheduling(); + printk("CPU%d: ", boot_cpu_id); + print_cpu_info(&cpu_data[boot_cpu_id]); + + /* + * not necessary because the MP table should list the boot + * CPU too, but we do it for the sake of robustness anyway. + * (and for the case when a non-SMP board boots an SMP kernel) + */ + cpu_present_map |= (1 << hard_smp_processor_id()); + + cpu_number_map[boot_cpu_id] = 0; + + init_idle(); + + /* + * If we couldnt find an SMP configuration at boot time, + * get out of here now! + */ + + if (!smp_found_config) { + printk(KERN_NOTICE "SMP motherboard not detected. Using dummy APIC emulation.\n"); +#ifndef CONFIG_VISWS + io_apic_irqs = 0; +#endif + cpu_online_map = cpu_present_map; + smp_num_cpus = 1; + goto smp_done; + } + + /* + * If SMP should be disabled, then really disable it! + */ + + if (!max_cpus) { + smp_found_config = 0; + printk(KERN_INFO "SMP mode deactivated, forcing use of dummy APIC emulation.\n"); + } + +#ifdef SMP_DEBUG + { + int reg; + + /* + * This is to verify that we're looking at + * a real local APIC. Check these against + * your board if the CPUs aren't getting + * started for no apparent reason. + */ + + reg = apic_read(APIC_LVR); + dprintk("Getting VERSION: %x\n", reg); + + apic_write(APIC_LVR, 0); + reg = apic_read(APIC_LVR); + dprintk("Getting VERSION: %x\n", reg); + + /* + * The two version reads above should print the same + * NON-ZERO!!! numbers. If the second one is zero, + * there is a problem with the APIC write/read + * definitions. + * + * The next two are just to see if we have sane values. + * They're only really relevant if we're in Virtual Wire + * compatibility mode, but most boxes are anymore. + */ + + + reg = apic_read(APIC_LVT0); + dprintk("Getting LVT0: %x\n", reg); + + reg = apic_read(APIC_LVT1); + dprintk("Getting LVT1: %x\n", reg); + } +#endif + + setup_local_APIC(); + + if (GET_APIC_ID(apic_read(APIC_ID)) != boot_cpu_id) + BUG(); + + /* + * Now scan the CPU present map and fire up the other CPUs. + */ + + /* + * Add all detected CPUs. (later on we can down individual + * CPUs which will change cpu_online_map but not necessarily + * cpu_present_map. We are pretty much ready for hot-swap CPUs.) + */ + cpu_online_map = cpu_present_map; + mb(); + + dprintk("CPU map: %lx\n", cpu_present_map); + + for (i = 0; i < NR_CPUS; i++) { + /* + * Don't even attempt to start the boot CPU! + */ + if (i == boot_cpu_id) + continue; + + if ((cpu_online_map & (1 << i)) + && (max_cpus < 0 || max_cpus > cpucount+1)) { + do_boot_cpu(i); + } + + /* + * Make sure we unmap all failed CPUs + */ + if (cpu_number_map[i] == -1 && (cpu_online_map & (1 << i))) { + printk("CPU #%d not responding - cannot use it.\n",i); + cpu_online_map &= ~(1 << i); + } + } + + /* + * Cleanup possible dangling ends... + */ + +#ifndef CONFIG_VISWS + { + unsigned long cfg; + + /* + * Install writable page 0 entry to set BIOS data area. + */ + cfg = pg0[0]; + /* writeable, present, addr 0 */ + pg0[0] = _PAGE_RW | _PAGE_PRESENT | 0; + local_flush_tlb(); + + /* + * Paranoid: Set warm reset code and vector here back + * to default values. + */ + CMOS_WRITE(0, 0xf); + + *((volatile long *) phys_to_virt(0x467)) = 0; + + /* + * Restore old page 0 entry. + */ + pg0[0] = cfg; + local_flush_tlb(); + } +#endif + + /* + * Allow the user to impress friends. + */ + + dprintk("Before bogomips.\n"); + if (!cpucount) { + printk(KERN_ERR "Error: only one processor found.\n"); + cpu_online_map = (1<used_math) __asm__("frstor %0": :"m" (current->thread.i387)); else @@ -489,7 +588,6 @@ pmd_t * pmd; pte_t * pte; -return; /* * Allocate a new page in virtual address space, * move the IDT into it and write protect this page. @@ -658,7 +756,7 @@ */ set_fixmap(FIX_APIC_BASE, APIC_PHYS_BASE); printk("Local APIC ID %lx\n", apic_read(APIC_ID)); - printk("Local APIC Version %lx\n", apic_read(APIC_VERSION)); + printk("Local APIC Version %lx\n", apic_read(APIC_LVR)); set_fixmap(FIX_CO_CPU, CO_CPU_PHYS); printk("Cobalt Revision %lx\n", co_cpu_read(CO_CPU_REV)); @@ -679,7 +777,7 @@ set_trap_gate(0,÷_error); set_trap_gate(1,&debug); - set_trap_gate(2,&nmi); + set_intr_gate(2,&nmi); set_system_gate(3,&int3); /* int3-5 can be called from all */ set_system_gate(4,&overflow); set_system_gate(5,&bounds); diff -u --recursive --new-file v2.3.19/linux/arch/m68k/config.in linux/arch/m68k/config.in --- v2.3.19/linux/arch/m68k/config.in Tue Sep 7 12:14:06 1999 +++ linux/arch/m68k/config.in Thu Oct 7 10:17:08 1999 @@ -10,40 +10,31 @@ endmenu mainmenu_option next_comment -comment 'Loadable module support' -bool 'Enable loadable module support' CONFIG_MODULES -if [ "$CONFIG_MODULES" = "y" ]; then - bool 'Set version information on all symbols for modules' CONFIG_MODVERSIONS - bool 'Kernel module loader' CONFIG_KMOD -fi -endmenu - -mainmenu_option next_comment comment 'Platform dependent setup' bool 'Amiga support' CONFIG_AMIGA bool 'Atari support' CONFIG_ATARI if [ "$CONFIG_ATARI" = "y" ]; then - bool ' Hades support' CONFIG_HADES - if [ "$CONFIG_HADES" = "y" ]; then - define_bool CONFIG_PCI y - fi + bool ' Hades support' CONFIG_HADES + if [ "$CONFIG_HADES" = "y" ]; then + define_bool CONFIG_PCI y + fi fi bool 'Macintosh support' CONFIG_MAC if [ "$CONFIG_MAC" = "y" ]; then - define_bool CONFIG_NUBUS y - define_bool CONFIG_M68K_L2_CACHE y + define_bool CONFIG_NUBUS y + define_bool CONFIG_M68K_L2_CACHE y fi bool 'Apollo support' CONFIG_APOLLO bool 'VME (Motorola and BVM) support' CONFIG_VME if [ "$CONFIG_VME" = "y" ]; then - bool 'MVME147 support' CONFIG_MVME147 - bool 'MVME162, 166 and 167 support' CONFIG_MVME16x - bool 'BVME4000 and BVME6000 support' CONFIG_BVME6000 + bool ' MVME147 support' CONFIG_MVME147 + bool ' MVME162, 166 and 167 support' CONFIG_MVME16x + bool ' BVME4000 and BVME6000 support' CONFIG_BVME6000 fi bool 'HP9000/300 support' CONFIG_HP300 if [ "$CONFIG_HP300" = "y" ]; then - bool 'DIO bus support' CONFIG_DIO + bool ' DIO bus support' CONFIG_DIO fi bool 'Sun3x support' CONFIG_SUN3X @@ -56,19 +47,19 @@ bool '68040 support' CONFIG_M68040 bool '68060 support' CONFIG_M68060 if [ "$CONFIG_EXPERIMENTAL" = "y" ]; then - bool 'Math emulation support' CONFIG_M68KFPU_EMU - if [ "$CONFIG_M68KFPU_EMU" = "y" ]; then - bool 'Math emulation extra precision' CONFIG_M68KFPU_EMU_EXTRAPREC - bool 'Math emulation only kernel' CONFIG_M68KFPU_EMU_ONLY - fi + bool 'Math emulation support (EXPERIMENTAL)' CONFIG_M68KFPU_EMU + if [ "$CONFIG_M68KFPU_EMU" = "y" ]; then + bool ' Math emulation extra precision' CONFIG_M68KFPU_EMU_EXTRAPREC + bool ' Math emulation only kernel' CONFIG_M68KFPU_EMU_ONLY + fi fi bool 'Advanced configuration options' CONFIG_ADVANCED if [ "$CONFIG_ADVANCED" = "y" ]; then - bool 'Use read-modify-write instructions' CONFIG_RMW_INSNS - bool 'Use one physical chunk of memory only' CONFIG_SINGLE_MEMORY_CHUNK - if [ "$CONFIG_M68060" = "y" ]; then - bool 'Use write-through caching for 68060 supervisor accesses' CONFIG_060_WRITETHROUGH - fi + bool 'Use read-modify-write instructions' CONFIG_RMW_INSNS + bool 'Use one physical chunk of memory only' CONFIG_SINGLE_MEMORY_CHUNK + if [ "$CONFIG_M68060" = "y" ]; then + bool 'Use write-through caching for 68060 supervisor accesses' CONFIG_060_WRITETHROUGH + fi fi endmenu @@ -86,55 +77,64 @@ if [ "$CONFIG_AMIGA" = "y" ]; then bool 'Amiga Zorro (AutoConfig) bus support' CONFIG_ZORRO if [ "$CONFIG_EXPERIMENTAL" = "y" ]; then - bool 'Amiga 1200/600 PCMCIA support' CONFIG_AMIGA_PCMCIA + bool 'Amiga 1200/600 PCMCIA support (EXPERIMENTAL)' CONFIG_AMIGA_PCMCIA fi fi if [ "$CONFIG_ATARI" = "y" ]; then - bool 'Support for ST-RAM as swap space' CONFIG_STRAM_SWAP - bool 'ST-RAM statistics in /proc' CONFIG_STRAM_PROC + bool 'Support for ST-RAM as swap space' CONFIG_STRAM_SWAP + bool 'ST-RAM statistics in /proc' CONFIG_STRAM_PROC fi if [ "$CONFIG_AMIGA" = "y" -o "$CONFIG_ATARI" = "y" ]; then - bool 'Use power LED as a heartbeat' CONFIG_HEARTBEAT + bool 'Use power LED as a heartbeat' CONFIG_HEARTBEAT else if [ "$CONFIG_HP300" = "y" ]; then -# We have a dedicated heartbeat LED. :-) - define_bool CONFIG_HEARTBEAT y + # We have a dedicated heartbeat LED. :-) + define_bool CONFIG_HEARTBEAT y fi fi bool '/proc/hardware support' CONFIG_PROC_HARDWARE if [ "$CONFIG_EXPERIMENTAL" = "y" ]; then - tristate 'Parallel port support (EXPERIMENTAL)' CONFIG_PARPORT - if [ "$CONFIG_PARPORT" != "n" ]; then - if [ "$CONFIG_AMIGA" != "n" ]; then - dep_tristate ' Amiga builtin port' CONFIG_PARPORT_AMIGA $CONFIG_PARPORT - if [ "$CONFIG_ZORRO" != "n" ]; then - dep_tristate ' Multiface III parallel port' CONFIG_PARPORT_MFC3 $CONFIG_PARPORT + tristate 'Parallel port support (EXPERIMENTAL)' CONFIG_PARPORT + if [ "$CONFIG_PARPORT" != "n" ]; then + if [ "$CONFIG_AMIGA" != "n" ]; then + dep_tristate ' Amiga builtin port' CONFIG_PARPORT_AMIGA $CONFIG_PARPORT + if [ "$CONFIG_ZORRO" != "n" ]; then + dep_tristate ' Multiface III parallel port' CONFIG_PARPORT_MFC3 $CONFIG_PARPORT + fi fi - fi - if [ "$CONFIG_Q40" != "n" ]; then - tristate ' Q40 Parallel port' CONFIG_PARPORT - if [ "$CONFIG_PARPORT" != "n" ]; then - define_bool CONFIG_PARPORT_PC y - fi - fi - fi - if [ "$CONFIG_ATARI" == "y" ]; then - dep_tristate ' Atari builtin port' CONFIG_PARPORT_ATARI $CONFIG_PARPORT - fi - dep_tristate 'Parallel printer support' CONFIG_PRINTER $CONFIG_PARPORT - if [ "$CONFIG_PRINTER" != "n" ]; then - bool ' Support IEEE1284 status readback' CONFIG_PRINTER_READBACK - fi + if [ "$CONFIG_Q40" != "n" ]; then + tristate ' Q40 Parallel port' CONFIG_PARPORT + if [ "$CONFIG_PARPORT" != "n" ]; then + define_bool CONFIG_PARPORT_PC y + fi + fi + fi + if [ "$CONFIG_ATARI" = "y" ]; then + dep_tristate ' Atari builtin port' CONFIG_PARPORT_ATARI $CONFIG_PARPORT + fi + dep_tristate ' Parallel printer support' CONFIG_PRINTER $CONFIG_PARPORT + if [ "$CONFIG_PRINTER" != "n" ]; then + bool ' Support IEEE1284 status readback' CONFIG_PRINTER_READBACK + fi fi endmenu +mainmenu_option next_comment +comment 'Loadable module support' +bool 'Enable loadable module support' CONFIG_MODULES +if [ "$CONFIG_MODULES" = "y" ]; then + bool ' Set version information on all symbols for modules' CONFIG_MODVERSIONS + bool ' Kernel module loader' CONFIG_KMOD +fi +endmenu + source drivers/block/Config.in if [ "$CONFIG_NET" = "y" ]; then - source net/Config.in + source net/Config.in fi mainmenu_option next_comment @@ -144,154 +144,154 @@ if [ "$CONFIG_SCSI" != "n" ]; then -comment 'SCSI support type (disk, tape, CD-ROM)' - -dep_tristate 'SCSI disk support' CONFIG_BLK_DEV_SD $CONFIG_SCSI -dep_tristate 'SCSI tape support' CONFIG_CHR_DEV_ST $CONFIG_SCSI -dep_tristate 'SCSI CD-ROM support' CONFIG_BLK_DEV_SR $CONFIG_SCSI -if [ "$CONFIG_BLK_DEV_SR" != "n" ]; then - bool ' Enable vendor-specific extensions (for SCSI CDROM)' CONFIG_BLK_DEV_SR_VENDOR -fi -dep_tristate 'SCSI generic support' CONFIG_CHR_DEV_SG $CONFIG_SCSI - -comment 'Some SCSI devices (e.g. CD jukebox) support multiple LUNs' - -bool 'Probe all LUNs on each SCSI device' CONFIG_SCSI_MULTI_LUN - -bool 'Verbose SCSI error reporting (kernel size +=12K)' CONFIG_SCSI_CONSTANTS -bool 'SCSI logging facility' CONFIG_SCSI_LOGGING + comment 'SCSI support type (disk, tape, CD-ROM)' -mainmenu_option next_comment -comment 'SCSI low-level drivers' - -if [ "$CONFIG_AMIGA" = "y" ]; then - dep_tristate 'A3000 WD33C93A support' CONFIG_A3000_SCSI $CONFIG_SCSI - if [ "$CONFIG_EXPERIMENTAL" = "y" ]; then - bool 'A4000T SCSI support' CONFIG_A4000T_SCSI - fi -fi -if [ "$CONFIG_ZORRO" = "y" ]; then - dep_tristate 'A2091 WD33C93A support' CONFIG_A2091_SCSI $CONFIG_SCSI - dep_tristate 'GVP Series II WD33C93A support' CONFIG_GVP11_SCSI $CONFIG_SCSI - dep_tristate 'CyberStorm SCSI support' CONFIG_CYBERSTORM_SCSI $CONFIG_SCSI - dep_tristate 'CyberStorm Mk II SCSI support' CONFIG_CYBERSTORMII_SCSI $CONFIG_SCSI - dep_tristate 'Blizzard 2060 SCSI support' CONFIG_BLZ2060_SCSI $CONFIG_SCSI - dep_tristate 'Blizzard 1230IV/1260 SCSI support' CONFIG_BLZ1230_SCSI $CONFIG_SCSI - dep_tristate 'Fastlane SCSI support' CONFIG_FASTLANE_SCSI $CONFIG_SCSI - if [ "$CONFIG_EXPERIMENTAL" = "y" ]; then - bool 'A4091 SCSI support' CONFIG_A4091_SCSI - bool 'WarpEngine SCSI support' CONFIG_WARPENGINE_SCSI - bool 'Blizzard PowerUP 603e+ SCSI' CONFIG_BLZ603EPLUS_SCSI - dep_tristate 'BSC Oktagon SCSI support' CONFIG_OKTAGON_SCSI $CONFIG_SCSI - bool 'Cyberstorm Mk III SCSI support' CONFIG_CYBERSTORMIII_SCSI -# bool 'GVP Turbo 040/060 SCSI support' CONFIG_GVP_TURBO_SCSI - fi -fi -if [ "$CONFIG_ATARI" = "y" ]; then - dep_tristate 'Atari native SCSI support' CONFIG_ATARI_SCSI $CONFIG_SCSI - if [ "$CONFIG_ATARI_SCSI" != "n" ]; then - bool ' Long delays for Toshiba CD-ROMs' CONFIG_ATARI_SCSI_TOSHIBA_DELAY - bool ' Reset SCSI-devices at boottime' CONFIG_ATARI_SCSI_RESET_BOOT - if [ "$CONFIG_EXPERIMENTAL" = "y" -a "$CONFIG_HADES" = "y" ]; then - bool ' Hades SCSI DMA emulator (EXPERIMENTAL)' CONFIG_TT_DMA_EMUL - fi - fi -fi -if [ "$CONFIG_MAC" = "y" ]; then - bool 'Macintosh NCR5380 SCSI' CONFIG_MAC_SCSI - dep_tristate 'Macintosh NCR53c9[46] SCSI' CONFIG_SCSI_MAC_ESP $CONFIG_SCSI -fi -#dep_tristate 'SCSI debugging host adapter' CONFIG_SCSI_DEBUG $CONFIG_SCSI - -if [ "$CONFIG_VME" = "y" -a "$CONFIG_MVME147" = "y" ]; then - bool 'WD33C93 SCSI driver for MVME147' CONFIG_MVME147_SCSI -fi - -if [ "$CONFIG_VME" = "y" -a "$CONFIG_MVME16x" = "y" ]; then - bool 'NCR53C710 SCSI driver for MVME16x' CONFIG_MVME16x_SCSI -fi + dep_tristate ' SCSI disk support' CONFIG_BLK_DEV_SD $CONFIG_SCSI + dep_tristate ' SCSI tape support' CONFIG_CHR_DEV_ST $CONFIG_SCSI + dep_tristate ' SCSI CD-ROM support' CONFIG_BLK_DEV_SR $CONFIG_SCSI + if [ "$CONFIG_BLK_DEV_SR" != "n" ]; then + bool ' Enable vendor-specific extensions (for SCSI CDROM)' CONFIG_BLK_DEV_SR_VENDOR + fi + dep_tristate ' SCSI generic support' CONFIG_CHR_DEV_SG $CONFIG_SCSI + + comment 'Some SCSI devices (e.g. CD jukebox) support multiple LUNs' + + bool ' Probe all LUNs on each SCSI device' CONFIG_SCSI_MULTI_LUN + + bool ' Verbose SCSI error reporting (kernel size +=12K)' CONFIG_SCSI_CONSTANTS + bool ' SCSI logging facility' CONFIG_SCSI_LOGGING + + mainmenu_option next_comment + comment 'SCSI low-level drivers' + + if [ "$CONFIG_AMIGA" = "y" ]; then + dep_tristate 'A3000 WD33C93A support' CONFIG_A3000_SCSI $CONFIG_SCSI + if [ "$CONFIG_EXPERIMENTAL" = "y" ]; then + bool 'A4000T SCSI support (EXPERIMENTAL)' CONFIG_A4000T_SCSI + fi + fi + if [ "$CONFIG_ZORRO" = "y" ]; then + dep_tristate 'A2091 WD33C93A support' CONFIG_A2091_SCSI $CONFIG_SCSI + dep_tristate 'GVP Series II WD33C93A support' CONFIG_GVP11_SCSI $CONFIG_SCSI + dep_tristate 'CyberStorm SCSI support' CONFIG_CYBERSTORM_SCSI $CONFIG_SCSI + dep_tristate 'CyberStorm Mk II SCSI support' CONFIG_CYBERSTORMII_SCSI $CONFIG_SCSI + dep_tristate 'Blizzard 2060 SCSI support' CONFIG_BLZ2060_SCSI $CONFIG_SCSI + dep_tristate 'Blizzard 1230IV/1260 SCSI support' CONFIG_BLZ1230_SCSI $CONFIG_SCSI + dep_tristate 'Fastlane SCSI support' CONFIG_FASTLANE_SCSI $CONFIG_SCSI + if [ "$CONFIG_EXPERIMENTAL" = "y" ]; then + bool 'A4091 SCSI support (EXPERIMENTAL)' CONFIG_A4091_SCSI + bool 'WarpEngine SCSI support (EXPERIMENTAL)' CONFIG_WARPENGINE_SCSI + bool 'Blizzard PowerUP 603e+ SCSI (EXPERIMENTAL)' CONFIG_BLZ603EPLUS_SCSI + dep_tristate 'BSC Oktagon SCSI support (EXPERIMENTAL)' CONFIG_OKTAGON_SCSI $CONFIG_SCSI + bool 'Cyberstorm Mk III SCSI support (EXPERIMENTAL)' CONFIG_CYBERSTORMIII_SCSI +# bool 'GVP Turbo 040/060 SCSI support (EXPERIMENTAL)' CONFIG_GVP_TURBO_SCSI + fi + fi + if [ "$CONFIG_ATARI" = "y" ]; then + dep_tristate 'Atari native SCSI support' CONFIG_ATARI_SCSI $CONFIG_SCSI + if [ "$CONFIG_ATARI_SCSI" != "n" ]; then + bool ' Long delays for Toshiba CD-ROMs' CONFIG_ATARI_SCSI_TOSHIBA_DELAY + bool ' Reset SCSI-devices at boottime' CONFIG_ATARI_SCSI_RESET_BOOT + if [ "$CONFIG_EXPERIMENTAL" = "y" -a "$CONFIG_HADES" = "y" ]; then + bool ' Hades SCSI DMA emulator (EXPERIMENTAL)' CONFIG_TT_DMA_EMUL + fi + fi + fi + if [ "$CONFIG_MAC" = "y" ]; then + bool 'Macintosh NCR5380 SCSI' CONFIG_MAC_SCSI + dep_tristate 'Macintosh NCR53c9[46] SCSI' CONFIG_SCSI_MAC_ESP $CONFIG_SCSI + fi +# dep_tristate 'SCSI debugging host adapter' CONFIG_SCSI_DEBUG $CONFIG_SCSI + + if [ "$CONFIG_VME" = "y" -a "$CONFIG_MVME147" = "y" ]; then + bool 'WD33C93 SCSI driver for MVME147' CONFIG_MVME147_SCSI + fi + + if [ "$CONFIG_VME" = "y" -a "$CONFIG_MVME16x" = "y" ]; then + bool 'NCR53C710 SCSI driver for MVME16x' CONFIG_MVME16x_SCSI + fi + + if [ "$CONFIG_VME" = "y" -a "$CONFIG_BVME6000" = "y" ]; then + bool 'NCR53C710 SCSI driver for BVME6000' CONFIG_BVME6000_SCSI + fi + + if [ "$CONFIG_SUN3X" = "y" ]; then + bool 'ESP SCSI driver' CONFIG_SUN3X_ESP + fi -if [ "$CONFIG_VME" = "y" -a "$CONFIG_BVME6000" = "y" ]; then - bool 'NCR53C710 SCSI driver for BVME6000' CONFIG_BVME6000_SCSI -fi - -if [ "$CONFIG_SUN3X" = "y" ]; then - bool 'ESP SCSI driver' CONFIG_SUN3X_ESP -fi - -endmenu + endmenu fi endmenu if [ "$CONFIG_NET" = "y" ]; then -mainmenu_option next_comment -comment 'Network device support' + mainmenu_option next_comment + comment 'Network device support' -bool 'Network device support' CONFIG_NETDEVICES -if [ "$CONFIG_NETDEVICES" = "y" ]; then -# -# Network device configuration -# -tristate 'Dummy net driver support' CONFIG_DUMMY -tristate 'SLIP (serial line) support' CONFIG_SLIP -if [ "$CONFIG_SLIP" != "n" ]; then - bool ' CSLIP compressed headers' CONFIG_SLIP_COMPRESSED - bool ' Keepalive and linefill' CONFIG_SLIP_SMART - bool ' Six bit SLIP encapsulation' CONFIG_SLIP_MODE_SLIP6 -fi -tristate 'PPP (point-to-point) support' CONFIG_PPP -if [ ! "$CONFIG_PPP" = "n" ]; then - comment 'CCP compressors for PPP are only built as modules.' -fi -tristate 'EQL (serial line load balancing) support' CONFIG_EQUALIZER -if [ "$CONFIG_ZORRO" = "y" ]; then - tristate 'Ariadne support' CONFIG_ARIADNE - tristate 'Ariadne II support' CONFIG_ARIADNE2 - tristate 'A2065 support' CONFIG_A2065 - tristate 'Hydra support' CONFIG_HYDRA -fi -if [ "$CONFIG_AMIGA_PCMCIA" = "y" ]; then - tristate 'PCMCIA NE2000 support' CONFIG_APNE -fi -if [ "$CONFIG_APOLLO" = "y" ] ; then - tristate 'Apollo 3c505 support' CONFIG_APOLLO_ELPLUS -fi -if [ "$CONFIG_MAC" = "y" ]; then - bool 'Mac NS 8390 based ethernet cards' CONFIG_DAYNAPORT -# bool 'Macintosh (AV) onboard MACE ethernet' CONFIG_MACMACE - bool 'Macintosh (Quadra) onboard SONIC ethernet' CONFIG_MACSONIC -fi -if [ "$CONFIG_VME" = "y" -a "$CONFIG_MVME147" = "y" ]; then - tristate 'MVME147 (Lance) Ethernet support' CONFIG_MVME147_NET -fi -if [ "$CONFIG_VME" = "y" -a "$CONFIG_MVME16x" = "y" ]; then - tristate 'MVME16x Ethernet support' CONFIG_MVME16x_NET -fi -if [ "$CONFIG_VME" = "y" -a "$CONFIG_BVME6000" = "y" ]; then - tristate 'BVME6000 Ethernet support' CONFIG_BVME6000_NET -fi -if [ "$CONFIG_ATARI" = "y" ]; then - tristate 'Atari Lance support' CONFIG_ATARILANCE - if [ "$CONFIG_ATARI_ACSI" != "n" ]; then - tristate 'BioNet-100 support' CONFIG_ATARI_BIONET - tristate 'PAMsNet support' CONFIG_ATARI_PAMSNET - fi -fi -if [ "$CONFIG_SUN3X" = "y" ]; then - bool 'Sun3x Lance support' CONFIG_SUNLANCE -fi -if [ "$CONFIG_HP300" = "y" ]; then - bool 'HP on-board LANCE support' CONFIG_HPLANCE -fi -if [ "$CONFIG_Q40" = "y" ]; then - if [ ! "$CONFIG_PARPORT" = "n" ]; then - dep_tristate 'PLIP (parallel port) support' CONFIG_PLIP $CONFIG_PARPORT - fi -fi -fi -endmenu + bool 'Network device support' CONFIG_NETDEVICES + if [ "$CONFIG_NETDEVICES" = "y" ]; then + # + # Network device configuration + # + tristate ' Dummy net driver support' CONFIG_DUMMY + tristate ' SLIP (serial line) support' CONFIG_SLIP + if [ "$CONFIG_SLIP" != "n" ]; then + bool ' CSLIP compressed headers' CONFIG_SLIP_COMPRESSED + bool ' Keepalive and linefill' CONFIG_SLIP_SMART + bool ' Six bit SLIP encapsulation' CONFIG_SLIP_MODE_SLIP6 + fi + tristate ' PPP (point-to-point) support' CONFIG_PPP + if [ ! "$CONFIG_PPP" = "n" ]; then + comment 'CCP compressors for PPP are only built as modules.' + fi + tristate ' EQL (serial line load balancing) support' CONFIG_EQUALIZER + if [ "$CONFIG_ZORRO" = "y" ]; then + tristate ' Ariadne support' CONFIG_ARIADNE + tristate ' Ariadne II support' CONFIG_ARIADNE2 + tristate ' A2065 support' CONFIG_A2065 + tristate ' Hydra support' CONFIG_HYDRA + fi + if [ "$CONFIG_AMIGA_PCMCIA" = "y" ]; then + tristate ' PCMCIA NE2000 support' CONFIG_APNE + fi + if [ "$CONFIG_APOLLO" = "y" ]; then + tristate ' Apollo 3c505 support' CONFIG_APOLLO_ELPLUS + fi + if [ "$CONFIG_MAC" = "y" ]; then + bool ' Mac NS 8390 based ethernet cards' CONFIG_DAYNAPORT +# bool ' Macintosh (AV) onboard MACE ethernet' CONFIG_MACMACE + bool ' Macintosh (Quadra) onboard SONIC ethernet' CONFIG_MACSONIC + fi + if [ "$CONFIG_VME" = "y" -a "$CONFIG_MVME147" = "y" ]; then + tristate ' MVME147 (Lance) Ethernet support' CONFIG_MVME147_NET + fi + if [ "$CONFIG_VME" = "y" -a "$CONFIG_MVME16x" = "y" ]; then + tristate ' MVME16x Ethernet support' CONFIG_MVME16x_NET + fi + if [ "$CONFIG_VME" = "y" -a "$CONFIG_BVME6000" = "y" ]; then + tristate ' BVME6000 Ethernet support' CONFIG_BVME6000_NET + fi + if [ "$CONFIG_ATARI" = "y" ]; then + tristate ' Atari Lance support' CONFIG_ATARILANCE + if [ "$CONFIG_ATARI_ACSI" != "n" ]; then + tristate ' BioNet-100 support' CONFIG_ATARI_BIONET + tristate ' PAMsNet support' CONFIG_ATARI_PAMSNET + fi + fi + if [ "$CONFIG_SUN3X" = "y" ]; then + bool ' Sun3x Lance support' CONFIG_SUNLANCE + fi + if [ "$CONFIG_HP300" = "y" ]; then + bool ' HP on-board LANCE support' CONFIG_HPLANCE + fi + if [ "$CONFIG_Q40" = "y" ]; then + if [ ! "$CONFIG_PARPORT" = "n" ]; then + dep_tristate ' PLIP (parallel port) support' CONFIG_PLIP $CONFIG_PARPORT + fi + fi + fi + endmenu fi @@ -303,85 +303,85 @@ fi if [ "$CONFIG_SERIAL" = "y" ]; then - bool ' Support for console on serial port' CONFIG_SERIAL_CONSOLE - bool 'Extended dumb serial driver options' CONFIG_SERIAL_EXTENDED + bool ' Support for console on serial port' CONFIG_SERIAL_CONSOLE + bool ' Extended dumb serial driver options' CONFIG_SERIAL_EXTENDED fi if [ "$CONFIG_SERIAL_EXTENDED" = "y" ]; then - bool ' Support more than 4 serial ports' CONFIG_SERIAL_MANY_PORTS - bool ' Support for sharing serial interrupts' CONFIG_SERIAL_SHARE_IRQ -# bool ' Autodetect IRQ - do not yet enable !!' CONFIG_SERIAL_DETECT_IRQ - bool ' Support special multiport boards' CONFIG_SERIAL_MULTIPORT - bool ' Support the Bell Technologies HUB6 card' CONFIG_HUB6 + bool ' Support more than 4 serial ports' CONFIG_SERIAL_MANY_PORTS + bool ' Support for sharing serial interrupts' CONFIG_SERIAL_SHARE_IRQ +# bool ' Autodetect IRQ - do not yet enable !!' CONFIG_SERIAL_DETECT_IRQ + bool ' Support special multiport boards' CONFIG_SERIAL_MULTIPORT + bool ' Support the Bell Technologies HUB6 card' CONFIG_HUB6 fi if [ "$CONFIG_VME" = "n" ]; then - define_bool CONFIG_VT y - if [ "$CONFIG_VT" = "y" ]; then - bool 'Support for console on virtual terminal' CONFIG_VT_CONSOLE - fi + define_bool CONFIG_VT y + if [ "$CONFIG_VT" = "y" ]; then + bool 'Support for console on virtual terminal' CONFIG_VT_CONSOLE + fi fi if [ "$CONFIG_ATARI" = "y" ]; then - define_bool CONFIG_NVRAM y + define_bool CONFIG_NVRAM y fi if [ "$CONFIG_AMIGA" = "y" ]; then - tristate 'Amiga mouse support' CONFIG_AMIGAMOUSE - if [ "$CONFIG_AMIGAMOUSE" != "n" ]; then - define_bool CONFIG_BUSMOUSE y - fi + tristate 'Amiga mouse support' CONFIG_AMIGAMOUSE + if [ "$CONFIG_AMIGAMOUSE" != "n" ]; then + define_bool CONFIG_BUSMOUSE y + fi fi if [ "$CONFIG_ATARI" = "y" ]; then - tristate 'Atari mouse support' CONFIG_ATARIMOUSE - if [ "$CONFIG_ATARIMOUSE" != "n" ]; then - define_bool CONFIG_BUSMOUSE y - fi + tristate 'Atari mouse support' CONFIG_ATARIMOUSE + if [ "$CONFIG_ATARIMOUSE" != "n" ]; then + define_bool CONFIG_BUSMOUSE y + fi fi if [ "$CONFIG_MAC" = "y" ]; then bool 'Mac ADB mouse support' CONFIG_ADBMOUSE - if [ "$CONFIG_ADBMOUSE" != "n" ]; then - define_bool CONFIG_BUSMOUSE y - fi + if [ "$CONFIG_ADBMOUSE" != "n" ]; then + define_bool CONFIG_BUSMOUSE y + fi fi if [ "$CONFIG_ATARI" = "y" ]; then - tristate 'Atari MFP serial support' CONFIG_ATARI_MFPSER - tristate 'Atari SCC serial support' CONFIG_ATARI_SCC - if [ "$CONFIG_ATARI_SCC" = "y" -o "$CONFIG_ATARI_SCC" = "m" ]; then - bool 'Atari SCC serial DMA support' CONFIG_ATARI_SCC_DMA - fi - tristate 'Atari MIDI serial support' CONFIG_ATARI_MIDI - if [ "$CONFIG_EXPERIMENTAL" = "y" ]; then - tristate 'Atari DSP56k support (EXPERIMENTAL)' CONFIG_ATARI_DSP56K - fi + tristate 'Atari MFP serial support' CONFIG_ATARI_MFPSER + tristate 'Atari SCC serial support' CONFIG_ATARI_SCC + if [ "$CONFIG_ATARI_SCC" = "y" -o "$CONFIG_ATARI_SCC" = "m" ]; then + bool ' Atari SCC serial DMA support' CONFIG_ATARI_SCC_DMA + fi + tristate 'Atari MIDI serial support' CONFIG_ATARI_MIDI + if [ "$CONFIG_EXPERIMENTAL" = "y" ]; then + tristate 'Atari DSP56k support (EXPERIMENTAL)' CONFIG_ATARI_DSP56K + fi fi if [ "$CONFIG_AMIGA" = "y" ]; then - tristate 'Amiga builtin serial support' CONFIG_AMIGA_BUILTIN_SERIAL - if [ "$CONFIG_AMIGA_PCMCIA" = "y" ]; then - tristate 'Hisoft Whippet PCMCIA serial support' CONFIG_WHIPPET_SERIAL - fi + tristate 'Amiga builtin serial support' CONFIG_AMIGA_BUILTIN_SERIAL + if [ "$CONFIG_AMIGA_PCMCIA" = "y" ]; then + tristate 'Hisoft Whippet PCMCIA serial support' CONFIG_WHIPPET_SERIAL + fi fi if [ "$CONFIG_PARPORT" = "n" ]; then - if [ "$CONFIG_ZORRO" = "y" ]; then - tristate 'GVP IO-Extender support' CONFIG_GVPIOEXT - dep_tristate 'GVP IO-Extender parallel printer support' CONFIG_GVPIOEXT_LP $CONFIG_GVPIOEXT - dep_tristate 'GVP IO-Extender PLIP support' CONFIG_GVPIOEXT_PLIP $CONFIG_GVPIOEXT - tristate 'Multiface Card III serial support' CONFIG_MULTIFACE_III_TTY - fi + if [ "$CONFIG_ZORRO" = "y" ]; then + tristate 'GVP IO-Extender support' CONFIG_GVPIOEXT + dep_tristate ' GVP IO-Extender parallel printer support' CONFIG_GVPIOEXT_LP $CONFIG_GVPIOEXT + dep_tristate ' GVP IO-Extender PLIP support' CONFIG_GVPIOEXT_PLIP $CONFIG_GVPIOEXT + tristate 'Multiface Card III serial support' CONFIG_MULTIFACE_III_TTY + fi fi if [ "$CONFIG_MAC" = "y" ]; then - bool 'Mac SCC serial support' CONFIG_MAC_SCC + bool 'Mac SCC serial support' CONFIG_MAC_SCC fi if [ "$CONFIG_HP300" = "y" -a "$CONFIG_DIO" = "y" ]; then - tristate 'HP DCA serial support' CONFIG_HPDCA + tristate 'HP DCA serial support' CONFIG_HPDCA fi if [ "$CONFIG_SUN3X" = "y" ]; then - bool 'Sun3x builtin serial support' CONFIG_SUN3X_ZS - if [ "$CONFIG_SUN3X_ZS" = "y" ]; then - bool 'Sun keyboard support' CONFIG_SUN_KEYBOARD - bool 'Sun mouse support' CONFIG_SUN_MOUSE - if [ "$CONFIG_SUN_MOUSE" != "n" ]; then - define_bool CONFIG_BUSMOUSE y + bool 'Sun3x builtin serial support' CONFIG_SUN3X_ZS + if [ "$CONFIG_SUN3X_ZS" = "y" ]; then + bool ' Sun keyboard support' CONFIG_SUN_KEYBOARD + bool ' Sun mouse support' CONFIG_SUN_MOUSE + if [ "$CONFIG_SUN_MOUSE" != "n" ]; then + define_bool CONFIG_BUSMOUSE y fi define_bool CONFIG_SBUS y define_bool CONFIG_SBUSCHAR y @@ -391,43 +391,43 @@ if [ "$CONFIG_AMIGA" = "y" -o "$CONFIG_ATARI" = "y" -o \ "$CONFIG_MAC" = "y" -o "$CONFIG_HP300" = "y" -o \ "$CONFIG_SUN3X" = "y" ]; then - if [ "$CONFIG_ATARI_MFPSER" = "y" -o "$CONFIG_ATARI_SCC" = "y" -o \ - "$CONFIG_ATARI_MIDI" = "y" -o "$CONFIG_MAC_SCC" = "y" -o \ - "$CONFIG_AMIGA_BUILTIN_SERIAL" = "y" -o \ - "$CONFIG_GVPIOEXT" = "y" -o "$CONFIG_MULTIFACE_III_TTY" = "y" -o \ - "$CONFIG_HPDCA" = "y" -o "$CONFIG_SUN3X_ZS" = "y" ]; then - bool 'Support for serial port console' CONFIG_SERIAL_CONSOLE - fi + if [ "$CONFIG_ATARI_MFPSER" = "y" -o "$CONFIG_ATARI_SCC" = "y" -o \ + "$CONFIG_ATARI_MIDI" = "y" -o "$CONFIG_MAC_SCC" = "y" -o \ + "$CONFIG_AMIGA_BUILTIN_SERIAL" = "y" -o \ + "$CONFIG_GVPIOEXT" = "y" -o "$CONFIG_MULTIFACE_III_TTY" = "y" -o \ + "$CONFIG_HPDCA" = "y" -o "$CONFIG_SUN3X_ZS" = "y" ]; then + bool 'Support for serial port console' CONFIG_SERIAL_CONSOLE + fi fi if [ "$CONFIG_VME" = "y" ]; then - define_bool CONFIG_SERIAL_CONSOLE y - if [ "$CONFIG_MVME147" = "y" ]; then - bool 'SCC support for MVME147 serial ports' CONFIG_MVME147_SCC - fi - if [ "$CONFIG_MVME16x" = "y" ]; then - bool 'CD2401 support for MVME166/7 serial ports' CONFIG_SERIAL167 - bool 'SCC support for MVME162 serial ports' CONFIG_MVME162_SCC - fi - if [ "$CONFIG_BVME6000" = "y" ]; then - bool 'SCC support for BVME6000 serial ports' CONFIG_BVME6000_SCC - fi + define_bool CONFIG_SERIAL_CONSOLE y + if [ "$CONFIG_MVME147" = "y" ]; then + bool 'SCC support for MVME147 serial ports' CONFIG_MVME147_SCC + fi + if [ "$CONFIG_MVME16x" = "y" ]; then + bool 'CD2401 support for MVME166/7 serial ports' CONFIG_SERIAL167 + bool 'SCC support for MVME162 serial ports' CONFIG_MVME162_SCC + fi + if [ "$CONFIG_BVME6000" = "y" ]; then + bool 'SCC support for BVME6000 serial ports' CONFIG_BVME6000_SCC + fi fi if [ "$CONFIG_APOLLO" = "y" ]; then - bool 'Support for DN serial port (dummy)' CONFIG_SERIAL - bool 'Support for serial port console' CONFIG_SERIAL_CONSOLE + bool 'Support for DN serial port (dummy)' CONFIG_SERIAL + bool 'Support for serial port console' CONFIG_SERIAL_CONSOLE fi bool 'Support for user serial device modules' CONFIG_USERIAL bool 'Watchdog Timer Support' CONFIG_WATCHDOG if [ "$CONFIG_WATCHDOG" != "n" ]; then - bool ' Disable watchdog shutdown on close' CONFIG_WATCHDOG_NOWAYOUT - bool ' Software Watchdog' CONFIG_SOFT_WATCHDOG + bool ' Disable watchdog shutdown on close' CONFIG_WATCHDOG_NOWAYOUT + bool ' Software Watchdog' CONFIG_SOFT_WATCHDOG fi if [ "$CONFIG_ATARI" = "y" ]; then - bool 'Enhanced Real Time Clock Support' CONFIG_RTC + bool 'Enhanced Real Time Clock Support' CONFIG_RTC fi bool 'Unix98 PTY support' CONFIG_UNIX98_PTYS if [ "$CONFIG_UNIX98_PTYS" = "y" ]; then - int 'Maximum number of Unix98 PTYs in use (0-2048)' CONFIG_UNIX98_PTY_COUNT 256 + int ' Maximum number of Unix98 PTYs in use (0-2048)' CONFIG_UNIX98_PTY_COUNT 256 fi endmenu @@ -437,22 +437,22 @@ tristate 'Sound support' CONFIG_SOUND if [ "$CONFIG_SOUND" != "n" ]; then - dep_tristate 'Amiga or Atari DMA sound support' CONFIG_DMASOUND $CONFIG_SOUND + dep_tristate ' Amiga or Atari DMA sound support' CONFIG_DMASOUND $CONFIG_SOUND fi endmenu source fs/Config.in if [ "$CONFIG_VME" = "n" ]; then - mainmenu_option next_comment - comment 'Console drivers' - if [ "$CONFIG_HP300" = "y" ]; then - bool 'Frame buffer support' CONFIG_FB - else - define_bool CONFIG_FB y - fi - source drivers/video/Config.in - endmenu + mainmenu_option next_comment + comment 'Console drivers' + if [ "$CONFIG_HP300" = "y" ]; then + bool 'Frame buffer support' CONFIG_FB + else + define_bool CONFIG_FB y + fi + source drivers/video/Config.in + endmenu fi mainmenu_option next_comment diff -u --recursive --new-file v2.3.19/linux/arch/mips/config.in linux/arch/mips/config.in --- v2.3.19/linux/arch/mips/config.in Thu Aug 26 13:05:34 1999 +++ linux/arch/mips/config.in Thu Oct 7 10:17:08 1999 @@ -13,9 +13,9 @@ comment 'Machine selection' bool 'Support for Acer PICA 1 chipset' CONFIG_ACER_PICA_61 if [ "$CONFIG_EXPERIMENTAL" = "y" ]; then - bool 'Support for Algorithmics P4032' CONFIG_ALGOR_P4032 - bool 'Support for BAGET MIPS series' CONFIG_BAGET_MIPS - bool 'Support for DECstations' CONFIG_DECSTATION + bool 'Support for Algorithmics P4032 (EXPERIMENTAL)' CONFIG_ALGOR_P4032 + bool 'Support for BAGET MIPS series (EXPERIMENTAL)' CONFIG_BAGET_MIPS + bool 'Support for DECstations (EXPERIMENTAL)' CONFIG_DECSTATION fi bool 'Support for Mips Magnum 4000' CONFIG_MIPS_MAGNUM_4000 bool 'Support for Olivetti M700-10' CONFIG_OLIVETTI_M700 @@ -30,19 +30,19 @@ unset CONFIG_VIDEO_G364 if [ "$CONFIG_ALGOR_P4032" = "y" ]; then - define_bool CONFIG_PCI y + define_bool CONFIG_PCI y fi if [ "$CONFIG_MIPS_MAGNUM_4000" = "y" -o \ "$CONFIG_OLIVETTI_M700" = "y" ]; then - define_bool CONFIG_MIPS_JAZZ y - define_bool CONFIG_FB y - define_bool CONFIG_FB_G364 y + define_bool CONFIG_MIPS_JAZZ y + define_bool CONFIG_FB y + define_bool CONFIG_FB_G364 y fi if [ "$CONFIG_ACER_PICA_61" = "y" ]; then - define_bool CONFIG_MIPS_JAZZ y + define_bool CONFIG_MIPS_JAZZ y fi if [ "$CONFIG_SNI_RM200_PCI" = "y" ]; then - define_bool CONFIG_PCI y + define_bool CONFIG_PCI y fi endmenu @@ -64,16 +64,16 @@ comment 'General setup' if [ "$CONFIG_DECSTATION" = "y" ]; then - define_bool CONFIG_CPU_LITTLE_ENDIAN y + define_bool CONFIG_CPU_LITTLE_ENDIAN y else - bool 'Generate little endian code' CONFIG_CPU_LITTLE_ENDIAN + bool 'Generate little endian code' CONFIG_CPU_LITTLE_ENDIAN fi define_bool CONFIG_ELF_KERNEL y if [ "$CONFIG_CPU_LITTLE_ENDIAN" = "n" ]; then - define_bool CONFIG_BINFMT_IRIX y - define_bool CONFIG_FORWARD_KEYBOARD y + define_bool CONFIG_BINFMT_IRIX y + define_bool CONFIG_FORWARD_KEYBOARD y fi define_bool CONFIG_BINFMT_AOUT n define_bool CONFIG_BINFMT_ELF y @@ -85,7 +85,7 @@ bool 'Sysctl support' CONFIG_SYSCTL if [ "$CONFIG_SGI" != "y" -a "$CONFIG_DECSTATION" != "y" -a "$CONFIG_BAGET_MIPS" != "y" ]; then -source drivers/parport/Config.in + source drivers/parport/Config.in fi endmenu @@ -93,24 +93,20 @@ comment 'Loadable module support' bool 'Enable loadable module support' CONFIG_MODULES if [ "$CONFIG_MODULES" = "y" ]; then - bool 'Set version information on all symbols for modules' CONFIG_MODVERSIONS - bool 'Kernel module loader' CONFIG_KMOD -fi - -if [ "$CONFIG_EXPERIMENTAL" = "y" ]; then - bool 'Support for frame buffer devices (EXPERIMENTAL)' CONFIG_FB + bool ' Set version information on all symbols for modules' CONFIG_MODVERSIONS + bool ' Kernel module loader' CONFIG_KMOD fi endmenu if [ "$CONFIG_DECSTATION" = "y" ]; then - mainmenu_option next_comment - comment 'TURBOchannel support' - bool 'TURBOchannel support' CONFIG_TC -# if [ "$CONFIG_TC" = "y" ]; then -# tristate 'MAGMA Parallel port support' CONFIG_PARPORT -# fi - endmenu + mainmenu_option next_comment + comment 'TURBOchannel support' + bool 'TURBOchannel support' CONFIG_TC +# if [ "$CONFIG_TC" = "y" ]; then +# tristate ' MAGMA Parallel port support' CONFIG_PARPORT +# fi + endmenu fi source drivers/i2o/Config.in @@ -120,7 +116,7 @@ source drivers/block/Config.in if [ "$CONFIG_NET" = "y" ]; then - source net/Config.in + source net/Config.in fi mainmenu_option next_comment @@ -129,125 +125,125 @@ tristate 'SCSI support' CONFIG_SCSI if [ "$CONFIG_SCSI" != "n" ]; then - if [ "$CONFIG_SGI" = "y" -o "$CONFIG_DECSTATION" = "y" ]; then - comment 'SCSI support type (disk, tape, CDrom)' + if [ "$CONFIG_SGI" = "y" -o "$CONFIG_DECSTATION" = "y" ]; then + comment ' SCSI support type (disk, tape, CDrom)' - dep_tristate 'SCSI disk support' CONFIG_BLK_DEV_SD $CONFIG_SCSI - dep_tristate 'SCSI tape support' CONFIG_CHR_DEV_ST $CONFIG_SCSI - dep_tristate 'SCSI CDROM support' CONFIG_BLK_DEV_SR $CONFIG_SCSI - dep_tristate 'SCSI generic support' CONFIG_CHR_DEV_SG $CONFIG_SCSI - - comment 'Some SCSI devices (e.g. CD jukebox) support multiple LUNs' - - bool 'Probe all LUNs on each SCSI device' CONFIG_SCSI_MULTI_LUN - - bool 'Verbose SCSI error reporting' CONFIG_SCSI_CONSTANTS - - #mainmenu_option next_comment - comment 'SCSI low-level drivers' - if [ "$CONFIG_SGI" = "y" ]; then - dep_tristate 'SGI wd93 Scsi Driver' CONFIG_SCSI_SGIWD93 $CONFIG_SCSI - else - if [ "$CONFIG_TC" = "y" ]; then - dep_tristate 'DEC NCR53C94 Scsi Driver' CONFIG_SCSI_DECNCR $CONFIG_SCSI - fi - dep_tristate 'DEC SII Scsi Driver' CONFIG_SCSI_DECSII $CONFIG_SCSI - fi - else - source drivers/scsi/Config.in - fi + dep_tristate ' SCSI disk support' CONFIG_BLK_DEV_SD $CONFIG_SCSI + dep_tristate ' SCSI tape support' CONFIG_CHR_DEV_ST $CONFIG_SCSI + dep_tristate ' SCSI CDROM support' CONFIG_BLK_DEV_SR $CONFIG_SCSI + dep_tristate ' SCSI generic support' CONFIG_CHR_DEV_SG $CONFIG_SCSI + + comment 'Some SCSI devices (e.g. CD jukebox) support multiple LUNs' + + bool ' Probe all LUNs on each SCSI device' CONFIG_SCSI_MULTI_LUN + + bool ' Verbose SCSI error reporting' CONFIG_SCSI_CONSTANTS + + #mainmenu_option next_comment + comment 'SCSI low-level drivers' + if [ "$CONFIG_SGI" = "y" ]; then + dep_tristate 'SGI wd93 Scsi Driver' CONFIG_SCSI_SGIWD93 $CONFIG_SCSI + else + if [ "$CONFIG_TC" = "y" ]; then + dep_tristate 'DEC NCR53C94 Scsi Driver' CONFIG_SCSI_DECNCR $CONFIG_SCSI + fi + dep_tristate 'DEC SII Scsi Driver' CONFIG_SCSI_DECSII $CONFIG_SCSI + fi + else + source drivers/scsi/Config.in + fi fi endmenu if [ "$CONFIG_NET" = "y" ]; then - mainmenu_option next_comment - comment 'Network device support' + mainmenu_option next_comment + comment 'Network device support' - bool 'Network device support' CONFIG_NETDEVICES - if [ "$CONFIG_NETDEVICES" = "y" ]; then - if [ "$CONFIG_SGI" != "y" -a "$CONFIG_DECSTATION" != "y" -a "$CONFIG_BAGET_MIPS" != "y" ]; then - source drivers/net/Config.in - else - tristate 'Dummy net driver support' CONFIG_DUMMY - tristate 'SLIP (serial line) support' CONFIG_SLIP - if [ "$CONFIG_SLIP" != "n" ]; then - bool ' CSLIP compressed headers' CONFIG_SLIP_COMPRESSED - bool ' Keepalive and linefill' CONFIG_SLIP_SMART - fi - tristate 'PPP (point-to-point) support' CONFIG_PPP - if [ ! "$CONFIG_PPP" = "n" ]; then - comment 'CCP compressors for PPP are only built as modules.' - fi - if [ "$CONFIG_SGI" = "y" ]; then - bool 'SGI Seeq ethernet controller support' CONFIG_SGISEEQ - fi - if [ "$CONFIG_DECSTATION" = "y" ]; then - bool 'DEC LANCE ethernet controller support' CONFIG_DECLANCE - fi - if [ "$CONFIG_BAGET_MIPS" = "y" ]; then - tristate 'Baget AMD LANCE support' CONFIG_BAGETLANCE - tristate 'Baget Backplane Shared Memory support' CONFIG_BAGETBSM - fi - fi - fi - endmenu + bool 'Network device support' CONFIG_NETDEVICES + if [ "$CONFIG_NETDEVICES" = "y" ]; then + if [ "$CONFIG_SGI" != "y" -a "$CONFIG_DECSTATION" != "y" -a "$CONFIG_BAGET_MIPS" != "y" ]; then + source drivers/net/Config.in + else + tristate ' Dummy net driver support' CONFIG_DUMMY + tristate ' SLIP (serial line) support' CONFIG_SLIP + if [ "$CONFIG_SLIP" != "n" ]; then + bool ' CSLIP compressed headers' CONFIG_SLIP_COMPRESSED + bool ' Keepalive and linefill' CONFIG_SLIP_SMART + fi + tristate ' PPP (point-to-point) support' CONFIG_PPP + if [ ! "$CONFIG_PPP" = "n" ]; then + comment ' CCP compressors for PPP are only built as modules.' + fi + if [ "$CONFIG_SGI" = "y" ]; then + bool ' SGI Seeq ethernet controller support' CONFIG_SGISEEQ + fi + if [ "$CONFIG_DECSTATION" = "y" ]; then + bool ' DEC LANCE ethernet controller support' CONFIG_DECLANCE + fi + if [ "$CONFIG_BAGET_MIPS" = "y" ]; then + tristate ' Baget AMD LANCE support' CONFIG_BAGETLANCE + tristate ' Baget Backplane Shared Memory support' CONFIG_BAGETBSM + fi + fi + fi + endmenu fi if [ "$CONFIG_SGI" != "y" -a "$CONFIG_DECSTATION" != "y" -a "$CONFIG_BAGET_MIPS" != "y" ]; then - source drivers/net/hamradio/Config.in + source drivers/net/hamradio/Config.in - mainmenu_option next_comment - comment 'ISDN subsystem' + mainmenu_option next_comment + comment 'ISDN subsystem' - if [ "$CONFIG_NET" != "n" ]; then - tristate 'ISDN support' CONFIG_ISDN - if [ "$CONFIG_ISDN" != "n" ]; then - source drivers/isdn/Config.in - fi - fi - endmenu + if [ "$CONFIG_NET" != "n" ]; then + tristate 'ISDN support' CONFIG_ISDN + if [ "$CONFIG_ISDN" != "n" ]; then + source drivers/isdn/Config.in + fi + fi + endmenu - mainmenu_option next_comment - comment comment 'Old CD-ROM drivers (not SCSI, not IDE)' + mainmenu_option next_comment + comment comment 'Old CD-ROM drivers (not SCSI, not IDE)' - bool 'Support non-SCSI/IDE/ATAPI drives' CONFIG_CD_NO_IDESCSI - if [ "$CONFIG_CD_NO_IDESCSI" != "n" ]; then - source drivers/cdrom/Config.in - fi - endmenu + bool 'Support non-SCSI/IDE/ATAPI drives' CONFIG_CD_NO_IDESCSI + if [ "$CONFIG_CD_NO_IDESCSI" != "n" ]; then + source drivers/cdrom/Config.in + fi + endmenu fi if [ "$CONFIG_DECSTATION" != "y" ]; then - source drivers/char/Config.in + source drivers/char/Config.in else - mainmenu_option next_comment - comment 'DECstation Character devices' + mainmenu_option next_comment + comment 'DECstation Character devices' - bool 'Virtual terminal' CONFIG_VT - if [ "$CONFIG_VT" = "y" ]; then - bool 'Support for console on virtual terminal' CONFIG_VT_CONSOLE - fi - tristate 'Standard/generic (dumb) serial support' CONFIG_SERIAL - if [ "$CONFIG_SGI" = "y" ]; then - bool 'SGI PROM Console Support' CONFIG_SGI_PROM_CONSOLE - fi - if [ "$CONFIG_SERIAL" = "y" ]; then - bool 'DZ11 Serial Support' CONFIG_DZ - if [ "$CONFIG_TC" = "y" ]; then - bool 'Z85C30 Serial Support' CONFIG_ZS - fi - bool ' Support for console on serial port' CONFIG_SERIAL_CONSOLE - fi - bool 'Unix98 PTY support' CONFIG_UNIX98_PTYS - if [ "$CONFIG_UNIX98_PTYS" = "y" ]; then - int 'Maximum number of Unix98 PTYs in use (0-2048)' CONFIG_UNIX98_PTY_COUNT 256 - fi - bool 'Keyboard Support' CONFIG_KEYBOARD - bool 'Mouse Support' CONFIG_MOUSE -# bool 'Enhanced Real Time Clock Support' CONFIG_RTC - endmenu + bool 'Virtual terminal' CONFIG_VT + if [ "$CONFIG_VT" = "y" ]; then + bool ' Support for console on virtual terminal' CONFIG_VT_CONSOLE + fi + if [ "$CONFIG_SGI" = "y" ]; then + bool 'SGI PROM Console Support' CONFIG_SGI_PROM_CONSOLE + fi + tristate 'Standard/generic (dumb) serial support' CONFIG_SERIAL + if [ "$CONFIG_SERIAL" = "y" ]; then + bool ' DZ11 Serial Support' CONFIG_DZ + if [ "$CONFIG_TC" = "y" ]; then + bool ' Z85C30 Serial Support' CONFIG_ZS + fi + bool ' Support for console on serial port' CONFIG_SERIAL_CONSOLE + fi + bool 'Unix98 PTY support' CONFIG_UNIX98_PTYS + if [ "$CONFIG_UNIX98_PTYS" = "y" ]; then + int 'Maximum number of Unix98 PTYs in use (0-2048)' CONFIG_UNIX98_PTY_COUNT 256 + fi + bool 'Keyboard Support' CONFIG_KEYBOARD + bool 'Mouse Support' CONFIG_MOUSE +# bool 'Enhanced Real Time Clock Support' CONFIG_RTC + endmenu fi source drivers/usb/Config.in @@ -255,36 +251,36 @@ source fs/Config.in if [ "$CONFIG_VT" = "y" ]; then - mainmenu_option next_comment - comment 'Console drivers' - if [ "$CONFIG_SGI" = "y" ]; then - tristate 'SGI Newport Console support' CONFIG_SGI_NEWPORT_CONSOLE - if [ "$CONFIG_SGI_NEWPORT_CONSOLE" != "y" ]; then - define_bool CONFIG_DUMMY_CONSOLE y - fi - else - if [ "$CONFIG_DECSTATION" != "y" ]; then - bool 'VGA text console' CONFIG_VGA_CONSOLE - fi - bool 'Support for frame buffer devices' CONFIG_FB - source drivers/video/Config.in - fi - endmenu + mainmenu_option next_comment + comment 'Console drivers' + if [ "$CONFIG_SGI" = "y" ]; then + tristate 'SGI Newport Console support' CONFIG_SGI_NEWPORT_CONSOLE + if [ "$CONFIG_SGI_NEWPORT_CONSOLE" != "y" ]; then + define_bool CONFIG_DUMMY_CONSOLE y + fi + else + if [ "$CONFIG_DECSTATION" != "y" ]; then + bool 'VGA text console' CONFIG_VGA_CONSOLE + fi + bool 'Support for frame buffer devices' CONFIG_FB + source drivers/video/Config.in + fi + endmenu fi if [ "$CONFIG_DECSTATION" != "y" ]; then - mainmenu_option next_comment - comment 'Sound' + mainmenu_option next_comment + comment 'Sound' - tristate 'Sound card support' CONFIG_SOUND - if [ "$CONFIG_SOUND" != "n" ]; then - source drivers/sound/Config.in - fi - endmenu + tristate 'Sound card support' CONFIG_SOUND + if [ "$CONFIG_SOUND" != "n" ]; then + source drivers/sound/Config.in + fi + endmenu fi if [ "$CONFIG_SGI" = "y" ]; then - source drivers/sgi/Config.in + source drivers/sgi/Config.in fi mainmenu_option next_comment @@ -293,10 +289,10 @@ #bool 'Debug kmalloc/kfree' CONFIG_DEBUG_MALLOC bool 'Are you using a crosscompiler' CONFIG_CROSSCOMPILE if [ "$CONFIG_MODULES" = "y" ]; then - bool ' Build fp execption handler module' CONFIG_MIPS_FPE_MODULE + bool ' Build fp execption handler module' CONFIG_MIPS_FPE_MODULE fi if [ "$CONFIG_SERIAL" = "y" ]; then - bool 'Remote GDB kernel debugging' CONFIG_REMOTE_DEBUG + bool 'Remote GDB kernel debugging' CONFIG_REMOTE_DEBUG fi bool 'Magic SysRq key' CONFIG_MAGIC_SYSRQ endmenu diff -u --recursive --new-file v2.3.19/linux/arch/mips/kernel/pci.c linux/arch/mips/kernel/pci.c --- v2.3.19/linux/arch/mips/kernel/pci.c Tue Aug 31 17:29:12 1999 +++ linux/arch/mips/kernel/pci.c Thu Oct 7 12:23:21 1999 @@ -13,7 +13,6 @@ #include #include #include -#include #ifdef CONFIG_PCI diff -u --recursive --new-file v2.3.19/linux/arch/mips/sni/pci.c linux/arch/mips/sni/pci.c --- v2.3.19/linux/arch/mips/sni/pci.c Fri Jun 25 17:40:13 1999 +++ linux/arch/mips/sni/pci.c Thu Oct 7 12:23:21 1999 @@ -13,7 +13,6 @@ #include #include #include -#include #include #ifdef CONFIG_PCI diff -u --recursive --new-file v2.3.19/linux/arch/mips/sni/setup.c linux/arch/mips/sni/setup.c --- v2.3.19/linux/arch/mips/sni/setup.c Tue Aug 31 17:29:12 1999 +++ linux/arch/mips/sni/setup.c Thu Oct 7 12:23:21 1999 @@ -31,7 +31,6 @@ #include #include #include -#include /* * Initial irq handlers. diff -u --recursive --new-file v2.3.19/linux/arch/ppc/8xx_io/Config.in linux/arch/ppc/8xx_io/Config.in --- v2.3.19/linux/arch/ppc/8xx_io/Config.in Wed Dec 31 16:00:00 1969 +++ linux/arch/ppc/8xx_io/Config.in Thu Oct 7 10:17:08 1999 @@ -0,0 +1,16 @@ +# +# MPC8xx Communication options +# +if [ "$CONFIG_NET_ETHERNET" = "y" ]; then + mainmenu_option next_comment + comment 'MPC8xx Communication Options' + bool 'CPM SCC Ethernet' CONFIG_SCC_ENET + if [ "$CONFIG_SCC_ENET" = "y" ]; then + bool 'Ethernet on SCC1' CONFIG_SCC1_ENET + if [ "$CONFIG_SCC1_ENET" != "y" ]; then + bool 'Ethernet on SCC2' CONFIG_SCC2_ENET + fi + fi + bool '860T FEC Ethernet' CONFIG_FEC_ENET + endmenu +fi diff -u --recursive --new-file v2.3.19/linux/arch/ppc/8xx_io/Makefile linux/arch/ppc/8xx_io/Makefile --- v2.3.19/linux/arch/ppc/8xx_io/Makefile Wed Sep 30 10:14:16 1998 +++ linux/arch/ppc/8xx_io/Makefile Thu Oct 7 10:17:08 1999 @@ -9,11 +9,12 @@ O_TARGET := 8xx_io.a O_OBJS = commproc.o uart.o -ifdef CONFIG_MBX -O_OBJS += enet.o -endif -ifdef CONFIG_FADS + +ifdef CONFIG_FEC_ENET O_OBJS += fec.o +endif +ifdef CONFIG_SCC_ENET +O_OBJS += enet.o endif include $(TOPDIR)/Rules.make diff -u --recursive --new-file v2.3.19/linux/arch/ppc/8xx_io/commproc.c linux/arch/ppc/8xx_io/commproc.c --- v2.3.19/linux/arch/ppc/8xx_io/commproc.c Fri Mar 19 10:50:03 1999 +++ linux/arch/ppc/8xx_io/commproc.c Thu Oct 7 10:17:08 1999 @@ -30,12 +30,7 @@ #include #include #include -#ifdef CONFIG_MBX -#include -#endif -#ifdef CONFIG_FADS -#include -#endif +#include #include #include #include @@ -95,32 +90,36 @@ */ dp_alloc_base = CPM_DATAONLY_BASE; dp_alloc_top = dp_alloc_base + CPM_DATAONLY_SIZE; + /* Set the host page for allocation. */ host_buffer = host_page_addr; /* Host virtual page address */ host_end = host_page_addr + PAGE_SIZE; - pte = va_to_pte(&init_task, host_page_addr); + pte = find_pte(&init_mm, host_page_addr); pte_val(*pte) |= _PAGE_NO_CACHE; flush_tlb_page(current->mm->mmap, host_buffer); /* Tell everyone where the comm processor resides. */ cpmp = (cpm8xx_t *)commproc; +} +/* This is called during init_IRQ. We used to do it above, but this + * was too early since init_IRQ was not yet called. + */ +void +cpm_interrupt_init(void) +{ /* Initialize the CPM interrupt controller. */ ((immap_t *)IMAP_ADDR)->im_cpic.cpic_cicr = (CICR_SCD_SCC4 | CICR_SCC_SCC3 | CICR_SCB_SCC2 | CICR_SCA_SCC1) | - (((5)/2) << 13) | CICR_HP_MASK; - /* I hard coded the CPM interrupt to 5 above - * since the CPM_INTERRUPT define is relative to - * the linux irq structure not what the hardware - * belives. -- Cort - */ + ((CPM_INTERRUPT/2) << 13) | CICR_HP_MASK; ((immap_t *)IMAP_ADDR)->im_cpic.cpic_cimr = 0; + /* Set our interrupt handler with the core CPU. */ - if (request_irq(CPM_INTERRUPT, cpm_interrupt, 0, "cpm", NULL) != 0) + if (request_8xxirq(CPM_INTERRUPT, cpm_interrupt, 0, "cpm", NULL) != 0) panic("Could not allocate CPM IRQ!"); /* Install our own error handler. @@ -178,6 +177,16 @@ ((immap_t *)IMAP_ADDR)->im_cpic.cpic_cimr |= (1 << vec); } +/* Free a CPM interrupt handler. +*/ +void +cpm_free_handler(int vec) +{ + cpm_vecs[vec].handler = NULL; + cpm_vecs[vec].dev_id = NULL; + ((immap_t *)IMAP_ADDR)->im_cpic.cpic_cimr &= ~(1 << vec); +} + /* Allocate some memory from the dual ported ram. We may want to * enforce alignment restrictions, but right now everyone is a good * citizen. @@ -218,7 +227,7 @@ * The internal baud rate clock is the system clock divided by 16. * This assumes the baudrate is 16x oversampled by the uart. */ -#define BRG_INT_CLK (((bd_t *)res)->bi_intfreq * 1000000) +#define BRG_INT_CLK (((bd_t *)__res)->bi_intfreq * 1000000) #define BRG_UART_CLK (BRG_INT_CLK/16) void diff -u --recursive --new-file v2.3.19/linux/arch/ppc/8xx_io/commproc.h linux/arch/ppc/8xx_io/commproc.h --- v2.3.19/linux/arch/ppc/8xx_io/commproc.h Wed Sep 30 10:14:16 1998 +++ linux/arch/ppc/8xx_io/commproc.h Thu Oct 7 10:17:08 1999 @@ -32,6 +32,7 @@ #define CPM_CR_INIT_TRX ((ushort)0x0000) #define CPM_CR_INIT_RX ((ushort)0x0001) #define CPM_CR_INIT_TX ((ushort)0x0002) +#define CPM_CR_HUNT_MODE ((ushort)0x0003) #define CPM_CR_STOP_TX ((ushort)0x0004) #define CPM_CR_RESTART_TX ((ushort)0x0006) #define CPM_CR_SET_GADDR ((ushort)0x0008) @@ -78,6 +79,7 @@ #define BD_SC_READY ((ushort)0x8000) /* Transmit is ready */ #define BD_SC_WRAP ((ushort)0x2000) /* Last buffer descriptor */ #define BD_SC_INTRPT ((ushort)0x1000) /* Interrupt on change */ +#define BD_SC_LAST ((ushort)0x0800) /* Last buffer in frame */ #define BD_SC_CM ((ushort)0x0200) /* Continous mode */ #define BD_SC_ID ((ushort)0x0100) /* Rec'd too many idles */ #define BD_SC_P ((ushort)0x0100) /* xmt preamble */ @@ -90,6 +92,7 @@ /* Parameter RAM offsets. */ #define PROFF_SCC1 ((uint)0x0000) +#define PROFF_IIC ((uint)0x0080) #define PROFF_SCC2 ((uint)0x0100) #define PROFF_SCC3 ((uint)0x0200) #define PROFF_SMC1 ((uint)0x0280) @@ -97,6 +100,7 @@ #define PROFF_SMC2 ((uint)0x0380) /* Define enough so I can at least use the serial port as a UART. + * The MBX uses SMC1 as the host serial port. */ typedef struct smc_uart { ushort smc_rbase; /* Rx Buffer descriptor base address */ @@ -136,11 +140,54 @@ #define SMCMR_SM_TRANS ((ushort)0x0030) #define SMCMR_SM_MASK ((ushort)0x0030) #define SMCMR_PM_EVEN ((ushort)0x0100) /* Even parity, else odd */ +#define SMCMR_REVD SMCMR_PM_EVEN #define SMCMR_PEN ((ushort)0x0200) /* Parity enable */ +#define SMCMR_BS SMCMR_PEN #define SMCMR_SL ((ushort)0x0400) /* Two stops, else one */ #define SMCR_CLEN_MASK ((ushort)0x7800) /* Character length */ #define smcr_mk_clen(C) (((C) << 11) & SMCR_CLEN_MASK) +/* SMC2 as Centronics parallel printer. It is half duplex, in that + * it can only receive or transmit. The parameter ram values for + * each direction are either unique or properly overlap, so we can + * include them in one structure. + */ +typedef struct smc_centronics { + ushort scent_rbase; + ushort scent_tbase; + u_char scent_cfcr; + u_char scent_smask; + ushort scent_mrblr; + uint scent_rstate; + uint scent_r_ptr; + ushort scent_rbptr; + ushort scent_r_cnt; + uint scent_rtemp; + uint scent_tstate; + uint scent_t_ptr; + ushort scent_tbptr; + ushort scent_t_cnt; + uint scent_ttemp; + ushort scent_max_sl; + ushort scent_sl_cnt; + ushort scent_character1; + ushort scent_character2; + ushort scent_character3; + ushort scent_character4; + ushort scent_character5; + ushort scent_character6; + ushort scent_character7; + ushort scent_character8; + ushort scent_rccm; + ushort scent_rccr; +} smc_cent_t; + +/* Centronics Status Mask Register. +*/ +#define SMC_CENT_F ((u_char)0x08) +#define SMC_CENT_PE ((u_char)0x04) +#define SMC_CENT_S ((u_char)0x02) + /* SMC Event and Mask register. */ #define SMCM_TXE ((unsigned char)0x10) @@ -329,6 +376,7 @@ ushort sen_taddrl; /* temp address (LSB) */ } scc_enet_t; +#ifdef CONFIG_MBX /* Bits in parallel I/O port registers that have to be set/cleared * to configure the pins for SCC1 use. The TCLK and RCLK seem unique * to the MBX860 board. Any two of the four available clocks could be @@ -348,6 +396,65 @@ */ #define SICR_ENET_MASK ((uint)0x000000ff) #define SICR_ENET_CLKRT ((uint)0x0000003d) +#endif + +#ifdef CONFIG_RPXLITE +/* This ENET stuff is for the MPC850 with ethernet on SCC2. Some of + * this may be unique to the RPX-Lite configuration. + * Note TENA is on Port B. + */ +#define PA_ENET_RXD ((ushort)0x0004) +#define PA_ENET_TXD ((ushort)0x0008) +#define PA_ENET_TCLK ((ushort)0x0200) +#define PA_ENET_RCLK ((ushort)0x0800) +#define PB_ENET_TENA ((uint)0x00002000) +#define PC_ENET_CLSN ((ushort)0x0040) +#define PC_ENET_RENA ((ushort)0x0080) + +#define SICR_ENET_MASK ((uint)0x0000ff00) +#define SICR_ENET_CLKRT ((uint)0x00003d00) +#endif + +#ifdef CONFIG_BSEIP +/* This ENET stuff is for the MPC823 with ethernet on SCC2. + * This is unique to the BSE ip-Engine board. + */ +#define PA_ENET_RXD ((ushort)0x0004) +#define PA_ENET_TXD ((ushort)0x0008) +#define PA_ENET_TCLK ((ushort)0x0100) +#define PA_ENET_RCLK ((ushort)0x0200) +#define PB_ENET_TENA ((uint)0x00002000) +#define PC_ENET_CLSN ((ushort)0x0040) +#define PC_ENET_RENA ((ushort)0x0080) + +/* BSE uses port B and C bits for PHY control also. +*/ +#define PB_BSE_POWERUP ((uint)0x00000004) +#define PB_BSE_FDXDIS ((uint)0x00008000) +#define PC_BSE_LOOPBACK ((ushort)0x0800) + +#define SICR_ENET_MASK ((uint)0x0000ff00) +#define SICR_ENET_CLKRT ((uint)0x00002c00) +#endif + +#ifdef CONFIG_RPXCLASSIC +/* Bits in parallel I/O port registers that have to be set/cleared + * to configure the pins for SCC1 use. + */ +#define PA_ENET_RXD ((ushort)0x0001) +#define PA_ENET_TXD ((ushort)0x0002) +#define PA_ENET_TCLK ((ushort)0x0200) +#define PA_ENET_RCLK ((ushort)0x0800) +#define PB_ENET_TENA ((uint)0x00001000) +#define PC_ENET_CLSN ((ushort)0x0010) +#define PC_ENET_RENA ((ushort)0x0020) + +/* Control bits in the SICR to route TCLK (CLK2) and RCLK (CLK4) to + * SCC1. Also, make sure GR1 (bit 24) and SC1 (bit 25) are zero. + */ +#define SICR_ENET_MASK ((uint)0x000000ff) +#define SICR_ENET_CLKRT ((uint)0x0000003d) +#endif /* SCC Event register as used by Ethernet. */ @@ -475,6 +582,30 @@ uint st_cpres; /* Preset CRC */ uint st_cmask; /* Constant mask for CRC */ } scc_trans_t; + +#define BD_SCC_TX_LAST ((ushort)0x0800) + +/* IIC parameter RAM. +*/ +typedef struct iic { + ushort iic_rbase; /* Rx Buffer descriptor base address */ + ushort iic_tbase; /* Tx Buffer descriptor base address */ + u_char iic_rfcr; /* Rx function code */ + u_char iic_tfcr; /* Tx function code */ + ushort iic_mrblr; /* Max receive buffer length */ + uint iic_rstate; /* Internal */ + uint iic_rdp; /* Internal */ + ushort iic_rbptr; /* Internal */ + ushort iic_rbc; /* Internal */ + uint iic_rxtmp; /* Internal */ + uint iic_tstate; /* Internal */ + uint iic_tdp; /* Internal */ + ushort iic_tbptr; /* Internal */ + ushort iic_tbc; /* Internal */ + uint iic_txtmp; /* Internal */ +} iic_t; + +#define BD_IIC_START ((ushort)0x0400) /* CPM interrupts. There are nearly 32 interrupts generated by CPM * channels or devices. All of these are presented to the PPC core diff -u --recursive --new-file v2.3.19/linux/arch/ppc/8xx_io/enet.c linux/arch/ppc/8xx_io/enet.c --- v2.3.19/linux/arch/ppc/8xx_io/enet.c Wed Aug 18 11:39:01 1999 +++ linux/arch/ppc/8xx_io/enet.c Thu Oct 7 10:17:08 1999 @@ -4,12 +4,13 @@ * * I copied the basic skeleton from the lance driver, because I did not * know how to write the Linux driver, but I did know how the LANCE worked. - * This version of the driver is specific to the MBX implementation, - * since the board contains control registers external to the processor - * for the control of the MC68160 SIA/transceiver. The MPC860 manual - * describes connections using the internal parallel port I/O. * - * The MBX860 uses the CPM SCC1 serial port for the Ethernet interface. + * This version of the driver is somewhat selectable for the different + * processor/board combinations. It works for the boards I know about + * now, and should be easily modified to include others. Some of the + * configuration information is contained in "commproc.h" and the + * remainder is here. + * * Buffer descriptors are kept in the CPM dual port RAM, and the frame * buffers are in the host memory. * @@ -21,7 +22,6 @@ * small packets. * */ -#include #include #include #include @@ -39,7 +39,7 @@ #include #include -#include +#include #include #include #include "commproc.h" @@ -164,16 +164,17 @@ */ /*static ushort my_enet_addr[] = { 0x0800, 0x3e26, 0x1559 };*/ -/* Right now, only the boards with an 860 use SCC1 for the Ethernet. - * All others use SCC2. We may need to make this board specific someday. +/* Typically, 860(T) boards use SCC1 for Ethernet, and other 8xx boards + * use SCC2. This is easily extended if necessary. */ -#ifndef CONFIG_MPC860 -/*static ushort my_enet_addr[] = { 0x2700, 0x00ec, 0x1000 };*/ +#ifdef CONFIG_SCC2_ENET #define CPM_CR_ENET CPM_CR_CH_SCC2 #define PROFF_ENET PROFF_SCC2 #define SCC_ENET 1 /* Index, not number! */ #define CPMVEC_ENET CPMVEC_SCC2 -#else +#endif + +#ifdef CONFIG_SCC1_ENET #define CPM_CR_ENET CPM_CR_CH_SCC1 #define PROFF_ENET PROFF_SCC1 #define SCC_ENET 0 @@ -326,7 +327,7 @@ static void cpm_enet_interrupt(void *dev_id) { - struct net_device *dev = dev_id; + struct net_device *dev = dev_id; volatile struct cpm_enet_private *cep; volatile cbd_t *bdp; ushort int_events; @@ -357,43 +358,10 @@ * I don't know if "normally" implies TXB is set when the buffer * descriptor is closed.....trial and error :-). */ -#if 0 - if (int_events & SCCE_ENET_TXE) { - - /* Transmission errors. - */ - bdp = cep->dirty_tx; -#ifndef final_version - printk("CPM ENET xmit error %x\n", bdp->cbd_sc); - if (bdp->cbd_sc & BD_ENET_TX_READY) - printk("HEY! Enet xmit interrupt and TX_READY.\n"); -#endif - if (bdp->cbd_sc & BD_ENET_TX_HB) /* No heartbeat */ - cep->stats.tx_heartbeat_errors++; - if (bdp->cbd_sc & BD_ENET_TX_LC) /* Late collision */ - cep->stats.tx_window_errors++; - if (bdp->cbd_sc & BD_ENET_TX_RL) /* Retrans limit */ - cep->stats.tx_aborted_errors++; - if (bdp->cbd_sc & BD_ENET_TX_UN) /* Underrun */ - cep->stats.tx_fifo_errors++; - if (bdp->cbd_sc & BD_ENET_TX_CSL) /* Carrier lost */ - cep->stats.tx_carrier_errors++; - - cep->stats.tx_errors++; - - /* No heartbeat or Lost carrier are not really bad errors. - * The others require a restart transmit command. - */ - if (bdp->cbd_sc & - (BD_ENET_TX_LC | BD_ENET_TX_RL | BD_ENET_TX_UN)) - must_restart = 1; - } -#endif /* Transmit OK, or non-fatal error. Update the buffer descriptors. */ if (int_events & (SCCE_ENET_TXE | SCCE_ENET_TXB)) { -#if 1 bdp = cep->dirty_tx; while ((bdp->cbd_sc&BD_ENET_TX_READY)==0) { if ((bdp==cep->cur_tx) && (cep->tx_full == 0)) @@ -421,13 +389,7 @@ } cep->stats.tx_packets++; -#else - bdp = cep->dirty_tx; -#if 1 - if (bdp->cbd_sc & BD_ENET_TX_READY) - printk("HEY! Enet xmit interrupt and TX_READY.\n"); -#endif -#endif + /* Deferred means some collisions occurred during transmit, * but we eventually sent the packet OK. */ @@ -697,9 +659,7 @@ * transmit and receive to make sure we don't catch the CPM with some * inconsistent control information. */ -/* until this gets cleared up -- Cort */ -int __init cpm_enet_init() { m8xx_enet_init(); } -int __init m8xx_enet_init(void) +int __init cpm_enet_init(void) { struct net_device *dev; struct cpm_enet_private *cep; @@ -718,7 +678,7 @@ immap = (immap_t *)IMAP_ADDR; /* and to internal registers */ - bd = (bd_t *)res; + bd = (bd_t *)__res; /* Allocate some private information. */ @@ -830,8 +790,8 @@ ep->sen_maxflr = PKT_MAXBUF_SIZE; /* maximum frame length register */ ep->sen_minflr = PKT_MINBUF_SIZE; /* minimum frame length register */ - ep->sen_maxd1 = PKT_MAXBUF_SIZE; /* maximum DMA1 length */ - ep->sen_maxd2 = PKT_MAXBUF_SIZE; /* maximum DMA2 length */ + ep->sen_maxd1 = PKT_MAXBLR_SIZE; /* maximum DMA1 length */ + ep->sen_maxd2 = PKT_MAXBLR_SIZE; /* maximum DMA2 length */ /* Clear hash tables. */ @@ -849,6 +809,9 @@ * If we performed a MBX diskless boot, the Ethernet controller * has been initialized and we copy the address out into our * own structure. + * + * All other types of boards supply the address in the board + * information structure, so we copy that into the controller. */ eap = (unsigned char *)&(ep->sen_paddrh); #ifndef CONFIG_MBX @@ -891,7 +854,7 @@ /* Make it uncached. */ - pte = va_to_pte(&init_task, mem_addr); + pte = find_pte(&init_mm, mem_addr); pte_val(*pte) |= _PAGE_NO_CACHE; flush_tlb_page(current->mm->mmap, mem_addr); @@ -983,7 +946,9 @@ dev->base_addr = (unsigned long)ep; dev->priv = cep; +#if 0 dev->name = "CPM_ENET"; +#endif /* The CPM Ethernet specific entries in the device structure. */ dev->open = cpm_enet_open; @@ -996,7 +961,7 @@ */ sccp->scc_gsmrl |= (SCC_GSMRL_ENR | SCC_GSMRL_ENT); - printk("CPM ENET Version 0.1, "); + printk("%s: CPM ENET Version 0.2, ", dev->name); for (i=0; i<5; i++) printk("%02x:", dev->dev_addr[i]); printk("%02x\n", dev->dev_addr[5]); diff -u --recursive --new-file v2.3.19/linux/arch/ppc/8xx_io/fec.c linux/arch/ppc/8xx_io/fec.c --- v2.3.19/linux/arch/ppc/8xx_io/fec.c Tue Aug 31 17:29:12 1999 +++ linux/arch/ppc/8xx_io/fec.c Thu Oct 7 10:17:08 1999 @@ -33,7 +33,7 @@ #include #include -#include +#include #include #include #include @@ -123,7 +123,7 @@ */ typedef struct mii_list { uint mii_regval; - void (*mii_func)(uint val); + void (*mii_func)(int val); struct mii_list *mii_next; } mii_list_t; @@ -244,7 +244,7 @@ /* Push the data cache so the CPM does not get stale memory * data. */ - /*flush_dcache_range(skb->data, skb->data + skb->len);*/ + flush_dcache_range(skb->data, skb->data + skb->len); /* Send it on its way. Tell CPM its ready, interrupt when done, * its the last BD of the frame, and to put the CRC on the end. @@ -282,7 +282,7 @@ static void fec_enet_interrupt(int irq, void * dev_id, struct pt_regs * regs) { - struct net_device *dev = dev_id; + struct net_device *dev = dev_id; struct fec_enet_private *fep; volatile cbd_t *bdp; volatile fec_t *ep; @@ -600,6 +600,9 @@ else printk(", Half-Duplex\n"); } + if (((mii_reg >> 18) & 0x1f) == 0x1f) { + printk("fec: %x\n", mii_reg); + } } static void @@ -609,6 +612,7 @@ /* Read status registers to clear any pending interrupt. */ mii_queue(mk_mii_read(1), mii_status); +#ifndef CONFIG_RPXCLASSIC mii_queue(mk_mii_read(18), mii_status); /* Read extended chip status register. @@ -616,8 +620,23 @@ mii_queue(mk_mii_read(0x14), mii_status); /* Enable Link status change interrupts. + */ mii_queue(mk_mii_write(0x11, 0x0002), NULL); + +#ifdef CONFIG_FADS + /* FADS uses the TRSTE in the BCSR, which is kind of weird. + * This really controls the startup default configuration. + * Changing the state of TRSTE once powered up doesn't do + * anything, you have to whack the control register. + * This of course screws up any autoconfig that was done....... + */ + mii_queue(mk_mii_write(0, 0x1000), NULL); +#endif +#else + /* Experimenting with the QS6612 PHY....not done yet. */ + mii_queue(mk_mii_read(31), mii_status); +#endif } /* This supports the mii_link interrupt below. @@ -676,7 +695,7 @@ static void mii_link_interrupt(int irq, void * dev_id, struct pt_regs * regs) { - struct net_device *dev = dev_id; + struct net_device *dev = dev_id; struct fec_enet_private *fep; volatile fec_t *ep; @@ -691,8 +710,19 @@ * as part of the "normal" processing. */ mii_queue(mk_mii_read(1), mii_relink); +#ifndef CONFIG_RPXCLASSIC + + /* Unique to LevelOne PHY. + */ mii_queue(mk_mii_read(18), mii_relink); mii_queue(mk_mii_read(20), mii_relink); +#else + + /* Unique to QS6612 PHY. + */ + mii_queue(mk_mii_read(6), mii_relink); + mii_queue(mk_mii_read(31), mii_relink); +#endif } static int @@ -788,9 +818,9 @@ } } -/* Initialize the FECC Ethernet on 860T. +/* Initialize the FEC Ethernet on 860T. */ -int __init m8xx_enet_init(void) +int __init fec_enet_init(void) { struct net_device *dev; struct fec_enet_private *fep; @@ -802,7 +832,10 @@ cbd_t *cbd_base; volatile immap_t *immap; volatile fec_t *fecp; - unsigned char rtc_save_cfg, rtc_val; + unsigned char *iap; + bd_t *bd; + + bd = (bd_t *)__res; immap = (immap_t *)IMAP_ADDR; /* pointer to internal registers */ @@ -833,15 +866,27 @@ fecp->fec_ivec = (FEC_INTERRUPT/2) << 29; + /* Right now, all of the boards supply the ethernet address in + * the board descriptor. If someone doesn't we can just use + * the hard coded address in this driver for testing (this is + * a Motorola address for a board I have, so it is unlikely to + * be used elsewhere). + */ + eap = (unsigned char *)&my_enet_addr[0]; +#if 1 + iap = bd->bi_enetaddr; + for (i=0; i<6; i++) + dev->dev_addr[i] = *eap++ = *iap++; +#else + for (i=0; i<6; i++) + dev->dev_addr[i] = *eap++; +#endif + /* Set station address. */ fecp->fec_addr_low = (my_enet_addr[0] << 16) | my_enet_addr[1]; fecp->fec_addr_high = my_enet_addr[2]; - eap = (unsigned char *)&my_enet_addr[0]; - for (i=0; i<6; i++) - dev->dev_addr[i] = *eap++; - /* Reset all multicast. */ fecp->fec_hash_table_high = 0; @@ -855,8 +900,8 @@ /* Allocate memory for buffer descriptors. */ if (((RX_RING_SIZE + TX_RING_SIZE) * sizeof(cbd_t)) > PAGE_SIZE) { - printk("FECC init error. Need more space.\n"); - printk("FECC initialization failed.\n"); + printk("FEC init error. Need more space.\n"); + printk("FEC initialization failed.\n"); return 1; } mem_addr = __get_free_page(GFP_KERNEL); @@ -864,7 +909,7 @@ /* Make it uncached. */ - pte = va_to_pte(&init_task, (int)mem_addr); + pte = find_pte(&init_mm, (int)mem_addr); pte_val(*pte) |= _PAGE_NO_CACHE; flush_tlb_page(current->mm->mmap, mem_addr); @@ -891,7 +936,7 @@ /* Make it uncached. */ - pte = va_to_pte(&init_task, mem_addr); + pte = find_pte(&init_mm, mem_addr); pte_val(*pte) |= _PAGE_NO_CACHE; flush_tlb_page(current->mm->mmap, mem_addr); @@ -948,9 +993,9 @@ /* Install our interrupt handlers. The 860T FADS board uses * IRQ2 for the MII interrupt. */ - if (request_irq(FEC_INTERRUPT, fec_enet_interrupt, 0, "fec", dev) != 0) + if (request_8xxirq(FEC_INTERRUPT, fec_enet_interrupt, 0, "fec", dev) != 0) panic("Could not allocate FEC IRQ!"); - if (request_irq(SIU_IRQ2, mii_link_interrupt, 0, "mii", dev) != 0) + if (request_8xxirq(SIU_IRQ2, mii_link_interrupt, 0, "mii", dev) != 0) panic("Could not allocate MII IRQ!"); dev->base_addr = (unsigned long)fecp; diff -u --recursive --new-file v2.3.19/linux/arch/ppc/8xx_io/uart.c linux/arch/ppc/8xx_io/uart.c --- v2.3.19/linux/arch/ppc/8xx_io/uart.c Tue Aug 31 17:29:12 1999 +++ linux/arch/ppc/8xx_io/uart.c Thu Oct 7 10:17:08 1999 @@ -38,13 +38,7 @@ #include #include #include - -#ifdef CONFIG_MBX -#include -#endif -#ifdef CONFIG_FADS -#include -#endif +#include #include "commproc.h" #ifdef CONFIG_SERIAL_CONSOLE @@ -101,18 +95,40 @@ * The SMCs do not support any modem control signals. */ #define smc_scc_num hub6 -#define SCC_NUM_BASE 2 -/* The index into the CPM registers for the first SCC in the table. +/* SMC2 is sometimes used for low performance TDM interfaces. Define + * this as 1 if you want SMC2 as a serial port UART managed by this driver. + * Define this as 0 if you wish to use SMC2 for something else. + */ +#define USE_SMC2 1 + +/* Define SCC to ttySx mapping. */ -#define SCC_IDX_BASE 1 +#define SCC_NUM_BASE (USE_SMC2 + 1) /* SCC base tty "number" */ +/* Define which SCC is the first one to use for a serial port. These + * are 0-based numbers, i.e. this assumes the first SCC (SCC1) is used + * for Ethernet, and the first available SCC for serial UART is SCC2. + * NOTE: IF YOU CHANGE THIS, you have to change the PROFF_xxx and + * interrupt vectors in the table below to match. + */ +#define SCC_IDX_BASE 1 /* table index */ + +/* Processors other than the 860 only get SMCs configured by default. + * Either they don't have SCCs or they are allocated somewhere else. + * Of course, there are now 860s without some SCCs, so we will need to + * address that someday. + */ static struct serial_state rs_table[] = { /* UART CLK PORT IRQ FLAGS NUM */ { 0, 0, PROFF_SMC1, CPMVEC_SMC1, 0, 0 }, /* SMC1 ttyS0 */ - { 0, 0, PROFF_SMC2, CPMVEC_SMC2, 0, 1 }, /* SMC1 ttyS0 */ - { 0, 0, PROFF_SCC2, CPMVEC_SCC2, 0, 2 }, /* SCC2 ttyS2 */ - { 0, 0, PROFF_SCC3, CPMVEC_SCC3, 0, 3 }, /* SCC3 ttyS3 */ +#if USE_SMC2 + { 0, 0, PROFF_SMC2, CPMVEC_SMC2, 0, 1 }, /* SMC2 ttyS1 */ +#endif +#if defined(CONFIG_MPC860) || defined(CONFIG_MPC860T) + { 0, 0, PROFF_SCC2, CPMVEC_SCC2, 0, SCC_NUM_BASE}, /* SCC2 ttyS2 */ + { 0, 0, PROFF_SCC3, CPMVEC_SCC3, 0, SCC_NUM_BASE + 1}, /* SCC3 ttyS3 */ +#endif }; #define NR_PORTS (sizeof(rs_table)/sizeof(struct serial_state)) @@ -820,15 +836,10 @@ /* Determine divisor based on baud rate */ i = cflag & CBAUD; - if (i & CBAUDEX) { - i &= ~CBAUDEX; - if (i < 1 || i > 4) - info->tty->termios->c_cflag &= ~CBAUDEX; - else - i += 15; - } - - baud_rate = baud_table[i]; + if (i >= (sizeof(baud_table)/sizeof(int))) + baud_rate = 9600; + else + baud_rate = baud_table[i]; info->timeout = (TX_BUF_SIZE*HZ*bits); info->timeout += HZ/50; /* Add .02 seconds of slop */ @@ -1692,7 +1703,7 @@ schedule_timeout(char_time); if (signal_pending(current)) break; - if (timeout && time_after(jiffies, orig_jiffies + timeout)) + if (timeout && ((orig_jiffies + timeout) < jiffies)) break; bdp = info->tx_cur; } while (bdp->cbd_sc & BD_SC_READY); @@ -2251,6 +2262,13 @@ #endif +/* This will be used for all boards when the MBX board information + * is modified to include a default baud rate. + */ +#ifndef CONFIG_MBX +static int baud_idx; +#endif + /* * The serial driver boot-time initialization code! */ @@ -2291,7 +2309,11 @@ serial_driver.subtype = SERIAL_TYPE_NORMAL; serial_driver.init_termios = tty_std_termios; serial_driver.init_termios.c_cflag = +#ifndef CONFIG_MBX + baud_idx | CS8 | CREAD | HUPCL | CLOCAL; +#else B9600 | CS8 | CREAD | HUPCL | CLOCAL; +#endif serial_driver.flags = TTY_DRIVER_REAL_RAW; serial_driver.refcount = &serial_refcount; serial_driver.table = serial_table; @@ -2337,12 +2359,21 @@ /* Configure SMCs Tx/Rx instead of port B parallel I/O. */ +#if USE_SMC2 cp->cp_pbpar |= 0x00000cc0; cp->cp_pbdir &= ~0x00000cc0; cp->cp_pbodr &= ~0x00000cc0; +#else + /* This will only enable SMC1 if you want SMC2 for something else. + */ + cp->cp_pbpar |= 0x000000c0; + cp->cp_pbdir &= ~0x000000c0; + cp->cp_pbodr &= ~0x000000c0; +#endif /* Configure SCC2 and SCC3 instead of port A parallel I/O. */ +#if defined(CONFIG_MPC860) || defined(CONFIG_MPC860T) #ifndef CONFIG_MBX /* The "standard" configuration through the 860. */ @@ -2366,15 +2397,16 @@ immap->im_ioport.iop_pcdir |= 0x03c6; immap->im_ioport.iop_pcpar &= ~0x03c6; - /* Wire BRG1 to SMC1 and BRG2 to SMC2. - */ - cp->cp_simode = 0x10000000; - /* Connect SCC2 and SCC3 to NMSI. Connect BRG3 to SCC2 and * BRG4 to SCC3. */ cp->cp_sicr &= ~0x00ffff00; cp->cp_sicr |= 0x001b1200; +#endif + + /* Wire BRG1 to SMC1 and BRG2 to SMC2. + */ + cp->cp_simode = 0x10000000; for (i = 0, state = rs_table; i < NR_PORTS; i++,state++) { state->magic = SSTATE_MAGIC; @@ -2580,7 +2612,12 @@ /* Set up the baud rate generator. */ +#ifndef CONFIG_MBX + m8xx_cpm_setbrg(state->smc_scc_num, + baud_table[baud_idx]); +#else m8xx_cpm_setbrg(state->smc_scc_num, 9600); +#endif /* If the port is the console, enable Rx and Tx. */ @@ -2599,12 +2636,26 @@ static int __init serial_console_setup(struct console *co, char *options) { struct serial_state *ser; - uint mem_addr, dp_addr; + uint mem_addr, dp_addr, bidx; volatile cbd_t *bdp; volatile cpm8xx_t *cp; volatile smc_t *sp; volatile smc_uart_t *up; + +#ifndef CONFIG_MBX + bd_t *bd; + + bd = (bd_t *)__res; + + for (bidx = 0; bidx < (sizeof(baud_table) / sizeof(int)); bidx++) + if (bd->bi_baudrate == baud_table[bidx]) + break; + + co->cflag = CREAD|CLOCAL|bidx|CS8; + baud_idx = bidx; +#else co->cflag = CREAD|CLOCAL|B9600|CS8; +#endif ser = rs_table + co->index; @@ -2670,7 +2721,11 @@ /* Set up the baud rate generator. */ +#ifndef CONFIG_MBX + m8xx_cpm_setbrg(ser->smc_scc_num, bd->bi_baudrate); +#else m8xx_cpm_setbrg(ser->smc_scc_num, 9600); +#endif /* And finally, enable Rx and Tx. */ diff -u --recursive --new-file v2.3.19/linux/arch/ppc/Makefile linux/arch/ppc/Makefile --- v2.3.19/linux/arch/ppc/Makefile Fri Sep 10 23:57:27 1999 +++ linux/arch/ppc/Makefile Thu Oct 7 10:17:08 1999 @@ -27,7 +27,7 @@ CPP = $(CC) -E $(CFLAGS) ifdef CONFIG_8xx -CFLAGS := $(CFLAGS) -mcpu=860 +CFLAGS := $(CFLAGS) -mcpu=860 -I../8xx_io endif ifdef CONFIG_PPC64 @@ -45,7 +45,7 @@ ARCHIVES := arch/ppc/kernel/kernel.o arch/ppc/mm/mm.o arch/ppc/lib/lib.o $(ARCHIVES) CORE_FILES := arch/ppc/kernel/kernel.o arch/ppc/mm/mm.o arch/ppc/lib/lib.o $(CORE_FILES) -ifdef CONFIG_8xx +ifdef CONFIG_MATH_EMULATION SUBDIRS += arch/ppc/math-emu ARCHIVES += arch/ppc/math-emu/math-emu.o CORE_FILES += arch/ppc/math-emu/math-emu.o @@ -77,7 +77,7 @@ BOOT_TARGETS = zImage znetboot.initrd zImage.initrd -ifdef CONFIG_MBX +ifdef CONFIG_8xx $(BOOT_TARGETS): $(CHECKS) vmlinux @$(MAKECOFFBOOT) $@ @$(MAKEMBXBOOT) $@ diff -u --recursive --new-file v2.3.19/linux/arch/ppc/amiga/Makefile linux/arch/ppc/amiga/Makefile --- v2.3.19/linux/arch/ppc/amiga/Makefile Tue Aug 4 16:06:36 1998 +++ linux/arch/ppc/amiga/Makefile Thu Oct 7 10:17:08 1999 @@ -12,4 +12,8 @@ bootinfo.o amisound.o chipram.o ints.o OX_OBJS := amiga_ksyms.o +ifdef CONFIG_AMIGA_PCMCIA +O_OBJS := $(O_OBJS) pcmcia.o +endif + include $(TOPDIR)/Rules.make diff -u --recursive --new-file v2.3.19/linux/arch/ppc/amiga/amiints.c linux/arch/ppc/amiga/amiints.c --- v2.3.19/linux/arch/ppc/amiga/amiints.c Tue Aug 31 17:29:12 1999 +++ linux/arch/ppc/amiga/amiints.c Thu Oct 7 10:17:08 1999 @@ -1,7 +1,3 @@ -/* Rename a few functions. */ -#define amiga_request_irq request_irq -#define amiga_free_irq free_irq - /* * linux/arch/m68k/amiga/amiints.c -- Amiga Linux interrupt handling code * @@ -23,6 +19,20 @@ * called again. * The whole interrupt handling for CIAs is moved to cia.c * /Roman Zippel + * + * 07/08/99: rewamp of the interrupt handling - we now have two types of + * interrupts, normal and fast handlers, fast handlers being + * marked with SA_INTERRUPT and runs with all other interrupts + * disabled. Normal interrupts disable their own source but + * run with all other interrupt sources enabled. + * PORTS and EXTER interrupts are always shared even if the + * drivers do not explicitly mark this when calling + * request_irq which they really should do. + * This is similar to the way interrupts are handled on all + * other architectures and makes a ton of sense besides + * having the advantage of making it easier to share + * drivers. + * /Jes */ #include @@ -90,7 +100,7 @@ } else { ami_irq_list[i] = new_irq_node(); ami_irq_list[i]->handler = ami_badint; - ami_irq_list[i]->flags = IRQ_FLG_STD; + ami_irq_list[i]->flags = 0; ami_irq_list[i]->dev_id = NULL; ami_irq_list[i]->devname = NULL; ami_irq_list[i]->next = NULL; @@ -108,7 +118,7 @@ custom.intreq = 0x7fff; #ifdef CONFIG_APUS - /* Clear any inter-CPU interrupt requests. Circumvents bug in + /* Clear any inter-CPU interupt requests. Circumvents bug in Blizzard IPL emulation HW (or so it appears). */ APUS_WRITE(APUS_INT_LVL, INTLVL_SETRESET | INTLVL_MASK); @@ -124,7 +134,7 @@ cia_init_IRQ(&ciab_base); } -static inline void amiga_insert_irq(irq_node_t **list, irq_node_t *node) +static inline int amiga_insert_irq(irq_node_t **list, irq_node_t *node) { unsigned long flags; irq_node_t *cur; @@ -138,19 +148,18 @@ cur = *list; - if (node->flags & IRQ_FLG_FAST) { - node->flags &= ~IRQ_FLG_SLOW; - while (cur && cur->flags & IRQ_FLG_FAST) { - list = &cur->next; - cur = cur->next; - } - } else if (node->flags & IRQ_FLG_SLOW) { - while (cur) { + if (node->flags & SA_INTERRUPT) { + if (node->flags & SA_SHIRQ) + return -EBUSY; + /* + * There should never be more than one + */ + while (cur && cur->flags & SA_INTERRUPT) { list = &cur->next; cur = cur->next; } } else { - while (cur && !(cur->flags & IRQ_FLG_SLOW)) { + while (cur) { list = &cur->next; cur = cur->next; } @@ -160,6 +169,7 @@ *list = node; restore_flags(flags); + return 0; } static inline void amiga_delete_irq(irq_node_t **list, void *dev_id) @@ -189,13 +199,16 @@ * If the addition was successful, it returns 0. */ -int amiga_request_irq(unsigned int irq, void (*handler)(int, void *, struct pt_regs *), +int amiga_request_irq(unsigned int irq, + void (*handler)(int, void *, struct pt_regs *), unsigned long flags, const char *devname, void *dev_id) { irq_node_t *node; + int error = 0; if (irq >= AMI_IRQS) { - printk ("%s: Unknown IRQ %d from %s\n", __FUNCTION__, irq, devname); + printk ("%s: Unknown IRQ %d from %s\n", __FUNCTION__, + irq, devname); return -ENXIO; } @@ -211,6 +224,11 @@ return cia_request_irq(&ciaa_base, irq - IRQ_AMIGA_CIAA, handler, flags, devname, dev_id); + /* + * IRQ_AMIGA_PORTS & IRQ_AMIGA_EXTER defaults to shared, + * we could add a check here for the SA_SHIRQ flag but all drivers + * should be aware of sharing anyway. + */ if (ami_servers[irq]) { if (!(node = new_irq_node())) return -ENOMEM; @@ -219,20 +237,8 @@ node->dev_id = dev_id; node->devname = devname; node->next = NULL; - amiga_insert_irq(&ami_irq_list[irq], node); + error = amiga_insert_irq(&ami_irq_list[irq], node); } else { - if (!(ami_irq_list[irq]->flags & IRQ_FLG_STD)) { - if (ami_irq_list[irq]->flags & IRQ_FLG_LOCK) { - printk("%s: IRQ %d from %s is not replaceable\n", - __FUNCTION__, irq, ami_irq_list[irq]->devname); - return -EBUSY; - } - if (!(flags & IRQ_FLG_REPLACE)) { - printk("%s: %s can't replace IRQ %d from %s\n", - __FUNCTION__, devname, irq, ami_irq_list[irq]->devname); - return -EBUSY; - } - } ami_irq_list[irq]->handler = handler; ami_irq_list[irq]->flags = flags; ami_irq_list[irq]->dev_id = dev_id; @@ -243,7 +249,7 @@ if (irq < IRQ_AMIGA_PORTS && !ami_ablecount[irq]) custom.intena = IF_SETCLR | ami_intena_vals[irq]; - return 0; + return error; } void amiga_free_irq(unsigned int irq, void *dev_id) @@ -276,7 +282,7 @@ printk("%s: removing probably wrong IRQ %d from %s\n", __FUNCTION__, irq, ami_irq_list[irq]->devname); ami_irq_list[irq]->handler = ami_badint; - ami_irq_list[irq]->flags = IRQ_FLG_STD; + ami_irq_list[irq]->flags = 0; ami_irq_list[irq]->dev_id = NULL; ami_irq_list[irq]->devname = NULL; custom.intena = ami_intena_vals[irq]; @@ -366,45 +372,58 @@ void amiga_do_irq_list(int irq, struct pt_regs *fp, struct irq_server *server) { irq_node_t *node, *slow_nodes; - unsigned short flags; + unsigned short flags, intena; kstat.irqs[0][SYS_IRQS + irq]++; if (server->count++) server->reentrance = 1; - /* serve first fast and normal handlers */ - for (node = ami_irq_list[irq]; - node && (!(node->flags & IRQ_FLG_SLOW)); - node = node->next) - node->handler(irq, node->dev_id, fp); - custom.intreq = ami_intena_vals[irq]; + + intena = ami_intena_vals[irq]; + custom.intreq = intena; + + /* serve first fast handlers - there can only be one of these */ + node = ami_irq_list[irq]; + + /* + * Timer interrupts show up like this + */ if (!node) { server->count--; return; } -#ifdef CONFIG_APUS - APUS_WRITE(APUS_IPL_EMU, IPLEMU_SETRESET | IPLEMU_DISABLEINT); - APUS_WRITE(APUS_IPL_EMU, IPLEMU_IPLMASK); - APUS_WRITE(APUS_IPL_EMU, (IPLEMU_SETRESET - | (~(fp->mq) & IPLEMU_IPLMASK))); - APUS_WRITE(APUS_IPL_EMU, IPLEMU_DISABLEINT); -#else + + if (node && (node->flags & SA_INTERRUPT)) { + save_flags(flags); + cli(); + node->handler(irq, node->dev_id, fp); + restore_flags(flags); + + server->count--; + return; + } + + /* + * Disable the interrupt source in question and reenable all + * other interrupts. No interrupt handler should ever touch + * the intena flags directly! + */ + custom.intena = intena; save_flags(flags); - restore_flags((flags & ~0x0700) | (fp->sr & 0x0700)); -#endif - /* if slow handlers exists, serve them now */ + sti(); + slow_nodes = node; for (;;) { for (; node; node = node->next) node->handler(irq, node->dev_id, fp); - /* if reentrance occurred, serve slow handlers again */ - custom.intena = ami_intena_vals[irq]; + if (!server->reentrance) { server->count--; - custom.intena = IF_SETCLR | ami_intena_vals[irq]; + restore_flags(flags); + custom.intena = IF_SETCLR | intena; return; } + server->reentrance = 0; - custom.intena = IF_SETCLR | ami_intena_vals[irq]; node = slow_nodes; } } @@ -522,24 +541,13 @@ for (i = 0; i < AMI_STD_IRQS; i++) { if (!(node = ami_irq_list[i])) continue; - if (node->flags & IRQ_FLG_STD) - continue; len += sprintf(buf+len, "ami %2d: %10u ", i, kstat.irqs[0][SYS_IRQS + i]); do { - if (ami_servers[i]) { - if (node->flags & IRQ_FLG_FAST) - len += sprintf(buf+len, "F "); - else if (node->flags & IRQ_FLG_SLOW) - len += sprintf(buf+len, "S "); - else - len += sprintf(buf+len, " "); - } else { - if (node->flags & IRQ_FLG_LOCK) - len += sprintf(buf+len, "L "); - else - len += sprintf(buf+len, " "); - } + if (node->flags & SA_INTERRUPT) + len += sprintf(buf+len, "F "); + else + len += sprintf(buf+len, " "); len += sprintf(buf+len, "%s\n", node->devname); if ((node = node->next)) len += sprintf(buf+len, " "); diff -u --recursive --new-file v2.3.19/linux/arch/ppc/amiga/bootinfo.c linux/arch/ppc/amiga/bootinfo.c --- v2.3.19/linux/arch/ppc/amiga/bootinfo.c Tue Aug 31 17:29:12 1999 +++ linux/arch/ppc/amiga/bootinfo.c Thu Oct 7 10:17:08 1999 @@ -16,9 +16,11 @@ extern char cmd_line[CL_SIZE]; -int num_memory = 0; -struct mem_info memory[NUM_MEMINFO]; -struct mem_info ramdisk; +extern int num_memory; +extern int m68k_realnum_memory; +extern struct mem_info memory[NUM_MEMINFO]; +extern struct mem_info m68k_memory[NUM_MEMINFO]; +extern struct mem_info ramdisk; extern int amiga_parse_bootinfo(const struct bi_record *); extern int atari_parse_bootinfo(const struct bi_record *); @@ -42,6 +44,11 @@ memory[num_memory].addr = data[0]; memory[num_memory].size = data[1]; num_memory++; + + /* FIXME: duplicate for m68k drivers. */ + m68k_memory[m68k_realnum_memory].addr = data[0]; + m68k_memory[m68k_realnum_memory].size = data[1]; + m68k_realnum_memory++; } else printk("parse_bootinfo: too many memory chunks\n"); break; diff -u --recursive --new-file v2.3.19/linux/arch/ppc/amiga/chipram.c linux/arch/ppc/amiga/chipram.c --- v2.3.19/linux/arch/ppc/amiga/chipram.c Tue Aug 4 16:06:36 1998 +++ linux/arch/ppc/amiga/chipram.c Thu Oct 7 10:17:08 1999 @@ -1 +1,175 @@ -#include "../../m68k/amiga/chipram.c" +/* +** linux/amiga/chipram.c +** +** Modified 03-May-94 by Geert Uytterhoeven +** (Geert.Uytterhoeven@cs.kuleuven.ac.be) +** - 64-bit aligned allocations for full AGA compatibility +*/ + +#include +#include +#include +#include +#include + +struct chip_desc { + unsigned first : 1; + unsigned last : 1; + unsigned alloced : 1; + unsigned length : 24; + long pad; /* We suppose this makes this struct 64 bits long!! */ +}; + +#define DP(ptr) ((struct chip_desc *)(ptr)) + +u_long amiga_chip_size; +static unsigned long chipavail; + +unsigned long amiga_chip_avail( void ) +{ +#ifdef DEBUG + printk("chip_avail : %ld bytes\n",chipavail); +#endif + return chipavail; +} + + +__init +void amiga_chip_init (void) +{ + struct chip_desc *dp; + + if (!AMIGAHW_PRESENT(CHIP_RAM)) + return; + +#ifndef CONFIG_APUS_FAST_EXCEPT + /* + * Remove the first 4 pages where PPC exception handlers will + * be located. + */ + amiga_chip_size -= 0x4000; +#endif + + /* initialize start boundary */ + + dp = DP(chipaddr); + dp->first = 1; + + dp->alloced = 0; + dp->length = amiga_chip_size - 2*sizeof(*dp); + + /* initialize end boundary */ + dp = DP(chipaddr + amiga_chip_size) - 1; + dp->last = 1; + + dp->alloced = 0; + dp->length = amiga_chip_size - 2*sizeof(*dp); + chipavail = dp->length; /*MILAN*/ + +#ifdef DEBUG + printk ("chipram end boundary is %p, length is %d\n", dp, + dp->length); +#endif +} + +void *amiga_chip_alloc (long size) +{ + /* last chunk */ + struct chip_desc *dp; + void *ptr; + + /* round off */ + size = (size + 7) & ~7; + +#ifdef DEBUG + printk("chip_alloc: allocate %ld bytes\n", size); +#endif + + /* + * get pointer to descriptor for last chunk by + * going backwards from end chunk + */ + dp = DP(chipaddr + amiga_chip_size) - 1; + dp = DP((unsigned long)dp - dp->length) - 1; + + while ((dp->alloced || dp->length < size) + && !dp->first) + dp = DP ((unsigned long)dp - dp[-1].length) - 2; + + if (dp->alloced || dp->length < size) { + printk ("no chipmem available for %ld allocation\n", size); + return NULL; + } + + if (dp->length < (size + 2*sizeof(*dp))) { + /* length too small to split; allocate the whole thing */ + dp->alloced = 1; + ptr = (void *)(dp+1); + dp = DP((unsigned long)ptr + dp->length); + dp->alloced = 1; +#ifdef DEBUG + printk ("chip_alloc: no split\n"); +#endif + } else { + /* split the extent; use the end part */ + long newsize = dp->length - (2*sizeof(*dp) + size); + +#ifdef DEBUG + printk ("chip_alloc: splitting %d to %ld\n", dp->length, + newsize); +#endif + dp->length = newsize; + dp = DP((unsigned long)(dp+1) + newsize); + dp->first = dp->last = 0; + dp->alloced = 0; + dp->length = newsize; + dp++; + dp->first = dp->last = 0; + dp->alloced = 1; + dp->length = size; + ptr = (void *)(dp+1); + dp = DP((unsigned long)ptr + size); + dp->alloced = 1; + dp->length = size; + } + +#ifdef DEBUG + printk ("chip_alloc: returning %p\n", ptr); +#endif + + if ((unsigned long)ptr & 7) + panic("chip_alloc: alignment violation\n"); + + chipavail -= size + (2*sizeof(*dp)); /*MILAN*/ + + return ptr; +} + +void amiga_chip_free (void *ptr) +{ + struct chip_desc *sdp = DP(ptr) - 1, *dp2; + struct chip_desc *edp = DP((unsigned long)ptr + sdp->length); + + chipavail += sdp->length + (2* sizeof(sdp)); /*MILAN*/ +#ifdef DEBUG + printk("chip_free: free %ld bytes at %p\n",sdp->length,ptr); +#endif + /* deallocate the chunk */ + sdp->alloced = edp->alloced = 0; + + /* check if we should merge with the previous chunk */ + if (!sdp->first && !sdp[-1].alloced) { + dp2 = DP((unsigned long)sdp - sdp[-1].length) - 2; + dp2->length += sdp->length + 2*sizeof(*sdp); + edp->length = dp2->length; + sdp = dp2; + } + + /* check if we should merge with the following chunk */ + if (!edp->last && !edp[1].alloced) { + dp2 = DP((unsigned long)edp + edp[1].length) + 2; + dp2->length += edp->length + 2*sizeof(*sdp); + sdp->length = dp2->length; + edp = dp2; + } +} diff -u --recursive --new-file v2.3.19/linux/arch/ppc/amiga/config.c linux/arch/ppc/amiga/config.c --- v2.3.19/linux/arch/ppc/amiga/config.c Tue Aug 31 17:29:12 1999 +++ linux/arch/ppc/amiga/config.c Thu Oct 7 10:17:08 1999 @@ -1,13 +1,12 @@ #define m68k_debug_device debug_device -#define m68k_num_memory num_memory -#define m68k_memory memory #include /* machine dependent "kbd-reset" setup function */ -void (*kbd_reset_setup) (char *, int) __initdata = 0; +void (*mach_kbd_reset_setup) (char *, int) __initdata = 0; #include +#include /* * linux/arch/m68k/amiga/config.c @@ -41,6 +40,7 @@ #include #include +unsigned long powerup_PCI_present; unsigned long amiga_model; unsigned long amiga_eclock; unsigned long amiga_masterclock; @@ -61,7 +61,6 @@ /* amiga specific keyboard functions */ extern int amiga_keyb_init(void); extern int amiga_kbdrate (struct kbd_repeat *); -extern void amiga_kbd_reset_setup(char*, int); /* amiga specific irq functions */ extern void amiga_init_IRQ (void); extern void (*amiga_default_handler[]) (int, void *, struct pt_regs *); @@ -137,8 +136,13 @@ switch (record->tag) { case BI_AMIGA_MODEL: - amiga_model = *data; - break; + { + unsigned long d = *data; + + powerup_PCI_present = d & 0x100; + amiga_model = d & 0xff; + } + break; case BI_AMIGA_ECLOCK: amiga_eclock = *data; @@ -352,7 +356,6 @@ mach_sched_init = amiga_sched_init; mach_keyb_init = amiga_keyb_init; mach_kbdrate = amiga_kbdrate; - kbd_reset_setup = amiga_kbd_reset_setup; mach_init_IRQ = amiga_init_IRQ; mach_default_handler = &amiga_default_handler; #ifndef CONFIG_APUS @@ -451,8 +454,7 @@ * Please don't change this to use ciaa, as it interferes with the * SCSI code. We'll have to take a look at this later */ - request_irq(IRQ_AMIGA_CIAB_TA, timer_routine, IRQ_FLG_LOCK, - "timer", NULL); + request_irq(IRQ_AMIGA_CIAB_TA, timer_routine, 0, "timer", NULL); /* start timer */ ciab.cra |= 0x11; } @@ -741,7 +743,7 @@ static void amiga_serial_putc(char c) { custom.serdat = (unsigned char)c | 0x100; - iobarrier_rw (); + mb(); while (!(custom.serdatr & 0x2000)) ; } @@ -921,3 +923,30 @@ return(len); } + +#ifdef CONFIG_APUS +int get_hardware_list(char *buffer) +{ + extern int get_cpuinfo(char *buffer); + int len = 0; + char model[80]; + u_long mem; + int i; + + if (mach_get_model) + mach_get_model(model); + else + strcpy(model, "Unknown PowerPC"); + + len += sprintf(buffer+len, "Model:\t\t%s\n", model); + len += get_cpuinfo(buffer+len); + for (mem = 0, i = 0; i < m68k_realnum_memory; i++) + mem += m68k_memory[i].size; + len += sprintf(buffer+len, "System Memory:\t%ldK\n", mem>>10); + + if (mach_get_hardware_list) + len += mach_get_hardware_list(buffer+len); + + return(len); +} +#endif diff -u --recursive --new-file v2.3.19/linux/arch/ppc/amiga/ints.c linux/arch/ppc/amiga/ints.c --- v2.3.19/linux/arch/ppc/amiga/ints.c Tue Aug 31 17:29:12 1999 +++ linux/arch/ppc/amiga/ints.c Thu Oct 7 10:17:08 1999 @@ -5,19 +5,22 @@ * Needed to drive the m68k emulating IRQ hardware on the PowerUp boards. */ +#include #include +#include #include -#include #include #include #include +#include #include #include +#include #include /* table for system interrupt handlers */ -irq_handler_t irq_list[SYS_IRQS]; +static irq_handler_t irq_list[SYS_IRQS]; static const char *default_names[SYS_IRQS] = { "spurious int", "int1 handler", "int2 handler", "int3 handler", @@ -42,14 +45,15 @@ * the IRQ handling routines. */ -void __init apus_init_IRQ(void) +__init +void m68k_init_IRQ(void) { int i; for (i = 0; i < SYS_IRQS; i++) { if (mach_default_handler) irq_list[i].handler = (*mach_default_handler)[i]; - irq_list[i].flags = IRQ_FLG_STD; + irq_list[i].flags = 0; irq_list[i].dev_id = NULL; irq_list[i].devname = default_names[i]; } @@ -83,6 +87,7 @@ return -ENXIO; } +#if 0 if (!(irq_list[irq].flags & IRQ_FLG_STD)) { if (irq_list[irq].flags & IRQ_FLG_LOCK) { printk("%s: IRQ %d from %s is not replaceable\n", @@ -95,6 +100,8 @@ return -EBUSY; } } +#endif + irq_list[irq].handler = handler; irq_list[irq].flags = flags; irq_list[irq].dev_id = dev_id; @@ -114,7 +121,7 @@ __FUNCTION__, irq, irq_list[irq].devname); irq_list[irq].handler = (*mach_default_handler)[irq]; - irq_list[irq].flags = IRQ_FLG_STD; + irq_list[irq].flags = 0; irq_list[irq].dev_id = NULL; irq_list[irq].devname = default_names[irq]; } @@ -134,7 +141,7 @@ } } -int get_irq_list(char *buf) +int m68k_get_irq_list(char *buf) { int i, len = 0; @@ -143,9 +150,6 @@ for (i = 0; i < SYS_IRQS; i++) { len += sprintf(buf+len, "auto %2d: %10u ", i, i ? kstat.irqs[0][i] : num_spurious); - if (irq_list[i].flags & IRQ_FLG_LOCK) - len += sprintf(buf+len, "L "); - else len += sprintf(buf+len, " "); len += sprintf(buf+len, "%s\n", irq_list[i].devname); } diff -u --recursive --new-file v2.3.19/linux/arch/ppc/amiga/pcmcia.c linux/arch/ppc/amiga/pcmcia.c --- v2.3.19/linux/arch/ppc/amiga/pcmcia.c Wed Dec 31 16:00:00 1969 +++ linux/arch/ppc/amiga/pcmcia.c Thu Oct 7 10:17:08 1999 @@ -0,0 +1 @@ +#include "../../m68k/amiga/pcmcia.c" diff -u --recursive --new-file v2.3.19/linux/arch/ppc/amiga/time.c linux/arch/ppc/amiga/time.c --- v2.3.19/linux/arch/ppc/amiga/time.c Sun Nov 15 10:51:41 1998 +++ linux/arch/ppc/amiga/time.c Thu Oct 7 10:17:08 1999 @@ -15,7 +15,7 @@ unsigned int day, unsigned int hour, unsigned int min, unsigned int sec); -unsigned long apus_get_rtc_time(void) +unsigned long m68k_get_rtc_time(void) { unsigned int year, mon, day, hour, min, sec; @@ -30,7 +30,7 @@ return mktime(year, mon, day, hour, min, sec); } -int apus_set_rtc_time(unsigned long nowtime) +int m68k_set_rtc_time(unsigned long nowtime) { if (mach_set_clock_mmss) return mach_set_clock_mmss (nowtime); @@ -89,4 +89,6 @@ dist = period / 4; } #endif + /* should be made smarter */ + ppc_md.heartbeat_count = 1; } diff -u --recursive --new-file v2.3.19/linux/arch/ppc/boot/Makefile linux/arch/ppc/boot/Makefile --- v2.3.19/linux/arch/ppc/boot/Makefile Fri Sep 10 23:57:27 1999 +++ linux/arch/ppc/boot/Makefile Thu Oct 7 10:17:08 1999 @@ -25,6 +25,10 @@ IOFF = 0 ISZ = 0 +ifeq ($(CONFIG_ALL_PPC),y) +CONFIG_PREP=y +endif + ifeq ($(CONFIG_SMP),y) TFTPIMAGE=/tftpboot/zImage.prep.smp$(MSIZE) else @@ -72,16 +76,19 @@ rm zvmlinux.initrd.tmp zImage: zvmlinux mkprep sImage +ifdef CONFIG_PREP ./mkprep -pbp zvmlinux zImage +endif sImage: ../../../vmlinux ifdef CONFIG_GEMINI $(OBJCOPY) -I elf32-powerpc -O binary ../../../vmlinux sImage -else endif zImage.initrd: zvmlinux.initrd mkprep +ifdef CONFIG_PREP ./mkprep -pbp zvmlinux.initrd zImage.initrd +endif zvmlinux: $(OBJECTS) ../coffboot/vmlinux.gz # @@ -110,7 +117,9 @@ $(HOSTCC) -o mkprep mkprep.c znetboot : zImage +ifdef CONFIG_PREP cp zImage $(TFTPIMAGE) +endif ifdef CONFIG_GEMINI cp sImage /tftpboot/ endif diff -u --recursive --new-file v2.3.19/linux/arch/ppc/common_defconfig linux/arch/ppc/common_defconfig --- v2.3.19/linux/arch/ppc/common_defconfig Tue Aug 31 17:29:12 1999 +++ linux/arch/ppc/common_defconfig Thu Oct 7 10:17:08 1999 @@ -1,5 +1,5 @@ # -# Automatically generated make config: don't edit +# Automatically generated by make menuconfig: don't edit # # @@ -13,6 +13,7 @@ # CONFIG_PREP is not set # CONFIG_CHRP is not set CONFIG_ALL_PPC=y +# CONFIG_GEMINI is not set # CONFIG_APUS is not set # CONFIG_MBX is not set # CONFIG_SMP is not set @@ -26,8 +27,6 @@ CONFIG_MODVERSIONS=y CONFIG_KMOD=y CONFIG_PCI=y -# CONFIG_PCI_QUIRKS is not set -CONFIG_PCI_OLD_PROC=y CONFIG_NET=y CONFIG_SYSCTL=y CONFIG_SYSVIPC=y @@ -40,9 +39,14 @@ CONFIG_FB=y CONFIG_FB_COMPAT_XPMAC=y CONFIG_PMAC_PBOOK=y -CONFIG_MAC_KEYBOARD=y CONFIG_MAC_FLOPPY=y CONFIG_MAC_SERIAL=y +# CONFIG_SERIAL_CONSOLE is not set +CONFIG_ADB=y +CONFIG_ADB_CUDA=y +CONFIG_ADB_MACIO=y +CONFIG_ADB_PMU=y +CONFIG_ADB_KEYBOARD=y CONFIG_PROC_DEVICETREE=y # CONFIG_TOTALMP is not set CONFIG_BOOTX_TEXT=y @@ -50,14 +54,16 @@ # CONFIG_CMDLINE_BOOL is not set # -# Block devices +# Plug and Play configuration # -CONFIG_BLK_DEV_FD=y -CONFIG_BLK_DEV_IDE=y +# CONFIG_PNP is not set +# CONFIG_ISAPNP is not set # -# Please see Documentation/ide.txt for help/info on IDE drives +# Block devices # +CONFIG_BLK_DEV_FD=y +CONFIG_BLK_DEV_IDE=y # CONFIG_BLK_DEV_HD_IDE is not set CONFIG_BLK_DEV_IDEDISK=y # CONFIG_IDEDISK_MULTI_MODE is not set @@ -77,10 +83,6 @@ CONFIG_IDEDMA_AUTO=y # CONFIG_IDE_CHIPSETS is not set # CONFIG_BLK_CPQ_DA is not set - -# -# Additional Block Devices -# CONFIG_BLK_DEV_LOOP=y # CONFIG_BLK_DEV_NBD is not set # CONFIG_BLK_DEV_MD is not set @@ -96,10 +98,11 @@ # Networking options # CONFIG_PACKET=y +# CONFIG_PACKET_MMAP is not set CONFIG_NETLINK=y # CONFIG_RTNETLINK is not set # CONFIG_NETLINK_DEV is not set -# CONFIG_FIREWALL is not set +# CONFIG_NETFILTER is not set # CONFIG_FILTER is not set CONFIG_UNIX=y CONFIG_INET=y @@ -112,17 +115,10 @@ # CONFIG_IP_MROUTE is not set CONFIG_IP_ALIAS=y CONFIG_SYN_COOKIES=y - -# -# (it is safe to leave these untouched) -# -CONFIG_INET_RARP=y CONFIG_SKB_LARGE=y # CONFIG_IPV6 is not set - -# -# -# +# CONFIG_KHTTPD is not set +# CONFIG_ATM is not set # CONFIG_IPX is not set CONFIG_ATALK=m # CONFIG_DECNET is not set @@ -134,7 +130,6 @@ # CONFIG_WAN_ROUTER is not set # CONFIG_NET_FASTROUTE is not set # CONFIG_NET_HW_FLOWCONTROL is not set -# CONFIG_CPU_IS_SLOW is not set # # QoS and/or fair queueing @@ -145,19 +140,11 @@ # SCSI support # CONFIG_SCSI=y - -# -# SCSI support type (disk, tape, CD-ROM) -# CONFIG_BLK_DEV_SD=y CONFIG_CHR_DEV_ST=y CONFIG_BLK_DEV_SR=y CONFIG_BLK_DEV_SR_VENDOR=y # CONFIG_CHR_DEV_SG is not set - -# -# Some SCSI devices (e.g. CD jukebox) support multiple LUNs -# # CONFIG_SCSI_MULTI_LUN is not set CONFIG_SCSI_CONSTANTS=y # CONFIG_SCSI_LOGGING is not set @@ -175,6 +162,7 @@ CONFIG_AIC7XXX_CMDS_PER_DEVICE=8 CONFIG_AIC7XXX_PROC_STATS=y CONFIG_AIC7XXX_RESET_DELAY=15 +# CONFIG_SCSI_IPS is not set # CONFIG_SCSI_ADVANSYS is not set # CONFIG_SCSI_IN2000 is not set # CONFIG_SCSI_AM53C974 is not set @@ -187,8 +175,6 @@ # CONFIG_SCSI_FUTURE_DOMAIN is not set # CONFIG_SCSI_GDTH is not set # CONFIG_SCSI_GENERIC_NCR5380 is not set -# CONFIG_SCSI_G_NCR5380_PORT is not set -# CONFIG_SCSI_G_NCR5380_MEM is not set # CONFIG_SCSI_INITIO is not set # CONFIG_SCSI_INIA100 is not set # CONFIG_SCSI_NCR53C406A is not set @@ -232,6 +218,7 @@ # CONFIG_DUMMY is not set # CONFIG_EQUALIZER is not set # CONFIG_ETHERTAP is not set +# CONFIG_NET_SB1000 is not set # # Ethernet (10 or 100Mbit) @@ -244,11 +231,12 @@ # CONFIG_NET_VENDOR_SMC is not set # CONFIG_NET_VENDOR_RACAL is not set # CONFIG_RTL8139 is not set +# CONFIG_SIS900 is not set # CONFIG_YELLOWFIN is not set +# CONFIG_ACENIC is not set # CONFIG_NET_ISA is not set CONFIG_NET_EISA=y CONFIG_PCNET32=y -# CONFIG_ACENIC is not set # CONFIG_AC3200 is not set # CONFIG_APRICOT is not set # CONFIG_CS89x0 is not set @@ -264,6 +252,7 @@ # CONFIG_ES3210 is not set # CONFIG_EPIC100 is not set # CONFIG_ZNET is not set +# CONFIG_ADAPTEC_STARFIRE is not set # CONFIG_NET_POCKET is not set # CONFIG_FDDI is not set # CONFIG_HIPPI is not set @@ -275,10 +264,9 @@ # CONFIG_COPS is not set # CONFIG_IPDDP is not set CONFIG_PPP=y - -# -# CCP compressors for PPP are only built as modules. -# +# CONFIG_PPP_ASYNC is not set +# CONFIG_PPP_DEFLATE is not set +# CONFIG_PPP_BSDCOMP is not set # CONFIG_SLIP is not set # CONFIG_NET_RADIO is not set @@ -286,6 +274,7 @@ # Token ring devices # # CONFIG_TR is not set +# CONFIG_NET_FC is not set # CONFIG_RCPCI is not set # CONFIG_SHAPER is not set @@ -298,6 +287,13 @@ # CONFIG_DLCI is not set # +# PCMCIA network devices +# +# CONFIG_PCMCIA_PCNET is not set +# CONFIG_PCMCIA_3C589 is not set +# CONFIG_PCMCIA_RAYCS is not set + +# # Amateur Radio support # # CONFIG_HAMRADIO is not set @@ -316,21 +312,22 @@ # Console drivers # CONFIG_DUMMY_CONSOLE=y +# CONFIG_FB_CLGEN is not set # CONFIG_FB_PM2 is not set CONFIG_FB_OF=y CONFIG_FB_CONTROL=y CONFIG_FB_PLATINUM=y CONFIG_FB_VALKYRIE=y -# CONFIG_FB_ATY is not set CONFIG_FB_IMSTT=y CONFIG_FB_CT65550=y # CONFIG_FB_S3TRIO is not set +# CONFIG_FB_VGA16 is not set CONFIG_FB_MATROX=y # CONFIG_FB_MATROX_MILLENIUM is not set CONFIG_FB_MATROX_MYSTIQUE=y CONFIG_FB_MATROX_G100=y # CONFIG_FB_MATROX_MULTIHEAD is not set -# CONFIG_FB_ATY is not set +CONFIG_FB_ATY=y # CONFIG_FB_VIRTUAL is not set # CONFIG_FBCON_ADVANCED is not set CONFIG_FBCON_CFB8=y @@ -365,7 +362,7 @@ # CONFIG_ATIXL_BUSMOUSE is not set # CONFIG_LOGIBUSMOUSE is not set # CONFIG_MS_BUSMOUSE is not set -CONFIG_ADBMOUSE=y +# CONFIG_ADB_MOUSE is not set CONFIG_MOUSE=y CONFIG_PSMOUSE=y # CONFIG_82C710_MOUSE is not set @@ -385,19 +382,14 @@ # # CONFIG_JOYSTICK is not set # CONFIG_DTLK is not set +# CONFIG_R3964 is not set +# CONFIG_APPLICOM is not set # # Ftape, the floppy tape device driver # # CONFIG_FTAPE is not set -# CONFIG_FT_NORMAL_DEBUG is not set -# CONFIG_FT_FULL_DEBUG is not set -# CONFIG_FT_NO_TRACE is not set -# CONFIG_FT_NO_TRACE_AT_ALL is not set -# CONFIG_FT_STD_FDC is not set -# CONFIG_FT_MACH2 is not set -# CONFIG_FT_PROBE_FC10 is not set -# CONFIG_FT_ALT_FDC is not set +# CONFIG_DRM is not set # # USB drivers - not for the faint of heart @@ -413,9 +405,13 @@ # 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_EFS_FS is not set CONFIG_ISO9660_FS=y # CONFIG_JOLIET is not set +# CONFIG_UDF_FS is not set # CONFIG_MINIX_FS is not set # CONFIG_NTFS_FS is not set # CONFIG_HPFS_FS is not set @@ -442,12 +438,14 @@ # # Partition Types # -# CONFIG_BSD_DISKLABEL is not set +# CONFIG_PARTITION_ADVANCED is not set CONFIG_MAC_PARTITION=y -# CONFIG_SMD_DISKLABEL is not set +CONFIG_MSDOS_PARTITION=y +# CONFIG_BSD_DISKLABEL is not set # CONFIG_SOLARIS_X86_PARTITION is not set -# CONFIG_SGI_DISKLABEL is not set # CONFIG_UNIXWARE_DISKLABEL is not set +# CONFIG_SGI_PARTITION is not set +# CONFIG_SUN_PARTITION is not set # CONFIG_NLS is not set # @@ -458,6 +456,8 @@ # CONFIG_SOUND_CMPCI is not set # CONFIG_SOUND_ES1370 is not set # CONFIG_SOUND_ES1371 is not set +# CONFIG_SOUND_ESSSOLO1 is not set +# CONFIG_SOUND_MAESTRO is not set # CONFIG_SOUND_SONICVIBES is not set # CONFIG_SOUND_MSNDCLAS is not set # CONFIG_SOUND_MSNDPIN is not set @@ -472,6 +472,7 @@ # CONFIG_SOUND_MSS is not set # CONFIG_SOUND_SSCAPE is not set # CONFIG_SOUND_TRIX is not set +# CONFIG_SOUND_VIA82CXXX is not set # CONFIG_SOUND_MAD16 is not set # CONFIG_SOUND_WAVEFRONT is not set CONFIG_SOUND_CS4232=m diff -u --recursive --new-file v2.3.19/linux/arch/ppc/config.in linux/arch/ppc/config.in --- v2.3.19/linux/arch/ppc/config.in Fri Sep 10 23:57:27 1999 +++ linux/arch/ppc/config.in Thu Oct 7 10:17:08 1999 @@ -1,4 +1,4 @@ -# $Id: config.in,v 1.103 1999/09/01 19:04:44 cort Exp $ +# $Id: config.in,v 1.106 1999/09/14 19:21:18 cort Exp $ # For a description of the syntax of this configuration file, # see the Configure script. # @@ -10,16 +10,33 @@ choice 'Processor type' \ "6xx/7xx CONFIG_6xx \ 630/Power3(64-Bit) CONFIG_PPC64 \ - 860/821 CONFIG_8xx" 6xx/7xx + 82xx CONFIG_82xx \ + 8xx CONFIG_8xx" 6xx/7xx -choice 'Machine Type' \ +if [ "$CONFIG_8xx" = "y" ]; then + choice 'Processor Model' \ + "821 CONFIG_MPC821 \ + 823 CONFIG_MPC823 \ + 850 CONFIG_MPC850 \ + 855 CONFIG_MPC855 \ + 860 CONFIG_MPC860 \ + 860T CONFIG_MPC860T" 860 + define_bool CONFIG_SERIAL_CONSOLE y + choice 'Machine Type' \ + "RPX-Lite CONFIG_RPXLITE \ + RPX-Classic CONFIG_RPXCLASSIC \ + BSE-IP CONFIG_BSEIP \ + MBX CONFIG_MBX \ + WinCept CONFIG_WINCEPT" RPX-Lite +else + choice 'Machine Type' \ "PowerMac CONFIG_PMAC \ PReP/MTX CONFIG_PREP \ CHRP CONFIG_CHRP \ PowerMac/PReP/CHRP CONFIG_ALL_PPC \ Gemini CONFIG_GEMINI \ - APUS CONFIG_APUS \ - MBX CONFIG_MBX" PowerMac + APUS CONFIG_APUS" PowerMac +fi bool 'Symmetric multi-processing support' CONFIG_SMP if [ "$CONFIG_ALL_PPC" != "y" ];then @@ -35,10 +52,6 @@ fi endmenu -if [ "$CONFIG_MBX" = "y" ];then - define_bool CONFIG_SERIAL_CONSOLE y -fi - mainmenu_option next_comment comment 'General setup' @@ -52,7 +65,11 @@ if [ "$CONFIG_APUS" = "y" ]; then define_bool CONFIG_PCI n else - define_bool CONFIG_PCI y + if [ "$CONFIG_8xx" = "y" ]; then + bool 'QSpan PCI' CONFIG_PCI + else + define_bool CONFIG_PCI y + fi fi bool 'Networking support' CONFIG_NET @@ -67,23 +84,32 @@ source drivers/parport/Config.in -bool 'Support for VGA Console' CONFIG_VGA_CONSOLE -bool 'Support for frame buffer devices' CONFIG_FB -if [ "$CONFIG_FB" = "y" ]; then - bool 'Backward compatibility mode for Xpmac' CONFIG_FB_COMPAT_XPMAC -fi - -bool 'Power management support for PowerBook 3400/2400' CONFIG_PMAC_PBOOK -bool 'Support for PowerMac keyboard' CONFIG_MAC_KEYBOARD -bool 'Support for PowerMac floppy' CONFIG_MAC_FLOPPY -tristate 'Support for PowerMac serial ports' CONFIG_MAC_SERIAL -if [ "$CONFIG_MAC_SERIAL" = "y" ]; then - bool ' Support for console on serial port' CONFIG_SERIAL_CONSOLE -fi -bool 'Support for Open Firmware device tree in /proc' CONFIG_PROC_DEVICETREE -bool 'Support for TotalImpact TotalMP' CONFIG_TOTALMP -bool 'Support for early boot text console (BootX only)' CONFIG_BOOTX_TEXT -bool 'Support for Motorola Hot Swap' CONFIG_MOTOROLA_HOTSWAP +if [ "$CONFIG_8xx" != "y" ]; then + bool 'Support for VGA Console' CONFIG_VGA_CONSOLE + bool 'Support for frame buffer devices' CONFIG_FB + if [ "$CONFIG_FB" = "y" ]; then + bool 'Backward compatibility mode for Xpmac' CONFIG_FB_COMPAT_XPMAC + fi + + bool 'Power management support for PowerBooks' CONFIG_PMAC_PBOOK + bool 'Support for PowerMac floppy' CONFIG_MAC_FLOPPY + tristate 'Support for PowerMac serial ports' CONFIG_MAC_SERIAL + if [ "$CONFIG_MAC_SERIAL" = "y" ]; then + bool ' Support for console on serial port' CONFIG_SERIAL_CONSOLE + fi + bool 'Apple Desktop Bus (ADB) support' CONFIG_ADB + if [ "$CONFIG_ADB" = "y" ]; then + bool ' Include CUDA ADB driver' CONFIG_ADB_CUDA + bool ' Include MacIO ADB driver' CONFIG_ADB_MACIO + bool ' Include PMU (Powerbook) ADB driver' CONFIG_ADB_PMU + bool 'Support for ADB keyboard' CONFIG_ADB_KEYBOARD + fi + bool 'Support for Open Firmware device tree in /proc' CONFIG_PROC_DEVICETREE + bool 'Support for TotalImpact TotalMP' CONFIG_TOTALMP + bool 'Support for early boot text console (BootX only)' CONFIG_BOOTX_TEXT + bool 'Support for Motorola Hot Swap' CONFIG_MOTOROLA_HOTSWAP +fi + if [ "$CONFIG_PREP" = "y" -o "$CONFIG_ALL_PPC" = "y" ]; then bool 'PReP bootloader kernel arguments' CONFIG_CMDLINE_BOOL y if [ "$CONFIG_CMDLINE_BOOL" = "y" ] ; then @@ -182,6 +208,10 @@ fi endmenu + +if [ "$CONFIG_8xx" = "y" ]; then +source arch/ppc/8xx_io/Config.in +fi mainmenu_option next_comment comment 'Kernel hacking' diff -u --recursive --new-file v2.3.19/linux/arch/ppc/defconfig linux/arch/ppc/defconfig --- v2.3.19/linux/arch/ppc/defconfig Tue Aug 31 17:29:12 1999 +++ linux/arch/ppc/defconfig Thu Oct 7 10:17:08 1999 @@ -1,5 +1,5 @@ # -# Automatically generated make config: don't edit +# Automatically generated by make menuconfig: don't edit # # @@ -13,6 +13,7 @@ # CONFIG_PREP is not set # CONFIG_CHRP is not set CONFIG_ALL_PPC=y +# CONFIG_GEMINI is not set # CONFIG_APUS is not set # CONFIG_MBX is not set # CONFIG_SMP is not set @@ -26,8 +27,6 @@ CONFIG_MODVERSIONS=y CONFIG_KMOD=y CONFIG_PCI=y -# CONFIG_PCI_QUIRKS is not set -CONFIG_PCI_OLD_PROC=y CONFIG_NET=y CONFIG_SYSCTL=y CONFIG_SYSVIPC=y @@ -40,9 +39,14 @@ CONFIG_FB=y CONFIG_FB_COMPAT_XPMAC=y CONFIG_PMAC_PBOOK=y -CONFIG_MAC_KEYBOARD=y CONFIG_MAC_FLOPPY=y CONFIG_MAC_SERIAL=y +# CONFIG_SERIAL_CONSOLE is not set +CONFIG_ADB=y +CONFIG_ADB_CUDA=y +CONFIG_ADB_MACIO=y +CONFIG_ADB_PMU=y +CONFIG_ADB_KEYBOARD=y CONFIG_PROC_DEVICETREE=y # CONFIG_TOTALMP is not set CONFIG_BOOTX_TEXT=y @@ -50,14 +54,16 @@ # CONFIG_CMDLINE_BOOL is not set # -# Block devices +# Plug and Play configuration # -CONFIG_BLK_DEV_FD=y -CONFIG_BLK_DEV_IDE=y +# CONFIG_PNP is not set +# CONFIG_ISAPNP is not set # -# Please see Documentation/ide.txt for help/info on IDE drives +# Block devices # +CONFIG_BLK_DEV_FD=y +CONFIG_BLK_DEV_IDE=y # CONFIG_BLK_DEV_HD_IDE is not set CONFIG_BLK_DEV_IDEDISK=y # CONFIG_IDEDISK_MULTI_MODE is not set @@ -77,10 +83,6 @@ CONFIG_IDEDMA_AUTO=y # CONFIG_IDE_CHIPSETS is not set # CONFIG_BLK_CPQ_DA is not set - -# -# Additional Block Devices -# CONFIG_BLK_DEV_LOOP=y # CONFIG_BLK_DEV_NBD is not set # CONFIG_BLK_DEV_MD is not set @@ -96,10 +98,11 @@ # Networking options # CONFIG_PACKET=y +# CONFIG_PACKET_MMAP is not set CONFIG_NETLINK=y # CONFIG_RTNETLINK is not set # CONFIG_NETLINK_DEV is not set -# CONFIG_FIREWALL is not set +# CONFIG_NETFILTER is not set # CONFIG_FILTER is not set CONFIG_UNIX=y CONFIG_INET=y @@ -112,17 +115,10 @@ # CONFIG_IP_MROUTE is not set CONFIG_IP_ALIAS=y CONFIG_SYN_COOKIES=y - -# -# (it is safe to leave these untouched) -# -CONFIG_INET_RARP=y CONFIG_SKB_LARGE=y # CONFIG_IPV6 is not set - -# -# -# +# CONFIG_KHTTPD is not set +# CONFIG_ATM is not set # CONFIG_IPX is not set CONFIG_ATALK=m # CONFIG_DECNET is not set @@ -134,7 +130,6 @@ # CONFIG_WAN_ROUTER is not set # CONFIG_NET_FASTROUTE is not set # CONFIG_NET_HW_FLOWCONTROL is not set -# CONFIG_CPU_IS_SLOW is not set # # QoS and/or fair queueing @@ -145,19 +140,11 @@ # SCSI support # CONFIG_SCSI=y - -# -# SCSI support type (disk, tape, CD-ROM) -# CONFIG_BLK_DEV_SD=y CONFIG_CHR_DEV_ST=y CONFIG_BLK_DEV_SR=y CONFIG_BLK_DEV_SR_VENDOR=y # CONFIG_CHR_DEV_SG is not set - -# -# Some SCSI devices (e.g. CD jukebox) support multiple LUNs -# # CONFIG_SCSI_MULTI_LUN is not set CONFIG_SCSI_CONSTANTS=y # CONFIG_SCSI_LOGGING is not set @@ -175,6 +162,7 @@ CONFIG_AIC7XXX_CMDS_PER_DEVICE=8 CONFIG_AIC7XXX_PROC_STATS=y CONFIG_AIC7XXX_RESET_DELAY=15 +# CONFIG_SCSI_IPS is not set # CONFIG_SCSI_ADVANSYS is not set # CONFIG_SCSI_IN2000 is not set # CONFIG_SCSI_AM53C974 is not set @@ -187,8 +175,6 @@ # CONFIG_SCSI_FUTURE_DOMAIN is not set # CONFIG_SCSI_GDTH is not set # CONFIG_SCSI_GENERIC_NCR5380 is not set -# CONFIG_SCSI_G_NCR5380_PORT is not set -# CONFIG_SCSI_G_NCR5380_MEM is not set # CONFIG_SCSI_INITIO is not set # CONFIG_SCSI_INIA100 is not set # CONFIG_SCSI_NCR53C406A is not set @@ -232,6 +218,7 @@ # CONFIG_DUMMY is not set # CONFIG_EQUALIZER is not set # CONFIG_ETHERTAP is not set +# CONFIG_NET_SB1000 is not set # # Ethernet (10 or 100Mbit) @@ -244,11 +231,12 @@ # CONFIG_NET_VENDOR_SMC is not set # CONFIG_NET_VENDOR_RACAL is not set # CONFIG_RTL8139 is not set +# CONFIG_SIS900 is not set # CONFIG_YELLOWFIN is not set +# CONFIG_ACENIC is not set # CONFIG_NET_ISA is not set CONFIG_NET_EISA=y CONFIG_PCNET32=y -# CONFIG_ACENIC is not set # CONFIG_AC3200 is not set # CONFIG_APRICOT is not set # CONFIG_CS89x0 is not set @@ -264,6 +252,7 @@ # CONFIG_ES3210 is not set # CONFIG_EPIC100 is not set # CONFIG_ZNET is not set +# CONFIG_ADAPTEC_STARFIRE is not set # CONFIG_NET_POCKET is not set # CONFIG_FDDI is not set # CONFIG_HIPPI is not set @@ -275,10 +264,9 @@ # CONFIG_COPS is not set # CONFIG_IPDDP is not set CONFIG_PPP=y - -# -# CCP compressors for PPP are only built as modules. -# +# CONFIG_PPP_ASYNC is not set +# CONFIG_PPP_DEFLATE is not set +# CONFIG_PPP_BSDCOMP is not set # CONFIG_SLIP is not set # CONFIG_NET_RADIO is not set @@ -286,6 +274,7 @@ # Token ring devices # # CONFIG_TR is not set +# CONFIG_NET_FC is not set # CONFIG_RCPCI is not set # CONFIG_SHAPER is not set @@ -298,6 +287,13 @@ # CONFIG_DLCI is not set # +# PCMCIA network devices +# +# CONFIG_PCMCIA_PCNET is not set +# CONFIG_PCMCIA_3C589 is not set +# CONFIG_PCMCIA_RAYCS is not set + +# # Amateur Radio support # # CONFIG_HAMRADIO is not set @@ -316,21 +312,22 @@ # Console drivers # CONFIG_DUMMY_CONSOLE=y +# CONFIG_FB_CLGEN is not set # CONFIG_FB_PM2 is not set CONFIG_FB_OF=y CONFIG_FB_CONTROL=y CONFIG_FB_PLATINUM=y CONFIG_FB_VALKYRIE=y -# CONFIG_FB_ATY is not set CONFIG_FB_IMSTT=y CONFIG_FB_CT65550=y # CONFIG_FB_S3TRIO is not set +# CONFIG_FB_VGA16 is not set CONFIG_FB_MATROX=y # CONFIG_FB_MATROX_MILLENIUM is not set CONFIG_FB_MATROX_MYSTIQUE=y CONFIG_FB_MATROX_G100=y # CONFIG_FB_MATROX_MULTIHEAD is not set -# CONFIG_FB_ATY is not set +CONFIG_FB_ATY=y # CONFIG_FB_VIRTUAL is not set # CONFIG_FBCON_ADVANCED is not set CONFIG_FBCON_CFB8=y @@ -365,7 +362,7 @@ # CONFIG_ATIXL_BUSMOUSE is not set # CONFIG_LOGIBUSMOUSE is not set # CONFIG_MS_BUSMOUSE is not set -CONFIG_ADBMOUSE=y +# CONFIG_ADB_MOUSE is not set CONFIG_MOUSE=y CONFIG_PSMOUSE=y # CONFIG_82C710_MOUSE is not set @@ -385,19 +382,14 @@ # # CONFIG_JOYSTICK is not set # CONFIG_DTLK is not set +# CONFIG_R3964 is not set +# CONFIG_APPLICOM is not set # # Ftape, the floppy tape device driver # # CONFIG_FTAPE is not set -# CONFIG_FT_NORMAL_DEBUG is not set -# CONFIG_FT_FULL_DEBUG is not set -# CONFIG_FT_NO_TRACE is not set -# CONFIG_FT_NO_TRACE_AT_ALL is not set -# CONFIG_FT_STD_FDC is not set -# CONFIG_FT_MACH2 is not set -# CONFIG_FT_PROBE_FC10 is not set -# CONFIG_FT_ALT_FDC is not set +# CONFIG_DRM is not set # # USB drivers - not for the faint of heart @@ -413,9 +405,13 @@ # 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_EFS_FS is not set CONFIG_ISO9660_FS=y # CONFIG_JOLIET is not set +# CONFIG_UDF_FS is not set # CONFIG_MINIX_FS is not set # CONFIG_NTFS_FS is not set # CONFIG_HPFS_FS is not set @@ -442,12 +438,14 @@ # # Partition Types # -# CONFIG_BSD_DISKLABEL is not set +# CONFIG_PARTITION_ADVANCED is not set CONFIG_MAC_PARTITION=y -# CONFIG_SMD_DISKLABEL is not set +CONFIG_MSDOS_PARTITION=y +# CONFIG_BSD_DISKLABEL is not set # CONFIG_SOLARIS_X86_PARTITION is not set -# CONFIG_SGI_DISKLABEL is not set # CONFIG_UNIXWARE_DISKLABEL is not set +# CONFIG_SGI_PARTITION is not set +# CONFIG_SUN_PARTITION is not set # CONFIG_NLS is not set # @@ -458,6 +456,8 @@ # CONFIG_SOUND_CMPCI is not set # CONFIG_SOUND_ES1370 is not set # CONFIG_SOUND_ES1371 is not set +# CONFIG_SOUND_ESSSOLO1 is not set +# CONFIG_SOUND_MAESTRO is not set # CONFIG_SOUND_SONICVIBES is not set # CONFIG_SOUND_MSNDCLAS is not set # CONFIG_SOUND_MSNDPIN is not set @@ -472,6 +472,7 @@ # CONFIG_SOUND_MSS is not set # CONFIG_SOUND_SSCAPE is not set # CONFIG_SOUND_TRIX is not set +# CONFIG_SOUND_VIA82CXXX is not set # CONFIG_SOUND_MAD16 is not set # CONFIG_SOUND_WAVEFRONT is not set CONFIG_SOUND_CS4232=m diff -u --recursive --new-file v2.3.19/linux/arch/ppc/gemini_defconfig linux/arch/ppc/gemini_defconfig --- v2.3.19/linux/arch/ppc/gemini_defconfig Fri Sep 10 23:57:28 1999 +++ linux/arch/ppc/gemini_defconfig Thu Oct 7 10:17:08 1999 @@ -1,5 +1,5 @@ # -# Automatically generated by make menuconfig: don't edit +# Automatically generated make config: don't edit # # @@ -8,14 +8,25 @@ CONFIG_PPC=y CONFIG_6xx=y # CONFIG_PPC64 is not set +# CONFIG_82xx is not set # CONFIG_8xx is not set +# CONFIG_MPC821 is not set +# CONFIG_MPC823 is not set +# CONFIG_MPC850 is not set +# CONFIG_MPC855 is not set +# CONFIG_MPC860 is not set +# CONFIG_MPC860T is not set +# CONFIG_RPXLITE is not set +# CONFIG_RPXCLASSIC is not set +# CONFIG_BSEIP is not set +# CONFIG_MBX is not set +# CONFIG_WINCEPT is not set # CONFIG_PMAC is not set # CONFIG_PREP is not set # CONFIG_CHRP is not set # CONFIG_ALL_PPC is not set CONFIG_GEMINI=y # CONFIG_APUS is not set -# CONFIG_MBX is not set # CONFIG_SMP is not set CONFIG_MACH_SPECIFIC=y CONFIG_6xx=y @@ -39,9 +50,9 @@ # CONFIG_VGA_CONSOLE is not set # CONFIG_FB is not set # CONFIG_PMAC_PBOOK is not set -CONFIG_MAC_KEYBOARD=y # CONFIG_MAC_FLOPPY is not set # CONFIG_MAC_SERIAL is not set +# CONFIG_ADB is not set # CONFIG_PROC_DEVICETREE is not set # CONFIG_TOTALMP is not set # CONFIG_BOOTX_TEXT is not set @@ -51,15 +62,22 @@ # Plug and Play configuration # # CONFIG_PNP is not set -# CONFIG_ISAPNP is not set # # Block devices # # CONFIG_BLK_DEV_FD is not set # CONFIG_BLK_DEV_IDE is not set + +# +# Please see Documentation/ide.txt for help/info on IDE drives +# # CONFIG_BLK_DEV_HD_ONLY is not set # CONFIG_BLK_CPQ_DA is not set + +# +# Additional Block Devices +# # CONFIG_BLK_DEV_LOOP is not set # CONFIG_BLK_DEV_NBD is not set # CONFIG_BLK_DEV_MD is not set @@ -91,10 +109,18 @@ # CONFIG_IP_MROUTE is not set CONFIG_IP_ALIAS=y CONFIG_SYN_COOKIES=y + +# +# (it is safe to leave these untouched) +# CONFIG_SKB_LARGE=y # CONFIG_IPV6 is not set # CONFIG_KHTTPD is not set # CONFIG_ATM is not set + +# +# +# # CONFIG_IPX is not set # CONFIG_ATALK is not set # CONFIG_DECNET is not set @@ -116,11 +142,19 @@ # SCSI support # CONFIG_SCSI=y + +# +# SCSI support type (disk, tape, CD-ROM) +# CONFIG_BLK_DEV_SD=y # CONFIG_CHR_DEV_ST is not set CONFIG_BLK_DEV_SR=y CONFIG_BLK_DEV_SR_VENDOR=y # CONFIG_CHR_DEV_SG is not set + +# +# Some SCSI devices (e.g. CD jukebox) support multiple LUNs +# # CONFIG_SCSI_MULTI_LUN is not set CONFIG_SCSI_CONSTANTS=y # CONFIG_SCSI_LOGGING is not set @@ -147,6 +181,8 @@ # CONFIG_SCSI_FUTURE_DOMAIN is not set # CONFIG_SCSI_GDTH is not set # CONFIG_SCSI_GENERIC_NCR5380 is not set +# CONFIG_SCSI_G_NCR5380_PORT is not set +# CONFIG_SCSI_G_NCR5380_MEM is not set # CONFIG_SCSI_INITIO is not set # CONFIG_SCSI_INIA100 is not set # CONFIG_SCSI_NCR53C406A is not set @@ -194,7 +230,21 @@ # # Ethernet (10 or 100Mbit) # -# CONFIG_NET_ETHERNET is not set +CONFIG_NET_ETHERNET=y +# CONFIG_MACE is not set +# CONFIG_BMAC is not set +CONFIG_NCR885E=y +# CONFIG_NET_VENDOR_3COM is not set +# CONFIG_LANCE is not set +# CONFIG_NET_VENDOR_SMC is not set +# CONFIG_NET_VENDOR_RACAL is not set +# CONFIG_RTL8139 is not set +# CONFIG_SIS900 is not set +# CONFIG_YELLOWFIN is not set +# CONFIG_ACENIC is not set +# CONFIG_NET_ISA is not set +# CONFIG_NET_EISA is not set +# CONFIG_NET_POCKET is not set # CONFIG_FDDI is not set # CONFIG_HIPPI is not set # CONFIG_PPP is not set @@ -241,7 +291,6 @@ # CONFIG_VT=y CONFIG_VT_CONSOLE=y -CONFIG_PC_KEYB=y CONFIG_SERIAL=y CONFIG_SERIAL_CONSOLE=y # CONFIG_SERIAL_EXTENDED is not set @@ -256,14 +305,13 @@ # CONFIG_ATIXL_BUSMOUSE is not set # CONFIG_LOGIBUSMOUSE is not set # CONFIG_MS_BUSMOUSE is not set -CONFIG_ADBMOUSE=y CONFIG_MOUSE=y CONFIG_PSMOUSE=y # CONFIG_82C710_MOUSE is not set # CONFIG_PC110_PAD is not set # CONFIG_QIC02_TAPE is not set # CONFIG_WATCHDOG is not set -CONFIG_NVRAM=y +# CONFIG_NVRAM is not set # CONFIG_RTC is not set # @@ -283,6 +331,15 @@ # Ftape, the floppy tape device driver # # CONFIG_FTAPE is not set +# CONFIG_FT_NORMAL_DEBUG is not set +# CONFIG_FT_FULL_DEBUG is not set +# CONFIG_FT_NO_TRACE is not set +# CONFIG_FT_NO_TRACE_AT_ALL is not set +# CONFIG_FT_STD_FDC is not set +# CONFIG_FT_MACH2 is not set +# CONFIG_FT_PROBE_FC10 is not set +# CONFIG_FT_ALT_FDC is not set +# CONFIG_DRM is not set # # USB drivers - not for the faint of heart @@ -298,12 +355,10 @@ # 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_EFS_FS is not set CONFIG_ISO9660_FS=y # CONFIG_JOLIET is not set +# CONFIG_UDF_FS is not set # CONFIG_MINIX_FS is not set # CONFIG_NTFS_FS is not set # CONFIG_HPFS_FS is not set @@ -347,6 +402,6 @@ # # Kernel hacking # -CONFIG_MAGIC_SYSRQ=y +# CONFIG_MAGIC_SYSRQ is not set # CONFIG_KGDB is not set # CONFIG_XMON is not set diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/Makefile linux/arch/ppc/kernel/Makefile --- v2.3.19/linux/arch/ppc/kernel/Makefile Fri Sep 10 23:57:28 1999 +++ linux/arch/ppc/kernel/Makefile Thu Oct 7 10:17:08 1999 @@ -12,48 +12,83 @@ O_TARGET := kernel.o OX_OBJS := ppc_ksyms.o setup.o +KHEAD := head.o +ifdef CONFIG_PPC_ALL +CONFIG_PMAC=y +CONFIG_PREP=y +CONFIG_CHRP=y +endif O_OBJS := entry.o traps.o irq.o idle.o time.o process.o signal.o syscalls.o \ misc.o bitops.o ptrace.o align.o ppc_htab.o semaphore.o + ifndef CONFIG_8xx O_OBJS += hashtable.o endif + ifdef CONFIG_PCI O_OBJS += pci.o endif + ifdef CONFIG_KGDB O_OBJS += ppc-stub.o endif + ifdef CONFIG_TOTALMP O_OBJS += totalmp.o endif -ifeq ($(CONFIG_MBX),y) -O_OBJS += mbx_setup.o mbx_pci.o i8259.o ppc8xx_pic.o +ifdef CONFIG_PMAC_PBOOK +O_OBJS += sleep.o +endif + +ifdef CONFIG_SMP +O_OBJS += smp.o +endif + +ifeq ($(CONFIG_8xx),y) +KHEAD := head_8xx.o +O_OBJS += m8xx_setup.o ppc8xx_pic.o +ifndef CONFIG_MATH_EMULATION +O_OBJS += softemu8xx.o +endif +ifdef CONFIG_PCI +O_OBJS += qspan_pci.c +endif +ifdef CONFIG_MBX +O_OBJS += i8259.o +endif else ifeq ($(CONFIG_APUS),y) O_OBJS += apus_setup.o prom.o open_pic.o else -ifneq ($(CONFIG_MBX),y) -O_OBJS += prep_time.o pmac_time.o chrp_time.o \ - pmac_setup.o pmac_support.o \ - prep_pci.o pmac_pci.o chrp_pci.o \ - residual.o prom.o open_pic.o feature.o \ - prep_nvram.o i8259.o pmac_pic.o indirect_pci.o \ +ifneq ($(CONFIG_8xx),y) +O_OBJS += chrp_setup.o chrp_pci.o chrp_time.o \ + pmac_time.o pmac_support.o pmac_pci.o pmac_setup.o \ + prom.o open_pic.o feature.o \ + i8259.o pmac_pic.o indirect_pci.o \ gemini_pci.o gemini_prom.o gemini_setup.o -OX_OBJS += chrp_setup.o prep_setup.o + +ifeq ($(CONFIG_PREP), y) +O_OBJS += prep_pci.o prep_setup.o prep_nvram.o prep_time.o residual.o endif + +ifeq ($(CONFIG_PMAC), y) endif + +ifeq ($(CONFIG_PMAC), y) endif -ifdef CONFIG_SMP -O_OBJS += smp.o +endif +endif endif -all: head.o kernel.o +all: $(KHEAD) kernel.o head.o: head.S ppc_defs.h + +head_8xx.o: head_8xx.S ppc_defs.h ppc_defs.h: mk_defs.c ppc_defs.head \ $(TOPDIR)/include/asm/mmu.h \ diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/apus_setup.c linux/arch/ppc/kernel/apus_setup.c --- v2.3.19/linux/arch/ppc/kernel/apus_setup.c Tue Aug 31 17:29:12 1999 +++ linux/arch/ppc/kernel/apus_setup.c Thu Oct 7 10:17:08 1999 @@ -1,11 +1,16 @@ /* * linux/arch/ppc/kernel/apus_setup.c * - * Copyright (C) 1998 Jesper Skov + * Copyright (C) 1998, 1999 Jesper Skov * * Basically what is needed to replace functionality found in * arch/m68k allowing Amiga drivers to work under APUS. * Bits of code and/or ideas from arch/m68k and arch/ppc files. + * + * TODO: + * This file needs a *really* good cleanup. Restructure and optimize. + * Make sure it can be compiled for non-APUS configs. Begin to move + * Amiga specific stuff into linux/machine/amiga. */ #include @@ -14,79 +19,96 @@ #include #include #include +#include #include +#include +#include + +#ifdef CONFIG_APUS +#include +#endif /* Get the IDE stuff from the 68k file */ +#include #define ide_init_hwif_ports m68k_ide_init_hwif_ports #define ide_default_irq m68k_ide_default_irq +#define ide_request_irq m68k_ide_request_irq #define ide_default_io_base m68k_ide_default_io_base #define ide_check_region m68k_ide_check_region #define ide_request_region m68k_ide_request_region #define ide_release_region m68k_ide_release_region #define ide_fix_driveid m68k_ide_fix_driveid +#define ide_init_default_hwifs m68k_ide_init_default_hwifs +#define select_t m68k_select_t +#define ide_free_irq m68k_ide_free_irq +//#include #include +#undef ide_free_irq +#undef select_t +#undef ide_request_irq +#undef ide_init_default_hwifs #undef ide_init_hwif_ports -#define ide_default_irq -#define ide_default_io_base -#define ide_check_region -#define ide_request_region -#define ide_release_region -#define ide_fix_driveid - +#undef ide_default_irq +#undef ide_default_io_base +#undef ide_check_region +#undef ide_request_region +#undef ide_release_region +#undef ide_fix_driveid +/*-------------------------------------------*/ +#include #include #include #include #include #include +#include #include -#include +#include -#include "time.h" #include "local_irq.h" -unsigned long apus_get_rtc_time(void); -int apus_set_rtc_time(unsigned long nowtime); - -/* APUS defs */ -extern int parse_bootinfo(const struct bi_record *); -extern char _end[]; -#ifdef CONFIG_APUS -struct mem_info ramdisk; -unsigned long isa_io_base; -unsigned long isa_mem_base; -unsigned long pci_dram_offset; -#endif -/* END APUS defs */ - -unsigned long m68k_machtype; -char debug_device[6] = ""; +unsigned long m68k_machtype __apusdata; +char debug_device[6] __apusdata = ""; void (*mach_sched_init) (void (*handler)(int, void *, struct pt_regs *)) __initdata; /* machine dependent keyboard functions */ int (*mach_keyb_init) (void) __initdata; -int (*mach_kbdrate) (struct kbd_repeat *) = NULL; -void (*mach_kbd_leds) (unsigned int) = NULL; +int (*mach_kbdrate) (struct kbd_repeat *) __apusdata = NULL; +void (*mach_kbd_leds) (unsigned int) __apusdata = NULL; /* machine dependent irq functions */ void (*mach_init_IRQ) (void) __initdata; -void (*(*mach_default_handler)[]) (int, void *, struct pt_regs *) = NULL; -void (*mach_get_model) (char *model) = NULL; -int (*mach_get_hardware_list) (char *buffer) = NULL; -int (*mach_get_irq_list) (char *) = NULL; -void (*mach_process_int) (int, struct pt_regs *) = NULL; +void (*(*mach_default_handler)[]) (int, void *, struct pt_regs *) __apusdata = NULL; +void (*mach_get_model) (char *model) __apusdata = NULL; +int (*mach_get_hardware_list) (char *buffer) __apusdata = NULL; +int (*mach_get_irq_list) (char *) __apusdata = NULL; +void (*mach_process_int) (int, struct pt_regs *) __apusdata = NULL; /* machine dependent timer functions */ -unsigned long (*mach_gettimeoffset) (void); -void (*mach_gettod) (int*, int*, int*, int*, int*, int*); -int (*mach_hwclk) (int, struct hwclk_time*) = NULL; -int (*mach_set_clock_mmss) (unsigned long) = NULL; -void (*mach_reset)( void ); -long mach_max_dma_address = 0x00ffffff; /* default set to the lower 16MB */ -#if defined(CONFIG_AMIGA_FLOPPY) || defined(CONFIG_ATARI_FLOPPY) +unsigned long (*mach_gettimeoffset) (void) __apusdata; +void (*mach_gettod) (int*, int*, int*, int*, int*, int*) __apusdata; +int (*mach_hwclk) (int, struct hwclk_time*) __apusdata = NULL; +int (*mach_set_clock_mmss) (unsigned long) __apusdata = NULL; +void (*mach_reset)( void ) __apusdata; +long mach_max_dma_address __apusdata = 0x00ffffff; /* default set to the lower 16MB */ +#if defined(CONFIG_AMIGA_FLOPPY) void (*mach_floppy_setup) (char *, int *) __initdata = NULL; -void (*mach_floppy_eject) (void) = NULL; +void (*mach_floppy_eject) (void) __apusdata = NULL; #endif #ifdef CONFIG_HEARTBEAT -void (*mach_heartbeat) (int) = NULL; +void (*mach_heartbeat) (int) __apusdata = NULL; +extern void apus_heartbeat (void); +static int heartbeat_enabled = 1; + +void enable_heartbeat(void) +{ + heartbeat_enabled = 1; +} + +void disable_heartbeat(void) +{ + heartbeat_enabled = 0; + mach_heartbeat(0); +} #endif extern unsigned long amiga_model; @@ -94,22 +116,154 @@ extern unsigned count_period_num; /* 1 decrementer count equals */ extern unsigned count_period_den; /* count_period_num / count_period_den us */ -extern struct mem_info memory[NUM_MEMINFO];/* memory description */ +int num_memory __apusdata = 0; +struct mem_info memory[NUM_MEMINFO] __apusdata;/* memory description */ +/* FIXME: Duplicate memory data to avoid conflicts with m68k shared code. */ +int m68k_realnum_memory __apusdata = 0; +struct mem_info m68k_memory[NUM_MEMINFO] __apusdata;/* memory description */ + +struct mem_info ramdisk __apusdata; extern void amiga_floppy_setup(char *, int *); extern void config_amiga(void); -static int __60nsram = 0; +static int __60nsram __apusdata = 0; + +/* for cpuinfo */ +static int __bus_speed __apusdata = 0; +static int __speed_test_failed __apusdata = 0; + +/********************************************** COMPILE PROTECTION */ +/* Provide some stubs that links to Amiga specific functions. + * This allows CONFIG_APUS to be removed from generic PPC files while + * preventing link errors for other PPC targets. + */ +__apus +unsigned long apus_get_rtc_time(void) +{ +#ifdef CONFIG_APUS + extern unsigned long m68k_get_rtc_time(void); + + return m68k_get_rtc_time (); +#else + return 0; +#endif +} + +__apus +int apus_set_rtc_time(unsigned long nowtime) +{ +#ifdef CONFIG_APUS + extern int m68k_set_rtc_time(unsigned long nowtime); + + return m68k_set_rtc_time (nowtime); +#else + return 0; +#endif +} + +__apus +int apus_request_irq(unsigned int irq, + void (*handler)(int, void *, struct pt_regs *), + unsigned long flags, const char *devname, + void *dev_id) +{ +#ifdef CONFIG_APUS + extern int amiga_request_irq(unsigned int irq, + void (*handler)(int, void *, + struct pt_regs *), + unsigned long flags, + const char *devname, + void *dev_id); + + return amiga_request_irq (irq, handler, flags, devname, dev_id); +#else + return 0; +#endif +} + +__apus +void apus_free_irq(unsigned int irq, void *dev_id) +{ +#ifdef CONFIG_APUS + extern void amiga_free_irq(unsigned int irq, void *dev_id); + + amiga_free_irq (irq, dev_id); +#endif +} + +__apus +void apus_process_int(unsigned long vec, void *fp) +{ +#ifdef CONFIG_APUS + extern void process_int(unsigned long vec, struct pt_regs *fp); + + process_int (vec, (struct pt_regs*)fp); +#endif +} + +__apus +int apus_get_irq_list(char *buf) +{ +#ifdef CONFIG_APUS + extern int m68k_get_irq_list (char*); + + return m68k_get_irq_list (buf); +#else + return 0; +#endif +} + + +/* Here some functions we don't support, but which the other ports reference */ +int pckbd_setkeycode(unsigned int scancode, unsigned int keycode) +{ + printk("Bogus call to " __FILE__ ":" __FUNCTION__ "\n"); + return 0; +} +int pckbd_getkeycode(unsigned int scancode) +{ + printk("Bogus call to " __FILE__ ":" __FUNCTION__ "\n"); + return 0; +} +int pckbd_translate(unsigned char scancode, unsigned char *keycode, + char raw_mode) +{ + printk("Bogus call to " __FILE__ ":" __FUNCTION__ "\n"); + return 0; +} +char pckbd_unexpected_up(unsigned char keycode) +{ + printk("Bogus call to " __FILE__ ":" __FUNCTION__ "\n"); + return 0; +} +void pckbd_leds(unsigned char leds) +{ + printk("Bogus call to " __FILE__ ":" __FUNCTION__ "\n"); +} +void pckbd_init_hw(void) +{ + printk("Bogus call to " __FILE__ ":" __FUNCTION__ "\n"); +} +unsigned char pckbd_sysrq_xlate[128]; + +struct pci_bus * __init pci_scan_peer_bridge(int bus) +{ + printk("Bogus call to " __FILE__ ":" __FUNCTION__ "\n"); + return NULL; +} /*********************************************************** SETUP */ /* From arch/m68k/kernel/setup.c. */ void __init apus_setup_arch(unsigned long * memory_start_p, unsigned long * memory_end_p) { +#ifdef CONFIG_APUS extern char cmd_line[]; int i; char *p, *q; + /* Let m68k-shared code know it should do the Amiga thing. */ m68k_machtype = MACH_AMIGA; /* Parse the command line for arch-specific options. @@ -143,10 +297,46 @@ } config_amiga(); + + { +#define LOG_SIZE 4096 + void* base; + + /* Throw away some memory - the P5 firmare stomps on top + * of CHIP memory during bootup. + */ + amiga_chip_alloc(0x1000); + + base = amiga_chip_alloc(LOG_SIZE+sizeof(klog_data_t)); + LOG_INIT(base, base+sizeof(klog_data_t), LOG_SIZE); + } +#endif } +__apus +int +apus_get_cpuinfo(char *buffer) +{ +#ifdef CONFIG_APUS + extern int __map_without_bats; + extern unsigned long powerup_PCI_present; + int len; + + len = sprintf(buffer, "machine\t\t: Amiga\n"); + len += sprintf(buffer+len, "bus speed\t: %d%s", __bus_speed, + (__speed_test_failed) ? " [failed]\n" : "\n"); + len += sprintf(buffer+len, "using BATs\t: %s\n", + (__map_without_bats) ? "No" : "Yes"); + len += sprintf(buffer+len, "ram speed\t: %dns\n", + (__60nsram) ? 60 : 70); + len += sprintf(buffer+len, "PCI bridge\t: %s\n", + (powerup_PCI_present) ? "Yes" : "No"); + return len; +#endif +} -void get_current_tb(unsigned long long *time) +__apus +static void get_current_tb(unsigned long long *time) { __asm __volatile ("1:mftbu 4 \n\t" " mftb 5 \n\t" @@ -161,14 +351,17 @@ } +__apus void apus_calibrate_decr(void) { +#ifdef CONFIG_APUS int freq, divisor; /* This algorithm for determining the bus speed was contributed by Ralph Schmidt. */ unsigned long long start, stop; int bus_speed; + int speed_test_failed = 0; { unsigned long loop = amiga_eclock / 10; @@ -200,16 +393,23 @@ "Defaulting to 50MHz", bus_speed); bus_speed = 50; freq = 12500000; + speed_test_failed = 1; } /* Ease diagnostics... */ { extern int __map_without_bats; + extern unsigned long powerup_PCI_present; - printk ("APUS: BATs=%d, BUS=%dMHz, RAM=%dns\n", + printk ("APUS: BATs=%d, BUS=%dMHz", (__map_without_bats) ? 0 : 1, - bus_speed, - (__60nsram) ? 60 : 70); + bus_speed); + if (speed_test_failed) + printk ("[FAILED - please report]"); + + printk (", RAM=%dns, PCI bridge=%d\n", + (__60nsram) ? 60 : 70, + (powerup_PCI_present) ? 1 : 0); /* print a bit more if asked politely... */ if (!(ciaa.pra & 0x40)){ @@ -232,25 +432,67 @@ decrementer_count = freq / HZ / divisor; count_period_num = divisor; count_period_den = freq / 1000000; + + __bus_speed = bus_speed; + __speed_test_failed = speed_test_failed; +#endif } +__apus void arch_gettod(int *year, int *mon, int *day, int *hour, int *min, int *sec) { +#ifdef CONFIG_APUS if (mach_gettod) mach_gettod(year, mon, day, hour, min, sec); else *year = *mon = *day = *hour = *min = *sec = 0; +#endif +} + +/* for "kbd-reset" cmdline param */ +__init +void kbd_reset_setup(char *str, int *ints) +{ +} + +#if defined(CONFIG_WHIPPET_SERIAL)||defined(CONFIG_MULTIFACE_III_TTY)||defined(CONFIG_GVPIOEXT)||defined(CONFIG_AMIGA_BUILTIN_SERIAL) + +long m68k_rs_init(void); +int m68k_register_serial(struct serial_struct *); +void m68k_unregister_serial(int); +long m68k_serial_console_init(long, long ); + +int rs_init(void) +{ + return m68k_rs_init(); +} +int register_serial(struct serial_struct *p) +{ + return m68k_register_serial(p); +} +void unregister_serial(int i) +{ + m68k_unregister_serial(i); } +#ifdef CONFIG_SERIAL_CONSOLE +long serial_console_init(long kmem_start, long kmem_end) +{ + return m68k_serial_console_init(kmem_start, kmem_end); +} +#endif +#endif /*********************************************************** FLOPPY */ -#if defined(CONFIG_AMIGA_FLOPPY) || defined(CONFIG_ATARI_FLOPPY) -void __init floppy_setup(char *str, int *ints) +#if defined(CONFIG_AMIGA_FLOPPY) +__init +void floppy_setup(char *str, int *ints) { if (mach_floppy_setup) mach_floppy_setup (str, ints); } +__apus void floppy_eject(void) { if (mach_floppy_eject) @@ -259,44 +501,13 @@ #endif /*********************************************************** MEMORY */ -extern void -map_page(struct task_struct *tsk, unsigned long va, - unsigned long pa, int flags); - -#define KMAP_MAX 8 -static unsigned long kmap_chunks[KMAP_MAX*3]; -static int kmap_chunk_count = 0; - -/* Based on arch/ppc/mm/init.c:ioremap() which maps the address range - to the same virtual address as the physical address - which may - cause problems since Z3 IO space is not the same as PCI/ISA. - This should be rewritten to something more like the m68k version. */ -unsigned long kernel_map (unsigned long phys_addr, unsigned long size, - int cacheflag, unsigned long *memavailp) -{ - unsigned long v_ret, end; - /* Remap to 0x90000000. Related comment in ppc/mm/init.c. */ - static unsigned long virt = 0x90000000; - v_ret = virt; - - if (kmap_chunk_count == KMAP_MAX*3) - panic ("kernel_map: Can only map %d chunks.\n", - KMAP_MAX); - - kmap_chunks[kmap_chunk_count++] = phys_addr; - kmap_chunks[kmap_chunk_count++] = size; - kmap_chunks[kmap_chunk_count++] = v_ret; - - for (end = phys_addr + size ; phys_addr < end; - phys_addr += PAGE_SIZE, virt += PAGE_SIZE) { - map_page(&init_task, virt, phys_addr, - pgprot_val(PAGE_KERNEL_CI) | _PAGE_GUARDED); - } - return v_ret; -} +#define KMAP_MAX 32 +unsigned long kmap_chunks[KMAP_MAX*3] __apusdata; +int kmap_chunk_count __apusdata = 0; /* From pgtable.h */ -extern __inline__ pte_t *my_find_pte(struct mm_struct *mm,unsigned long va) +__apus +static __inline__ pte_t *my_find_pte(struct mm_struct *mm,unsigned long va) { pgd_t *dir = 0; pmd_t *pmd = 0; @@ -318,10 +529,11 @@ /* Again simulating an m68k/mm/kmap.c function. */ +__apus void kernel_set_cachemode( unsigned long address, unsigned long size, unsigned int cmode ) { - int mask, flags; + unsigned long mask, flags; switch (cmode) { @@ -360,6 +572,7 @@ } } +__apus unsigned long mm_ptov (unsigned long paddr) { unsigned long ret; @@ -388,6 +601,7 @@ return ret; } +__apus int mm_end_of_chunk (unsigned long addr, int len) { if (memory[0].addr + memory[0].size == addr + len) @@ -399,6 +613,7 @@ #define L1_CACHE_BYTES 32 #define MAX_CACHE_SIZE 8192 +__apus void cache_push(__u32 addr, int length) { addr = mm_ptov(addr); @@ -417,6 +632,8 @@ "sync \n\t" : : "r" (addr)); } + +__apus void cache_clear(__u32 addr, int length) { if (MAX_CACHE_SIZE < length) @@ -450,6 +667,7 @@ : : "r" (addr)); } +/****************************************************** from setup.c */ void apus_restart(char *cmd) { @@ -478,37 +696,13 @@ apus_restart(NULL); } -void -apus_do_IRQ(struct pt_regs *regs, - int cpu, - int isfake) -{ - int old_level, new_level; - - /* I don't think we need SMP code here - Corey */ - - old_level = ~(regs->mq) & IPLEMU_IPLMASK; - new_level = (~(regs->mq) >> 3) & IPLEMU_IPLMASK; - if (new_level != 0) - { - APUS_WRITE(APUS_IPL_EMU, IPLEMU_IPLMASK); - APUS_WRITE(APUS_IPL_EMU, (IPLEMU_SETRESET - | (~(new_level) & IPLEMU_IPLMASK))); - APUS_WRITE(APUS_IPL_EMU, IPLEMU_DISABLEINT); - - process_int (VEC_SPUR+new_level, regs); - APUS_WRITE(APUS_IPL_EMU, IPLEMU_SETRESET | IPLEMU_DISABLEINT); - APUS_WRITE(APUS_IPL_EMU, IPLEMU_IPLMASK); - APUS_WRITE(APUS_IPL_EMU, (IPLEMU_SETRESET - | (~(old_level) & IPLEMU_IPLMASK))); - } - APUS_WRITE(APUS_IPL_EMU, IPLEMU_DISABLEINT); -} - +/****************************************************** from setup.c/IDE */ #if defined(CONFIG_BLK_DEV_IDE) || defined(CONFIG_BLK_DEV_IDE_MODULE) /* * IDE stuff. */ +void ide_insw(ide_ioreg_t port, void *buf, int ns); +void ide_outsw(ide_ioreg_t port, void *buf, int ns); void apus_ide_insw(ide_ioreg_t port, void *buf, int ns) { @@ -524,13 +718,13 @@ int apus_ide_default_irq(ide_ioreg_t base) { - m68k_ide_default_irq(base); + return m68k_ide_default_irq(base); } ide_ioreg_t apus_ide_default_io_base(int index) { - m68k_ide_default_io_base(index); + return 0; } int @@ -560,25 +754,156 @@ m68k_ide_fix_driveid(id); } -void __init -apus_ide_init_hwif_ports (hw_regs_t *hw, ide_ioreg_t data_port, ide_ioreg_t ctrl_port, int *irq) +__init +void apus_ide_init_hwif_ports (hw_regs_t *hw, ide_ioreg_t data_port, + ide_ioreg_t ctrl_port, int *irq) { m68k_ide_init_hwif_ports(hw, data_port, ctrl_port, irq); } #endif +/****************************************************** from irq.c */ +#define VEC_SPUR (24) -void __init -apus_local_init_IRQ(void) +void +apus_do_IRQ(struct pt_regs *regs, + int cpu, + int isfake) { - ppc_md.mask_irq = amiga_disable_irq; - ppc_md.unmask_irq = amiga_enable_irq; - apus_init_IRQ(); + int old_level, new_level; + + new_level = (~(regs->mq) >> 3) & IPLEMU_IPLMASK; + + if (0 != new_level && 7 != new_level) { + old_level = ~(regs->mq) & IPLEMU_IPLMASK; + + apus_process_int (VEC_SPUR+new_level, regs); + + APUS_WRITE(APUS_IPL_EMU, IPLEMU_SETRESET | IPLEMU_DISABLEINT); + APUS_WRITE(APUS_IPL_EMU, IPLEMU_IPLMASK); + APUS_WRITE(APUS_IPL_EMU, (IPLEMU_SETRESET + | (~(old_level) & IPLEMU_IPLMASK))); + APUS_WRITE(APUS_IPL_EMU, IPLEMU_DISABLEINT); + } } -void __init -apus_init(unsigned long r3, unsigned long r4, unsigned long r5, - unsigned long r6, unsigned long r7) +__apus +static void apus_save_flags(unsigned long* flags) { + unsigned short __f; + APUS_READ(APUS_IPL_EMU, __f); + return ((~__f) & IPLEMU_IPLMASK) << 8; +} + +__apus +static void apus_restore_flags(unsigned long flags) +{ + APUS_WRITE(APUS_IPL_EMU, IPLEMU_SETRESET | IPLEMU_DISABLEINT); + APUS_WRITE(APUS_IPL_EMU, IPLEMU_IPLMASK); + APUS_WRITE(APUS_IPL_EMU, IPLEMU_SETRESET + | (~(flags >> 8) & IPLEMU_IPLMASK)); + APUS_WRITE(APUS_IPL_EMU, IPLEMU_DISABLEINT); +} + +__apus +static void apus_sti(void) +{ + APUS_WRITE(APUS_IPL_EMU, IPLEMU_SETRESET | IPLEMU_DISABLEINT); + APUS_WRITE(APUS_IPL_EMU, IPLEMU_IPLMASK); + APUS_WRITE(APUS_IPL_EMU, IPLEMU_SETRESET | IPLEMU_IPLMASK); + APUS_WRITE(APUS_IPL_EMU, IPLEMU_DISABLEINT); +} + +__apus +static void apus_cli(void) +{ + APUS_WRITE(APUS_IPL_EMU, IPLEMU_SETRESET | IPLEMU_DISABLEINT); + APUS_WRITE(APUS_IPL_EMU, IPLEMU_IPLMASK); + APUS_WRITE(APUS_IPL_EMU, IPLEMU_SETRESET); + APUS_WRITE(APUS_IPL_EMU, IPLEMU_DISABLEINT); +} + +/****************************************************** keyboard */ +__apus +static int apus_kbd_setkeycode(unsigned int scancode, unsigned int keycode) +{ + return -EOPNOTSUPP; +} + +__apus +static int apus_kbd_getkeycode(unsigned int scancode) +{ + return scancode > 127 ? -EINVAL : scancode; +} + +__apus +static int apus_kbd_translate(unsigned char keycode, unsigned char *keycodep, + char raw_mode) +{ + *keycodep = keycode; + return 1; +} + +__apus +static char apus_kbd_unexpected_up(unsigned char keycode) +{ + return 0200; +} + +__apus +static void apus_kbd_leds(unsigned char leds) +{ +} + +__apus +static void apus_kbd_init_hw(void) +{ +#ifdef CONFIG_APUS + extern int amiga_keyb_init(void); + +printk("**** " __FUNCTION__ "\n"); + amiga_keyb_init(); +#endif +} + + +/****************************************************** init */ +extern void amiga_disable_irq(unsigned int irq); +extern void amiga_enable_irq(unsigned int irq); +extern void m68k_init_IRQ (void); + +struct hw_interrupt_type amiga_irq_ctl = { + " Amiga ", + NULL, + NULL, + NULL, + amiga_enable_irq, + amiga_disable_irq, + NULL, + 0 +}; + +__init +void apus_init_IRQ(void) +{ + int i; + + for (i = 0; i < NR_IRQS; i++) + irq_desc[i].ctl = &amiga_irq_ctl; + m68k_init_IRQ (); + + int_control.int_sti = apus_sti; + int_control.int_cli = apus_cli; + int_control.int_save_flags = apus_save_flags; + int_control.int_restore_flags = apus_restore_flags; +} + +__init +void apus_init(unsigned long r3, unsigned long r4, unsigned long r5, + unsigned long r6, unsigned long r7) +{ + extern int parse_bootinfo(const struct bi_record *); + extern char _end[]; + /* Parse bootinfo. The bootinfo is located right after the kernel bss */ parse_bootinfo((const struct bi_record *)&_end); @@ -591,9 +916,6 @@ initrd_end = (unsigned long) __va(ramdisk.size + ramdisk.addr); } - /* Make sure code below is not executed. */ - r4 = 0; - r6 = 0; #endif /* CONFIG_BLK_DEV_INITRD */ ISA_DMA_THRESHOLD = 0x00ffffff; @@ -604,7 +926,10 @@ ppc_md.irq_cannonicalize = NULL; ppc_md.init_IRQ = apus_init_IRQ; ppc_md.do_IRQ = apus_do_IRQ; - ppc_md.get_irq_source = NULL; +#ifdef CONFIG_HEARTBEAT + ppc_md.heartbeat = apus_heartbeat; + ppc_md.heartbeat_count = 1; +#endif ppc_md.init = NULL; ppc_md.restart = apus_restart; @@ -616,24 +941,29 @@ ppc_md.get_rtc_time = apus_get_rtc_time; ppc_md.calibrate_decr = apus_calibrate_decr; + ppc_md.nvram_read_val = NULL; + ppc_md.nvram_write_val = NULL; + /* These should not be used for the APUS yet, since it uses the M68K keyboard now. */ - ppc_md.kbd_setkeycode = NULL; - ppc_md.kbd_getkeycode = NULL; - ppc_md.kbd_translate = NULL; - ppc_md.kbd_unexpected_up = NULL; - ppc_md.kbd_leds = NULL; - ppc_md.kbd_init_hw = NULL; + ppc_md.kbd_setkeycode = apus_kbd_setkeycode; + ppc_md.kbd_getkeycode = apus_kbd_getkeycode; + ppc_md.kbd_translate = apus_kbd_translate; + ppc_md.kbd_unexpected_up = apus_kbd_unexpected_up; + ppc_md.kbd_leds = apus_kbd_leds; + ppc_md.kbd_init_hw = apus_kbd_init_hw; +#ifdef CONFIG_MAGIC_SYSRQ ppc_md.kbd_sysrq_xlate = NULL; +#endif #if defined(CONFIG_BLK_DEV_IDE) || defined(CONFIG_BLK_DEV_IDE_MODULE) ppc_ide_md.insw = apus_ide_insw; ppc_ide_md.outsw = apus_ide_outsw; ppc_ide_md.default_irq = apus_ide_default_irq; ppc_ide_md.default_io_base = apus_ide_default_io_base; - ppc_ide_md.check_region = apus_ide_check_region; - ppc_ide_md.request_region = apus_ide_request_region; - ppc_ide_md.release_region = apus_ide_release_region; + ppc_ide_md.ide_check_region = apus_ide_check_region; + ppc_ide_md.ide_request_region = apus_ide_request_region; + ppc_ide_md.ide_release_region = apus_ide_release_region; ppc_ide_md.fix_driveid = apus_ide_fix_driveid; ppc_ide_md.ide_init_hwif = apus_ide_init_hwif_ports; diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/chrp_pci.c linux/arch/ppc/kernel/chrp_pci.c --- v2.3.19/linux/arch/ppc/kernel/chrp_pci.c Tue Aug 31 17:29:12 1999 +++ linux/arch/ppc/kernel/chrp_pci.c Thu Oct 7 10:17:08 1999 @@ -354,7 +354,8 @@ else { if ( !strncmp("IBM,7043-150", get_property(find_path_device("/"), "name", NULL),12) || - !strncmp("IBM,7046-155", get_property(find_path_device("/"), "name", NULL),12) ) + !strncmp("IBM,7046-155", get_property(find_path_device("/"), "name", NULL),12) || + !strncmp("IBM,7046-B50", get_property(find_path_device("/"), "name", NULL),12) ) { pci_dram_offset = 0; isa_mem_base = 0x80000000; diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/chrp_setup.c linux/arch/ppc/kernel/chrp_setup.c --- v2.3.19/linux/arch/ppc/kernel/chrp_setup.c Tue Aug 31 17:29:12 1999 +++ linux/arch/ppc/kernel/chrp_setup.c Thu Oct 7 10:17:08 1999 @@ -33,6 +33,8 @@ #include #include #include +#include +#include #include #include @@ -46,7 +48,6 @@ #include #include #include -#include #include #include @@ -55,14 +56,6 @@ #include "i8259.h" #include "open_pic.h" -/* Fixme - need to move these into their own .c and .h file */ -extern void i8259_mask_and_ack_irq(unsigned int irq_nr); -extern void i8259_set_irq_mask(unsigned int irq_nr); -extern void i8259_mask_irq(unsigned int irq_nr); -extern void i8259_unmask_irq(unsigned int irq_nr); -extern void i8259_init(void); - -/* Fixme - remove this when it is fixed. - Corey */ extern volatile unsigned char *chrp_int_ack_special; unsigned long chrp_get_rtc_time(void); @@ -91,7 +84,6 @@ extern void mackbd_init_hw(void); extern unsigned char mackbd_sysrq_xlate[128]; -/* for the mac fs */ kdev_t boot_dev; extern PTE *Hash, *Hash_end; @@ -185,12 +177,11 @@ } /* - * Fixes for the National Semiconductor PC78308VUL SuperI/O - * - * Some versions of Open Firmware incorrectly initialize the IRQ settings - * for keyboard and mouse - */ - + * Fixes for the National Semiconductor PC78308VUL SuperI/O + * + * Some versions of Open Firmware incorrectly initialize the IRQ settings + * for keyboard and mouse + */ static inline void __init sio_write(u8 val, u8 index) { outb(index, 0x15c); @@ -236,7 +227,7 @@ void __init - chrp_setup_arch(unsigned long * memory_start_p, unsigned long * memory_end_p) +chrp_setup_arch(unsigned long * memory_start_p, unsigned long * memory_end_p) { extern char cmd_line[]; struct device_node *device; @@ -358,6 +349,46 @@ } } +int chrp_get_irq( struct pt_regs *regs ) +{ + int irq; + + irq = openpic_irq( smp_processor_id() ); + if (irq == IRQ_8259_CASCADE) + { + /* + * This magic address generates a PCI IACK cycle. + */ + if ( chrp_int_ack_special ) + irq = *chrp_int_ack_special; + else + irq = i8259_irq( smp_processor_id() ); + /* + * Acknowledge as soon as possible to allow i8259 + * interrupt nesting */ + openpic_eoi( smp_processor_id() ); + } + if (irq == OPENPIC_VEC_SPURIOUS) + /* + * Spurious interrupts should never be + * acknowledged + */ + irq = -1; + return irq; +} + +void chrp_post_irq(int irq) +{ + /* + * If it's an i8259 irq then we've already done the + * openpic irq. So we just check to make sure the controller + * is an openpic and if it is then eoi -- Cort + */ + if ( irq_desc[irq].ctl == &open_pic ) + openpic_eoi( smp_processor_id() ); +} + +#if 0 void chrp_do_IRQ(struct pt_regs *regs, int cpu, @@ -432,9 +463,9 @@ if (!openpic_eoi_done) openpic_eoi(0); } +#endif -void __init - chrp_init_IRQ(void) +void __init chrp_init_IRQ(void) { struct device_node *np; int i; @@ -465,11 +496,8 @@ } void __init - chrp_init2(void) +chrp_init2(void) { - adb_init(); - - /* Should this be here? - Corey */ pmac_nvram_init(); } @@ -482,8 +510,9 @@ ide_ioreg_t chrp_ide_regbase[MAX_HWIFS]; ide_ioreg_t chrp_idedma_regbase; -void chrp_ide_probe(void) { - +void +chrp_ide_probe(void) +{ struct pci_dev *pdev = pci_find_device(PCI_VENDOR_ID_WINBOND, PCI_DEVICE_ID_WINBOND_82C105, NULL); chrp_ide_ports_known = 1; @@ -570,11 +599,12 @@ hw->irq = chrp_ide_irq; } +#if defined(CONFIG_BLK_DEV_IDE_MODULE) EXPORT_SYMBOL(chrp_ide_irq); EXPORT_SYMBOL(chrp_ide_ports_known); EXPORT_SYMBOL(chrp_ide_regbase); EXPORT_SYMBOL(chrp_ide_probe); - +#endif #endif void __init @@ -601,7 +631,8 @@ ppc_md.get_cpuinfo = chrp_get_cpuinfo; ppc_md.irq_cannonicalize = chrp_irq_cannonicalize; ppc_md.init_IRQ = chrp_init_IRQ; - ppc_md.do_IRQ = chrp_do_IRQ; + ppc_md.get_irq = chrp_get_irq; + ppc_md.post_irq = chrp_post_irq; ppc_md.init = chrp_init2; @@ -616,7 +647,7 @@ #ifdef CONFIG_VT #ifdef CONFIG_MAC_KEYBOAD - if ( adb_hardware == ADB_NONE ) + if (adb_driver == NULL) { ppc_md.kbd_setkeycode = pckbd_setkeycode; ppc_md.kbd_getkeycode = pckbd_getkeycode; @@ -678,7 +709,8 @@ if ( ppc_md.progress ) ppc_md.progress("Linux/PPC "UTS_RELEASE"\n", 0x0); } -void chrp_progress(char *s, unsigned short hex) +void +chrp_progress(char *s, unsigned short hex) { extern unsigned int rtas_data; int max_width, width; diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/entry.S linux/arch/ppc/kernel/entry.S --- v2.3.19/linux/arch/ppc/kernel/entry.S Fri Sep 10 23:57:28 1999 +++ linux/arch/ppc/kernel/entry.S Thu Oct 7 10:17:08 1999 @@ -1,7 +1,7 @@ /* * arch/ppc/kernel/entry.S * - * $Id: entry.S,v 1.3 1999/09/05 11:56:26 paulus Exp $ + * $Id: entry.S,v 1.4 1999/09/14 05:18:14 dmalek Exp $ * * PowerPC version * Copyright (C) 1995-1996 Gary Thomas (gdt@linuxppc.org) @@ -26,6 +26,7 @@ #include "ppc_asm.h" #include #include +#include #include #include #include diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/feature.c linux/arch/ppc/kernel/feature.c --- v2.3.19/linux/arch/ppc/kernel/feature.c Wed Mar 10 21:30:31 1999 +++ linux/arch/ppc/kernel/feature.c Thu Oct 7 10:17:08 1999 @@ -41,7 +41,9 @@ OH_BAY_FLOPPY_ENABLE, /* FEATURE_Mediabay_floppy_enable */ 0, /* FEATURE_BMac_reset */ 0, /* FEATURE_BMac_IO_enable */ - 0 /* FEATURE_Modem_Reset -> guess...*/ + 0, /* FEATURE_Modem_Reset -> guess... */ + OH_IDE_POWER, /* FEATURE_IDE_DiskPower -> guess... */ + OH_IDE_RESET /* FEATURE_IDE_Reset (0 based) -> guess... */ }; /* assume these are the same as the ohare until proven otherwise */ @@ -63,7 +65,9 @@ OH_BAY_FLOPPY_ENABLE, /* FEATURE_Mediabay_floppy_enable */ 0x80000000, /* FEATURE_BMac_reset */ 0x60000000, /* FEATURE_BMac_IO_enable */ - 0x02000000 /* FEATURE_Modem_Reset -> guess...*/ + 0x02000000, /* FEATURE_Modem_Reset -> guess...*/ + OH_IDE_POWER, /* FEATURE_IDE_DiskPower -> guess... */ + OH_IDE_RESET /* FEATURE_IDE_Reset (0 based) -> guess... */ }; /* definition of a feature controller object */ @@ -191,9 +195,10 @@ save_flags(flags); cli(); - st_le32( controllers[controller].reg, - ld_le32(controllers[controller].reg) | + out_le32( controllers[controller].reg, + in_le32(controllers[controller].reg) | controllers[controller].bits[f]); + (void)in_le32(controllers[controller].reg); restore_flags(flags); udelay(10); @@ -220,9 +225,10 @@ save_flags(flags); cli(); - st_le32( controllers[controller].reg, - ld_le32(controllers[controller].reg) & + out_le32( controllers[controller].reg, + in_le32(controllers[controller].reg) & ~(controllers[controller].bits[f])); + (void)in_le32(controllers[controller].reg); restore_flags(flags); udelay(10); @@ -241,7 +247,7 @@ if (controller < 0) return controller; - return (ld_le32(controllers[controller].reg) & + return (in_le32(controllers[controller].reg) & controllers[controller].bits[f]) != 0; } diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/gemini_pci.c linux/arch/ppc/kernel/gemini_pci.c --- v2.3.19/linux/arch/ppc/kernel/gemini_pci.c Fri Sep 10 23:57:28 1999 +++ linux/arch/ppc/kernel/gemini_pci.c Thu Oct 7 10:17:08 1999 @@ -244,7 +244,6 @@ void __init gemini_pcibios_fixup(void) { - struct pci_bus *bus; unsigned long orig_mem_base, orig_io_base; orig_mem_base = pci_mem_base; diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/gemini_setup.c linux/arch/ppc/kernel/gemini_setup.c --- v2.3.19/linux/arch/ppc/kernel/gemini_setup.c Fri Sep 10 23:57:28 1999 +++ linux/arch/ppc/kernel/gemini_setup.c Thu Oct 7 10:17:08 1999 @@ -53,6 +53,8 @@ 0, 0, 14, 0, 0, 13, 5, 9, 6, 11, 8, 10, 0, 12, 7, 0 }; +int chrp_get_irq(struct pt_regs *); +void chrp_post_irq(int); static inline unsigned long _get_HID1(void) { @@ -479,7 +481,7 @@ void __init gemini_init(unsigned long r3, unsigned long r4, unsigned long r5, unsigned long r6, unsigned long r7) { - void chrp_do_IRQ(struct pt_regs *, int, int); + int chrp_get_irq( struct pt_regs * ); void layout_bus( struct pci_bus * ); gemini_setup_pci_ptrs(); @@ -501,7 +503,8 @@ ppc_md.get_cpuinfo = gemini_get_cpuinfo; ppc_md.irq_cannonicalize = NULL; ppc_md.init_IRQ = gemini_init_IRQ; - ppc_md.do_IRQ = chrp_do_IRQ; + ppc_md.get_irq = chrp_get_irq; + ppc_md.post_irq = chrp_post_irq; ppc_md.init = NULL; ppc_md.restart = gemini_restart; diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/head.S linux/arch/ppc/kernel/head.S --- v2.3.19/linux/arch/ppc/kernel/head.S Fri Sep 10 23:57:28 1999 +++ linux/arch/ppc/kernel/head.S Thu Oct 7 10:17:08 1999 @@ -1,7 +1,7 @@ /* * arch/ppc/kernel/head.S * - * $Id: head.S,v 1.143 1999/09/05 11:56:28 paulus Exp $ + * $Id: head.S,v 1.147 1999/09/15 23:58:53 cort Exp $ * * PowerPC version * Copyright (C) 1995-1996 Gary Thomas (gdt@linuxppc.org) @@ -333,8 +333,12 @@ .long ret_from_except /* System reset */ -#ifdef CONFIG_SMP /* MVME/MTX start the secondary here */ +#ifdef CONFIG_SMP /* MVME/MTX and gemini start the secondary here */ +#ifdef CONFIG_GEMINI + STD_EXCEPTION(0x100, Reset, __secondary_start_gemini) +#else /* CONFIG_GEMINI */ STD_EXCEPTION(0x100, Reset, __secondary_start_psurge) +#endif /* CONFIG_GEMINI */ #else STD_EXCEPTION(0x100, Reset, UnknownException) #endif @@ -421,6 +425,8 @@ li r20,MSR_KERNEL li r4,0 bl transfer_to_handler + .globl do_IRQ_intercept +do_IRQ_intercept: .long do_IRQ; .long ret_from_except @@ -461,7 +467,17 @@ .long KernelFP .long ret_from_except - STD_EXCEPTION(0x900, Decrementer, timer_interrupt) + . = 0x900 +Decrementer: + EXCEPTION_PROLOG + addi r3,r1,STACK_FRAME_OVERHEAD + li r20,MSR_KERNEL + bl transfer_to_handler + .globl timer_interrupt_intercept +timer_interrupt_intercept: + .long timer_interrupt + .long ret_from_except + STD_EXCEPTION(0xa00, Trap_0a, UnknownException) STD_EXCEPTION(0xb00, Trap_0b, UnknownException) @@ -1011,6 +1027,20 @@ mr r24,r3 /* cpu # */ blr + .globl __secondary_start_gemini +__secondary_start_gemini: +1011: b 1011b + + mfspr r4,HID0 + ori r4,r4,HID0_ICFI + li r3,0 + ori r3,r3,HID0_ICE + andc r4,r4,r3 + mtspr HID0,r4 + sync + bl prom_init + b __secondary_start + .globl __secondary_start_psurge __secondary_start_psurge: li r24,1 /* cpu # */ diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/head_8xx.S linux/arch/ppc/kernel/head_8xx.S --- v2.3.19/linux/arch/ppc/kernel/head_8xx.S Tue Aug 31 17:29:13 1999 +++ linux/arch/ppc/kernel/head_8xx.S Thu Oct 7 10:17:08 1999 @@ -1,7 +1,7 @@ /* * arch/ppc/kernel/except_8xx.S * - * $Id: head_8xx.S,v 1.2 1999/08/23 02:53:19 paulus Exp $ + * $Id: head_8xx.S,v 1.4 1999/09/18 18:43:19 dmalek Exp $ * * PowerPC version * Copyright (C) 1995-1996 Gary Thomas (gdt@linuxppc.org) @@ -28,6 +28,8 @@ #include #include #include +#include +#include .text .globl _stext @@ -109,25 +111,19 @@ mtspr MI_AP, r8 mtspr MD_AP, r8 -/* We will get these from a configuration file as soon as I verify - * the extraneous bits don't cause problems in the TLB. - */ -#if defined(CONFIG_MBX) || defined(CONFIG_RPXLITE) -#define BOOT_IMMR 0xfa000000 -#endif -#ifdef CONFIG_BSEIP -#define BOOT_IMMR 0xff000000 -#endif - /* Map another 8 MByte at 0xfa000000 to get the processor + /* Map another 8 MByte at the IMMR to get the processor * internal registers (among other things). */ - lis r8, BOOT_IMMR@h /* Create vaddr for TLB */ + mfspr r9, 638 /* Get current IMMR */ + andis. r9, r9, 0xff80 /* Get 8Mbyte boundary */ + + mr r8, r9 /* Create vaddr for TLB */ ori r8, r8, MD_EVALID /* Mark it valid */ mtspr MD_EPN, r8 li r8, MD_PS8MEG /* Set 8M byte page */ ori r8, r8, MD_SVALID /* Make it valid */ mtspr MD_TWC, r8 - lis r8, BOOT_IMMR@h /* Create paddr for TLB */ + mr r8, r9 /* Create paddr for TLB */ ori r8, r8, MI_BOOTINIT|0x2 /* Inhibit cache -- Cort */ mtspr MD_RPN, r8 @@ -301,6 +297,8 @@ li r20,MSR_KERNEL li r4,0 bl transfer_to_handler + .globl do_IRQ_intercept +do_IRQ_intercept: .long do_IRQ; .long ret_from_except @@ -335,7 +333,17 @@ */ STD_EXCEPTION(0x800, FPUnavailable, UnknownException) - STD_EXCEPTION(0x900, Decrementer, timer_interrupt) + . = 0x900 +Decrementer: + EXCEPTION_PROLOG + addi r3,r1,STACK_FRAME_OVERHEAD + li r20,MSR_KERNEL + bl transfer_to_handler + .globl timer_interrupt_intercept +timer_interrupt_intercept: + .long timer_interrupt + .long ret_from_except + STD_EXCEPTION(0xa00, Trap_0a, UnknownException) STD_EXCEPTION(0xb00, Trap_0b, UnknownException) @@ -553,7 +561,6 @@ mtcr r21 lwz r21, 4(r0) b DataAccess -#endif /* CONFIG_8xx */ STD_EXCEPTION(0x1500, Trap_15, UnknownException) STD_EXCEPTION(0x1600, Trap_16, UnknownException) diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/i8259.c linux/arch/ppc/kernel/i8259.c --- v2.3.19/linux/arch/ppc/kernel/i8259.c Tue May 11 08:24:32 1999 +++ linux/arch/ppc/kernel/i8259.c Thu Oct 7 10:17:08 1999 @@ -96,7 +96,6 @@ " i8259 ", NULL, NULL, - NULL, i8259_unmask_irq, i8259_mask_irq, i8259_mask_and_ack_irq, diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/idle.c linux/arch/ppc/kernel/idle.c --- v2.3.19/linux/arch/ppc/kernel/idle.c Fri Sep 10 23:57:28 1999 +++ linux/arch/ppc/kernel/idle.c Thu Oct 7 10:17:08 1999 @@ -1,5 +1,5 @@ /* - * $Id: idle.c,v 1.66 1999/09/05 11:56:30 paulus Exp $ + * $Id: idle.c,v 1.67 1999/09/10 05:05:47 paulus Exp $ * * Idle daemon for PowerPC. Idle daemon will handle any action * that needs to be taken when the system becomes idle. @@ -73,7 +73,7 @@ * SMP entry into the idle task - calls the same thing as the * non-smp versions. -- Cort */ -int cpu_idle() +int cpu_idle(void) { idled(); return 0; diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/indirect_pci.c linux/arch/ppc/kernel/indirect_pci.c --- v2.3.19/linux/arch/ppc/kernel/indirect_pci.c Tue May 11 08:24:32 1999 +++ linux/arch/ppc/kernel/indirect_pci.c Thu Oct 7 10:17:08 1999 @@ -19,7 +19,7 @@ int indirect_pcibios_read_config_byte(unsigned char bus, unsigned char dev_fn, unsigned char offset, unsigned char *val) { - unsigned flags; + unsigned long flags; save_flags(flags); cli(); @@ -35,7 +35,7 @@ int indirect_pcibios_read_config_word(unsigned char bus, unsigned char dev_fn, unsigned char offset, unsigned short *val) { - unsigned flags; + unsigned long flags; if (offset&1) return PCIBIOS_BAD_REGISTER_NUMBER; @@ -53,7 +53,7 @@ int indirect_pcibios_read_config_dword(unsigned char bus, unsigned char dev_fn, unsigned char offset, unsigned int *val) { - unsigned flags; + unsigned long flags; if (offset&3) return PCIBIOS_BAD_REGISTER_NUMBER; @@ -71,7 +71,7 @@ int indirect_pcibios_write_config_byte(unsigned char bus, unsigned char dev_fn, unsigned char offset, unsigned char val) { - unsigned flags; + unsigned long flags; save_flags(flags); cli(); @@ -87,7 +87,7 @@ int indirect_pcibios_write_config_word(unsigned char bus, unsigned char dev_fn, unsigned char offset, unsigned short val) { - unsigned flags; + unsigned long flags; if (offset&1) return PCIBIOS_BAD_REGISTER_NUMBER; @@ -105,7 +105,7 @@ int indirect_pcibios_write_config_dword(unsigned char bus, unsigned char dev_fn, unsigned char offset, unsigned int val) { - unsigned flags; + unsigned long flags; if (offset&3) return PCIBIOS_BAD_REGISTER_NUMBER; diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/irq.c linux/arch/ppc/kernel/irq.c --- v2.3.19/linux/arch/ppc/kernel/irq.c Fri Sep 10 23:57:28 1999 +++ linux/arch/ppc/kernel/irq.c Thu Oct 7 10:17:08 1999 @@ -1,5 +1,5 @@ /* - * $Id: irq.c,v 1.109 1999/09/05 11:56:31 paulus Exp $ + * $Id: irq.c,v 1.113 1999/09/17 17:22:56 cort Exp $ * * arch/ppc/kernel/irq.c * @@ -79,8 +79,8 @@ #define NR_MASK_WORDS ((NR_IRQS + 31) / 32) +struct irqdesc irq_desc[NR_IRQS] = {{0, 0}, }; int ppc_spurious_interrupts = 0; - unsigned int ppc_local_bh_count[NR_CPUS]; unsigned int ppc_local_irq_count[NR_CPUS]; struct irqaction *ppc_irq_action[NR_IRQS]; @@ -124,9 +124,16 @@ kfree(ptr); } -struct irqdesc irq_desc[NR_IRQS] = {{0, 0}, }; - +#ifndef CONFIG_8xx int request_irq(unsigned int irq, void (*handler)(int, void *, struct pt_regs *), +#else +/* Name change so we can catch standard drivers that potentially mess up + * the internal interrupt controller on 8xx and 82xx. Just bear with me, + * I don't like this either and I am searching a better solution. For + * now, this is what I need. -- Dan + */ +int request_8xxirq(unsigned int irq, void (*handler)(int, void *, struct pt_regs *), +#endif unsigned long irqflags, const char * devname, void *dev_id) { struct irqaction *old, **p, *action; @@ -186,7 +193,11 @@ void free_irq(unsigned int irq, void *dev_id) { +#ifndef CONFIG_8xx request_irq(irq, NULL, 0, NULL, dev_id); +#else + request_8xxirq(irq, NULL, 0, NULL, dev_id); +#endif } /* XXX should implement irq disable depth like on intel */ @@ -277,12 +288,28 @@ asmlinkage void do_IRQ(struct pt_regs *regs, int isfake) { int cpu = smp_processor_id(); + int irq; + + hardirq_enter( cpu ); - hardirq_enter(cpu); - ppc_md.do_IRQ(regs, cpu, isfake); - hardirq_exit(cpu); + /* every arch is required to have a get_irq -- Cort */ + irq = ppc_md.get_irq( regs ); + if ( irq < 0 ) + { + printk(KERN_DEBUG "Bogus interrupt %d from PC = %lx\n", + irq, regs->nip); + ppc_spurious_interrupts++; + return; + } + ppc_irq_dispatch_handler( regs, irq ); + if ( ppc_md.post_irq ) + ppc_md.post_irq( irq ); + + hardirq_exit( cpu ); } + + unsigned long probe_irq_on (void) { return 0; @@ -469,7 +496,7 @@ */ void __global_cli(void) { - unsigned int flags; + unsigned long flags; __save_flags(flags); if (flags & (1 << 15)) { diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/local_irq.h linux/arch/ppc/kernel/local_irq.h --- v2.3.19/linux/arch/ppc/kernel/local_irq.h Tue Aug 31 17:29:13 1999 +++ linux/arch/ppc/kernel/local_irq.h Thu Oct 7 10:17:08 1999 @@ -4,28 +4,9 @@ #include #include +#include void ppc_irq_dispatch_handler(struct pt_regs *regs, int irq); - -/* Structure describing interrupts */ -struct hw_interrupt_type { - const char * typename; - void (*startup)(unsigned int irq); - void (*shutdown)(unsigned int irq); - void (*handle)(unsigned int irq, struct pt_regs * regs); - void (*enable)(unsigned int irq); - void (*disable)(unsigned int irq); - void (*mask_and_ack)(unsigned int irq); - int irq_offset; -}; - -struct irqdesc { - struct irqaction *action; - struct hw_interrupt_type *ctl; -}; - -extern struct irqdesc irq_desc[NR_IRQS]; - #define NR_MASK_WORDS ((NR_IRQS + 31) / 32) diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/m8xx_setup.c linux/arch/ppc/kernel/m8xx_setup.c --- v2.3.19/linux/arch/ppc/kernel/m8xx_setup.c Wed Dec 31 16:00:00 1969 +++ linux/arch/ppc/kernel/m8xx_setup.c Thu Oct 7 10:17:08 1999 @@ -0,0 +1,521 @@ +/* + * $Id: m8xx_setup.c,v 1.4 1999/09/18 18:40:36 dmalek Exp $ + * + * linux/arch/ppc/kernel/setup.c + * + * Copyright (C) 1995 Linus Torvalds + * Adapted from 'alpha' version by Gary Thomas + * Modified by Cort Dougan (cort@cs.nmt.edu) + * Modified for MBX using prep/chrp/pmac functions by Dan (dmalek@jlc.net) + * Further modified for generic 8xx by Dan. + */ + +/* + * bootup setup stuff.. + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include "time.h" +#include "ppc8xx_pic.h" + +static int m8xx_set_rtc_time(unsigned long time); +unsigned long m8xx_get_rtc_time(void); +void m8xx_calibrate_decr(void); + +#if 0 +extern int mackbd_setkeycode(unsigned int scancode, unsigned int keycode); +extern int mackbd_getkeycode(unsigned int scancode); +extern int mackbd_pretranslate(unsigned char scancode, char raw_mode); +extern int mackbd_translate(unsigned char scancode, unsigned char *keycode, + char raw_mode); +extern char mackbd_unexpected_up(unsigned char keycode); +extern void mackbd_leds(unsigned char leds); +extern void mackbd_init_hw(void); +#endif + +extern unsigned long loops_per_sec; + +unsigned char __res[sizeof(bd_t)]; +unsigned long empty_zero_page[1024]; + +#ifdef CONFIG_BLK_DEV_RAM +extern int rd_doload; /* 1 = load ramdisk, 0 = don't load */ +extern int rd_prompt; /* 1 = prompt for ramdisk, 0 = don't prompt */ +extern int rd_image_start; /* starting block # of image */ +#endif + +extern char saved_command_line[256]; + +extern unsigned long find_available_memory(void); +extern void m8xx_cpm_reset(uint); + +void __init adbdev_init(void) +{ +} + +void __init +m8xx_setup_arch(unsigned long * memory_start_p, unsigned long * memory_end_p) +{ + int cpm_page; + extern char cmd_line[]; + + cpm_page = *memory_start_p; + *memory_start_p += PAGE_SIZE; + + printk("Boot arguments: %s\n", cmd_line); + + /* Reset the Communication Processor Module. + */ + m8xx_cpm_reset(cpm_page); + +#ifdef notdef + ROOT_DEV = to_kdev_t(0x0301); /* hda1 */ +#endif + +#ifdef CONFIG_BLK_DEV_INITRD +#if 0 + ROOT_DEV = to_kdev_t(0x0200); /* floppy */ + rd_prompt = 1; + rd_doload = 1; + rd_image_start = 0; +#endif + /* initrd_start and size are setup by boot/head.S and kernel/head.S */ + if ( initrd_start ) + { + if (initrd_end > *memory_end_p) + { + printk("initrd extends beyond end of memory " + "(0x%08lx > 0x%08lx)\ndisabling initrd\n", + initrd_end,*memory_end_p); + initrd_start = 0; + } + } +#endif +} + +void +abort(void) +{ +#ifdef CONFIG_XMON + extern void xmon(void *); + xmon(0); +#endif + machine_restart(NULL); +} + +/* The decrementer counts at the system (internal) clock frequency divided by + * sixteen, or external oscillator divided by four. We force the processor + * to use system clock divided by sixteen. + */ +void __init m8xx_calibrate_decr(void) +{ + bd_t *binfo = (bd_t *)__res; + int freq, fp, divisor; + + /* Unlock the SCCR. + */ + ((volatile immap_t *)IMAP_ADDR)->im_clkrstk.cark_sccrk = ~KAPWR_KEY; + ((volatile immap_t *)IMAP_ADDR)->im_clkrstk.cark_sccrk = KAPWR_KEY; + + /* Force all 8xx processors to use divide by 16 processor clock. + */ + ((volatile immap_t *)IMAP_ADDR)->im_clkrst.car_sccr |= 0x02000000; + + /* Processor frequency is MHz. + * The value 'fp' is the number of decrementer ticks per second. + */ + fp = (binfo->bi_intfreq * 1000000) / 16; + freq = fp*60; /* try to make freq/1e6 an integer */ + divisor = 60; + printk("time_init: decrementer frequency = %d/%d\n", freq, divisor); + decrementer_count = freq / HZ / divisor; + count_period_num = divisor; + count_period_den = freq / 1000000; +} + +/* A place holder for time base interrupts, if they are ever enabled. +*/ +void timebase_interrupt(int irq, void * dev, struct pt_regs * regs) +{ + printk("timebase_interrupt()\n"); +} + +/* The RTC on the MPC8xx is an internal register. + * We want to protect this during power down, so we need to unlock, + * modify, and re-lock. + */ +static int +m8xx_set_rtc_time(unsigned long time) +{ + ((volatile immap_t *)IMAP_ADDR)->im_sitk.sitk_rtck = KAPWR_KEY; + ((volatile immap_t *)IMAP_ADDR)->im_sit.sit_rtc = time; + ((volatile immap_t *)IMAP_ADDR)->im_sitk.sitk_rtck = ~KAPWR_KEY; + return(0); +} + +unsigned long __init +m8xx_get_rtc_time(void) +{ + /* First, unlock all of the registers we are going to modify. + * To protect them from corruption during power down, registers + * that are maintained by keep alive power are "locked". To + * modify these registers we have to write the key value to + * the key location associated with the register. + * Some boards power up with these unlocked, while others + * are locked. Writing anything (including the unlock code?) + * to the unlocked registers will lock them again. So, here + * we guarantee the registers are locked, then we unlock them + * for our use. + */ + ((volatile immap_t *)IMAP_ADDR)->im_sitk.sitk_tbscrk = ~KAPWR_KEY; + ((volatile immap_t *)IMAP_ADDR)->im_sitk.sitk_rtcsck = ~KAPWR_KEY; + ((volatile immap_t *)IMAP_ADDR)->im_sitk.sitk_tbk = ~KAPWR_KEY; + ((volatile immap_t *)IMAP_ADDR)->im_sitk.sitk_tbscrk = KAPWR_KEY; + ((volatile immap_t *)IMAP_ADDR)->im_sitk.sitk_rtcsck = KAPWR_KEY; + ((volatile immap_t *)IMAP_ADDR)->im_sitk.sitk_tbk = KAPWR_KEY; + + /* Disable the RTC one second and alarm interrupts. + */ + ((volatile immap_t *)IMAP_ADDR)->im_sit.sit_rtcsc &= + ~(RTCSC_SIE | RTCSC_ALE); + + /* Enabling the decrementer also enables the timebase interrupts + * (or from the other point of view, to get decrementer interrupts + * we have to enable the timebase). The decrementer interrupt + * is wired into the vector table, nothing to do here for that. + */ + ((volatile immap_t *)IMAP_ADDR)->im_sit.sit_tbscr = + ((mk_int_int_mask(DEC_INTERRUPT) << 8) | + (TBSCR_TBF | TBSCR_TBE)); + if (request_8xxirq(DEC_INTERRUPT, timebase_interrupt, 0, "tbint", NULL) != 0) + panic("Could not allocate timer IRQ!"); + + /* Get time from the RTC. + */ + return((unsigned long)(((immap_t *)IMAP_ADDR)->im_sit.sit_rtc)); +} + +void +m8xx_restart(char *cmd) +{ + extern void m8xx_gorom(void); + + m8xx_gorom(); +} + +void +m8xx_power_off(void) +{ + m8xx_restart(NULL); +} + +void +m8xx_halt(void) +{ + m8xx_restart(NULL); +} + + +int m8xx_setup_residual(char *buffer) +{ + int len = 0; + bd_t *bp; + + bp = (bd_t *)__res; + + len += sprintf(len+buffer,"clock\t\t: %dMHz\n" + "bus clock\t: %dMHz\n", + bp->bi_intfreq /*/ 1000000*/, + bp->bi_busfreq /*/ 1000000*/); + + return len; +} + +/* Initialize the internal interrupt controller. The number of + * interrupts supported can vary with the processor type, and the + * 82xx family can have up to 64. + * External interrupts can be either edge or level triggered, and + * need to be initialized by the appropriate driver. + */ +void __init +m8xx_init_IRQ(void) +{ + int i; + void cpm_interrupt_init(void); + + ppc8xx_pic.irq_offset = 0; + for ( i = 0 ; i < NR_SIU_INTS ; i++ ) + irq_desc[i].ctl = &ppc8xx_pic; + + /* We could probably incorporate the CPM into the multilevel + * interrupt structure. + */ + cpm_interrupt_init(); + unmask_irq(CPM_INTERRUPT); + +#if defined(CONFIG_PCI) + for ( i = NR_SIU_INTS ; i < (NR_SIU_INTS + NR_8259_INTS) ; i++ ) + irq_desc[i].ctl = &i8259_pic; + i8259_pic.irq_offset = NR_SIU_INTS; + i8259_init(); + request_8xxirq(ISA_BRIDGE_INT, mbx_i8259_action, 0, "8259 cascade", NULL); + enable_irq(ISA_BRIDGE_INT); +#endif +} + +#if defined(CONFIG_BLK_DEV_IDE) || defined(CONFIG_BLK_DEV_IDE_MODULE) + +/* Define this to make a PCMCIA ATA Flash card work. +*/ +#define ATA_FLASH 1 + +/* + * IDE stuff. + */ +void +m8xx_ide_insw(ide_ioreg_t port, void *buf, int ns) +{ +#ifdef ATA_FLASH + ide_insw(port, buf, ns); +#else + ide_insw(port+_IO_BASE, buf, ns); +#endif +} + +void +m8xx_ide_outsw(ide_ioreg_t port, void *buf, int ns) +{ +#ifdef ATA_FLASH + ide_outsw(port, buf, ns); +#else + ide_outsw(port+_IO_BASE, buf, ns); +#endif +} + +int +m8xx_ide_default_irq(ide_ioreg_t base) +{ +#ifdef ATA_FLASH + return PCMCIA_INTERRUPT; +#else + return 14; +#endif +} + +ide_ioreg_t +m8xx_ide_default_io_base(int index) +{ + return index; +} + +int +m8xx_ide_check_region(ide_ioreg_t from, unsigned int extent) +{ + return 0; +} + +void +m8xx_ide_request_region(ide_ioreg_t from, + unsigned int extent, + const char *name) +{ +} + +void +m8xx_ide_release_region(ide_ioreg_t from, + unsigned int extent) +{ +} + +int +m8xx_ide_request_irq(unsigned int irq, + void (*handler)(int, void *, struct pt_regs *), + unsigned long flags, + const char *device, + void *dev_id) +{ +#ifdef ATA_FLASH + return request_8xxirq(irq, handler, flags, device, dev_id); +#else + return request_irq(irq, handler, flags, device, dev_id); +#endif +} + +void +m8xx_ide_fix_driveid(struct hd_driveid *id) +{ + ppc_generic_ide_fix_driveid(id); +} + +/* We can use an external IDE controller or wire the IDE interface to + * the internal PCMCIA controller. + */ +void __init m8xx_ide_init_hwif_ports(ide_ioreg_t *p, ide_ioreg_t base, int *irq) +{ + ide_ioreg_t port = base; + int i; +#ifdef ATA_FLASH + volatile pcmconf8xx_t *pcmp; +#endif + +#ifdef ATA_FLASH + *p = 0; + *irq = 0; + + if (base != 0) /* Only map the first ATA flash drive */ + return; + + pcmp = (pcmconf8xx_t *)(&(((immap_t *)IMAP_ADDR)->im_pcmcia)); + if (pcmp->pcmc_pipr & 0x18000000) + return; /* No card in slot */ + + base = (unsigned long) ioremap(PCMCIA_MEM_ADDR, 0x200); + + /* For the M-Systems ATA card, the first 8 registers map 1:1. + * The following register, control/Altstatus, is located at 0x0e. + * Following that, the irq offset, is not used, so we place it in + * an unused location, 0x0a. + */ + *p++ = base + 8; + for (i = 1; i < 8; ++i) + *p++ = base + i; + *p++ = base + 0x0e; /* control/altstatus */ + *p = base + 0x0a; /* IRQ, not used */ + if (irq) + *irq = PCMCIA_INTERRUPT; + + /* Configure the interface for this interrupt. + */ + pcmp->pcmc_pgcra = (mk_int_int_mask(PCMCIA_INTERRUPT) << 24) | + (mk_int_int_mask(PCMCIA_INTERRUPT) << 16); + + /* Enable status change interrupt from slot A. + */ + pcmp->pcmc_per = 0xff100000; + pcmp->pcmc_pscr = ~0; +#else + + /* Just a regular IDE drive on some I/O port. + */ + i = 8; + while (i--) + *p++ = port++; + *p++ = base + 0x206; + if (irq != NULL) + *irq = 0; +#endif +} +#endif + +void __init +m8xx_init(unsigned long r3, unsigned long r4, unsigned long r5, + unsigned long r6, unsigned long r7) +{ + + if ( r3 ) + memcpy( (void *)__res,(void *)(r3+KERNELBASE), sizeof(bd_t) ); + +#ifdef CONFIG_PCI + m8xx_setup_pci_ptrs(); +#endif + +#ifdef CONFIG_BLK_DEV_INITRD + /* take care of initrd if we have one */ + if ( r4 ) + { + initrd_start = r4 + KERNELBASE; + initrd_end = r5 + KERNELBASE; + } +#endif /* CONFIG_BLK_DEV_INITRD */ + /* take care of cmd line */ + if ( r6 ) + { + + *(char *)(r7+KERNELBASE) = 0; + strcpy(cmd_line, (char *)(r6+KERNELBASE)); + } + + ppc_md.setup_arch = m8xx_setup_arch; + ppc_md.setup_residual = m8xx_setup_residual; + ppc_md.get_cpuinfo = NULL; + ppc_md.irq_cannonicalize = NULL; + ppc_md.init_IRQ = m8xx_init_IRQ; + ppc_md.get_irq = m8xx_get_irq; + ppc_md.init = NULL; + + ppc_md.restart = m8xx_restart; + ppc_md.power_off = m8xx_power_off; + ppc_md.halt = m8xx_halt; + + ppc_md.time_init = NULL; + ppc_md.set_rtc_time = m8xx_set_rtc_time; + ppc_md.get_rtc_time = m8xx_get_rtc_time; + ppc_md.calibrate_decr = m8xx_calibrate_decr; + +#if 0 + ppc_md.kbd_setkeycode = pckbd_setkeycode; + ppc_md.kbd_getkeycode = pckbd_getkeycode; + ppc_md.kbd_pretranslate = pckbd_pretranslate; + ppc_md.kbd_translate = pckbd_translate; + ppc_md.kbd_unexpected_up = pckbd_unexpected_up; + ppc_md.kbd_leds = pckbd_leds; + ppc_md.kbd_init_hw = pckbd_init_hw; +#ifdef CONFIG_MAGIC_SYSRQ + ppc_md.kbd_sysrq_xlate = pckbd_sysrq_xlate; +#endif +#else + ppc_md.kbd_setkeycode = NULL; + ppc_md.kbd_getkeycode = NULL; + ppc_md.kbd_translate = NULL; + ppc_md.kbd_unexpected_up = NULL; + ppc_md.kbd_leds = NULL; + ppc_md.kbd_init_hw = NULL; +#ifdef CONFIG_MAGIC_SYSRQ + ppc_md.kbd_sysrq_xlate = NULL; +#endif +#endif + +#if defined(CONFIG_BLK_DEV_IDE) || defined(CONFIG_BLK_DEV_IDE_MODULE) + ppc_ide_md.insw = m8xx_ide_insw; + ppc_ide_md.outsw = m8xx_ide_outsw; + ppc_ide_md.default_irq = m8xx_ide_default_irq; + ppc_ide_md.default_io_base = m8xx_ide_default_io_base; + ppc_ide_md.check_region = m8xx_ide_check_region; + ppc_ide_md.request_region = m8xx_ide_request_region; + ppc_ide_md.release_region = m8xx_ide_release_region; + ppc_ide_md.fix_driveid = m8xx_ide_fix_driveid; + ppc_ide_md.ide_init_hwif = m8xx_ide_init_hwif_ports; + ppc_ide_md.ide_request_irq = m8xx_ide_request_irq; + + ppc_ide_md.io_base = _IO_BASE; +#endif +} diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/misc.S linux/arch/ppc/kernel/misc.S --- v2.3.19/linux/arch/ppc/kernel/misc.S Fri Sep 10 23:57:28 1999 +++ linux/arch/ppc/kernel/misc.S Thu Oct 7 10:17:08 1999 @@ -45,17 +45,34 @@ mtlr r0 blr -_GLOBAL(__cli) +/* void __no_use_save_flags(unsigned long *flags) */ +_GLOBAL(__no_use_save_flags) + mfmsr r4 + stw r4,0(r3) + blr + +/* void __no_use_restore_flags(unsigned long flags) */ +_GLOBAL(__no_use_restore_flags) + andi. r4,r3,MSR_EE + bne 10f + lis r4,ppc_n_lost_interrupts@ha + lwz r4,ppc_n_lost_interrupts@l(r4) + cmpi 0,r4,0 /* lost interrupts to process first? */ + bne- do_lost_interrupts +10: sync + mtmsr r3 + isync + blr + +_GLOBAL(__no_use_cli) mfmsr r0 /* Get current interrupt state */ rlwinm r3,r0,16+1,32-1,31 /* Extract old value of 'EE' */ - li r4,0 /* Need [unsigned] value of MSR_EE */ - ori r4,r4,MSR_EE /* Set to turn off bit */ - andc r0,r0,r4 /* Clears bit in (r4) */ + rlwinm r0,r0,0,17,15 /* clear MSR_EE in r0 */ sync /* Some chip revs have problems here... */ mtmsr r0 /* Update machine state */ blr /* Done */ -_GLOBAL(__sti) +_GLOBAL(__no_use_sti) lis r4,ppc_n_lost_interrupts@ha lwz r4,ppc_n_lost_interrupts@l(r4) mfmsr r3 /* Get current state */ @@ -472,6 +489,7 @@ * * ashrdi3: XXXYYY/ZZZAAA -> SSSXXX/YYYZZZ * ashldi3: XXXYYY/ZZZAAA -> YYYZZZ/AAA000 + * lshrdi3: XXXYYY/ZZZAAA -> 000XXX/YYYZZZ */ _GLOBAL(__ashrdi3) li r6,32 @@ -481,7 +499,7 @@ or r4,r4,r7 /* YYYZZZ */ sraw r3,r3,r5 /* SSSXXX */ blr - + _GLOBAL(__ashldi3) li r6,32 sub r6,r6,r5 @@ -491,6 +509,15 @@ or r3,r3,r7 /* YYYZZZ */ blr +_GLOBAL(__lshrdi3) + li r6,32 + sub r6,r6,r5 + slw r7,r3,r6 /* isolate YYY */ + srw r4,r4,r5 /* isolate ZZZ */ + or r4,r4,r7 /* YYYZZZ */ + srw r3,r3,r5 /* 000XXX */ + blr + _GLOBAL(abs) cmpi 0,r3,0 bge 10f @@ -553,36 +580,42 @@ Author: Terry Greeniaus (tgree@phys.ualberta.ca) Please e-mail updates to this file to me, thanks! */ +/* Usage: + + When setting the L2CR register, you must do a few special + things. If you are enabling the cache, you must perform a + global invalidate. If you are disabling the cache, you must + flush the cache contents first. This routine takes care of + doing these things. When first enabling the cache, make sure + you pass in the L2CR you want, as well as passing in the + global invalidate bit set. A global invalidate will only be + performed if the L2I bit is set in applyThis. When enabling + the cache, you should also set the L2E bit in applyThis. If + you want to modify the L2CR contents after the cache has been + enabled, the recommended procedure is to first call + __setL2CR(0) to disable the cache and then call it again with + the new values for L2CR. Examples: + + _setL2CR(0) - disables the cache + _setL2CR(0xB3A04000) - enables my G3 upgrade card: + - L2E set to turn on the cache + - L2SIZ set to 1MB + - L2CLK set to 1:1 + - L2RAM set to pipelined synchronous late-write + - L2I set to perform a global invalidation + - L2OH set to 0.5 nS + - L2DF set because this upgrade card + requires it + + A similar call should work for your card. You need to know + the correct setting for your card and then place them in the + fields I have outlined above. Other fields support optional + features, such as L2DO which caches only data, or L2TS which + causes cache pushes from the L1 cache to go to the L2 cache + instead of to main memory. +*/ _GLOBAL(_set_L2CR) - /* Usage: - - When setting the L2CR register, you must do a few special things. If you are enabling the - cache, you must perform a global invalidate. If you are disabling the cache, you must - flush the cache contents first. This routine takes care of doing these things. When first - enabling the cache, make sure you pass in the L2CR you want, as well as passing in the - global invalidate bit set. A global invalidate will only be performed if the L2I bit is set - in applyThis. When enabling the cache, you should also set the L2E bit in applyThis. If you - want to modify the L2CR contents after the cache has been enabled, the recommended - procedure is to first call __setL2CR(0) to disable the cache and then call it again with - the new values for L2CR. Examples: - - _setL2CR(0) - disables the cache - _setL2CR(0xB3A04000) - enables my G3 upgrade card: - - L2E set to turn on the cache - - L2SIZ set to 1MB - - L2CLK set to 1:1 - - L2RAM set to pipelined syncronous late-write - - L2I set to perform a global invalidation - - L2OH set to 0.5 nS - - L2DF set because this upgrade card requires it - - A similar call should work for your card. You need to know the correct setting for your - card and then place them in the fields I have outlined above. Other fields support optional - features, such as L2DO which caches only data, or L2TS which causes cache pushes from - the L1 cache to go to the L2 cache instead of to main memory. - */ - /* Make sure this is a 750 chip */ mfspr r4,PVR rlwinm r4,r4,16,16,31 @@ -594,76 +627,74 @@ thisIs750: /* Get the current enable bit of the L2CR into r4 */ mfspr r4,L2CR - rlwinm r4,r4,0,0,0 + mfmsr r7 /* See if we want to perform a global inval this time. */ - rlwinm r6,r3,0,10,10 /* r6 contains the new invalidate bit */ - rlwinm. r5,r3,0,0,0 /* r5 contains the new enable bit */ - rlwinm r3,r3,0,11,9 /* Turn off the invalidate bit */ - rlwinm r3,r3,0,1,31 /* Turn off the enable bit */ - or r3,r3,r4 /* Keep the enable bit the same as it was for now. */ - bne dontDisableCache /* Only disable the cache if L2CRApply has the enable bit off */ + rlwinm r6,r3,0,10,10 /* r6 contains the new invalidate bit */ + rlwinm. r5,r3,0,0,0 /* r5 contains the new enable bit */ + rlwinm r3,r3,0,11,9 /* Turn off the invalidate bit */ + rlwimi r3,r4,0,0,0 /* Keep the enable bit the same as it was. */ + bne dontDisableCache /* Only disable the cache if L2CRApply + has the enable bit off */ disableCache: - /* Disable the cache. First, we turn off data relocation. */ - mfmsr r7 - rlwinm r4,r7,0,28,26 /* Turn off DR bit */ - rlwinm r4,r4,0,17,15 /* Turn off EE bit - an external exception while we are flushing - the cache is fatal (comment this line and see!) */ + /* Disable the cache. First, we turn off interrupts. + An interrupt while we are flushing the cache could bring + in data which may not get properly flushed. */ + rlwinm r4,r7,0,17,15 /* Turn off EE bit */ sync mtmsr r4 sync - /* - Now, read the first 2MB of memory to put new data in the cache. - (Actually we only need the size of the L2 cache plus - the size of the L1 cache, but 2MB will cover everything just to be safe). - */ +/* + Now, read the first 2MB of memory to put new data in the cache. + (Actually we only need the size of the L2 cache plus the size + of the L1 cache, but 2MB will cover everything just to be safe). +*/ lis r4,0x0001 mtctr r4 - li r4,0 -loadLoop: - lwzx r0,r0,r4 + lis r4,KERNELBASE@h +1: lwzx r0,r0,r4 addi r4,r4,0x0020 /* Go to start of next cache line */ - bdnz loadLoop + bdnz 1b /* Now, flush the first 2MB of memory */ lis r4,0x0001 mtctr r4 - li r4,0 + lis r4,KERNELBASE@h sync -flushLoop: - dcbf r0,r4 +2: dcbf r0,r4 addi r4,r4,0x0020 /* Go to start of next cache line */ - bdnz flushLoop + bdnz 2b /* Turn off the L2CR enable bit. */ rlwinm r3,r3,0,1,31 - /* Reenable data relocation. */ - sync - mtmsr r7 - sync - dontDisableCache: /* Set up the L2CR configuration bits */ sync mtspr L2CR,r3 sync + + /* Reenable interrupts if necessary. */ + mtmsr r7 + sync + cmplwi r6,0 beq noInval /* Perform a global invalidation */ oris r3,r3,0x0020 sync - mtspr 1017,r3 + mtspr L2CR,r3 sync -invalCompleteLoop: /* Wait for the invalidation to complete */ - mfspr r3,1017 + + /* Wait for the invalidation to complete */ +3: mfspr r3,L2CR rlwinm. r4,r3,0,31,31 - bne invalCompleteLoop + bne 3b - rlwinm r3,r3,0,11,9; /* Turn off the L2I bit */ + rlwinm r3,r3,0,11,9 /* Turn off the L2I bit */ sync mtspr L2CR,r3 sync @@ -672,8 +703,7 @@ /* See if we need to enable the cache */ cmplwi r5,0 beqlr - -enableCache: + /* Enable the cache */ oris r3,r3,0x8000 mtspr L2CR,r3 @@ -967,7 +997,7 @@ .long sys_getresuid /* 165 */ .long sys_query_module .long sys_poll -#ifdef CONFIG_NFSD +#ifdef CONFIG_NFSD .long sys_nfsservctl #else .long sys_ni_syscall diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/open_pic.c linux/arch/ppc/kernel/open_pic.c --- v2.3.19/linux/arch/ppc/kernel/open_pic.c Tue Aug 31 17:29:13 1999 +++ linux/arch/ppc/kernel/open_pic.c Thu Oct 7 10:17:08 1999 @@ -33,7 +33,6 @@ " OpenPIC ", NULL, NULL, - NULL, openpic_enable_irq, openpic_disable_irq, 0, @@ -352,6 +351,13 @@ openpic_write(&OpenPIC->THIS_CPU.IPI_Dispatch(ipi), cpumask); } +void openpic_enable_IPI(u_int ipi) +{ + check_arg_ipi(ipi); + openpic_clearfield(&OpenPIC->Global.IPI_Vector_Priority(ipi), + OPENPIC_MASK); +} + /* * Initialize a timer interrupt (and disable it) * @@ -384,13 +390,13 @@ void openpic_enable_irq(u_int irq) { check_arg_irq(irq); - openpic_clearfield(&OpenPIC->Source[irq].Vector_Priority, OPENPIC_MASK); + openpic_clearfield(&OpenPIC->Source[irq-irq_desc[irq].ctl->irq_offset].Vector_Priority, OPENPIC_MASK); } void openpic_disable_irq(u_int irq) { check_arg_irq(irq); - openpic_setfield(&OpenPIC->Source[irq].Vector_Priority, OPENPIC_MASK); + openpic_setfield(&OpenPIC->Source[irq-irq_desc[irq].ctl->irq_offset].Vector_Priority, OPENPIC_MASK); } /* diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/pci.c linux/arch/ppc/kernel/pci.c --- v2.3.19/linux/arch/ppc/kernel/pci.c Fri Sep 10 23:57:28 1999 +++ linux/arch/ppc/kernel/pci.c Thu Oct 7 12:23:21 1999 @@ -1,5 +1,5 @@ /* - * $Id: pci.c,v 1.60 1999/09/08 03:04:07 cort Exp $ + * $Id: pci.c,v 1.64 1999/09/17 18:01:53 cort Exp $ * Common pmac/prep/chrp pci routines. -- Cort */ @@ -92,7 +92,7 @@ struct resource *pr; if (!r->start) continue; - pr = pci_find_parent_resource(dev, r); + pr = pci_find_parent_resource(dev, r, 0); if (!pr || request_resource(pr, r) < 0) { printk(KERN_ERR "PCI: Address space collision on region %d of device %s\n", idx, dev->name); @@ -117,7 +117,7 @@ return str; } -#ifndef CONFIG_MBX +#ifndef CONFIG_8xx /* Recursively searches any node that is of type PCI-PCI bridge. Without * this, the old code would miss children of P2P bridges and hence not * fix IRQ's for cards located behind P2P bridges. @@ -141,8 +141,3 @@ } } #endif - -int pcibios_assign_resource(struct pci_dev *pdev, int resource) -{ - return 0; -} diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/pmac_pic.c linux/arch/ppc/kernel/pmac_pic.c --- v2.3.19/linux/arch/ppc/kernel/pmac_pic.c Tue Aug 31 17:29:13 1999 +++ linux/arch/ppc/kernel/pmac_pic.c Thu Oct 7 10:17:08 1999 @@ -102,7 +102,6 @@ " PMAC-PIC ", NULL, NULL, - NULL, pmac_unmask_irq, pmac_mask_irq, pmac_mask_and_ack_irq, @@ -113,7 +112,6 @@ " GATWICK ", NULL, NULL, - NULL, pmac_unmask_irq, pmac_mask_irq, pmac_mask_and_ack_irq, @@ -143,6 +141,7 @@ ppc_irq_dispatch_handler( regs, irq ); } +#if 0 void pmac_do_IRQ(struct pt_regs *regs, int cpu, @@ -155,19 +154,13 @@ /* IPI's are a hack on the powersurge -- Cort */ if ( cpu != 0 ) { - if (!isfake) - { #ifdef CONFIG_XMON - static int xmon_2nd; - if (xmon_2nd) - xmon(regs); + static int xmon_2nd; + if (xmon_2nd) + xmon(regs); #endif - smp_message_recv(); - goto out; - } - /* could be here due to a do_fake_interrupt call but we don't - mess with the controller from the second cpu -- Cort */ - goto out; + smp_message_recv(); + return -1; } { @@ -214,11 +207,65 @@ out: #endif /* CONFIG_SMP */ } +#endif + +int +pmac_get_irq(struct pt_regs *regs) +{ + int irq; + unsigned long bits = 0; + +#ifdef __SMP__ + /* IPI's are a hack on the powersurge -- Cort */ + if ( smp_processor_id() != 0 ) + { +#ifdef CONFIG_XMON + static int xmon_2nd; + if (xmon_2nd) + xmon(regs); +#endif + smp_message_recv(); + return -1; + } + + { + unsigned int loops = MAXCOUNT; + while (test_bit(0, &global_irq_lock)) { + if (smp_processor_id() == global_irq_holder) { + printk("uh oh, interrupt while we hold global irq lock!\n"); +#ifdef CONFIG_XMON + xmon(0); +#endif + break; + } + if (loops-- == 0) { + printk("do_IRQ waiting for irq lock (holder=%d)\n", global_irq_holder); +#ifdef CONFIG_XMON + xmon(0); +#endif + } + } + } +#endif /* __SMP__ */ + + for (irq = max_real_irqs - 1; irq > 0; irq -= 32) { + int i = irq >> 5; + bits = ld_le32(&pmac_irq_hw[i]->flag) + | ppc_lost_interrupts[i]; + if (bits == 0) + continue; + irq -= cntlzw(bits); + break; + } + + return irq; +} /* This routine will fix some missing interrupt values in the device tree * on the gatwick mac-io controller used by some PowerBooks */ -static void __init pmac_fix_gatwick_interrupts(struct device_node *gw, int irq_base) +static void __init +pmac_fix_gatwick_interrupts(struct device_node *gw, int irq_base) { struct device_node *node; int count; @@ -362,3 +409,41 @@ request_irq(20, xmon_irq, 0, "NMI - XMON", 0); #endif /* CONFIG_XMON */ } + +#ifdef CONFIG_PMAC_PBOOK +/* + * These procedures are used in implementing sleep on the powerbooks. + * sleep_save_intrs() saves the states of all interrupt enables + * and disables all interupts except for the nominated one. + * sleep_restore_intrs() restores the states of all interrupt enables. + */ +unsigned int sleep_save_mask[2]; + +void +sleep_save_intrs(int viaint) +{ + sleep_save_mask[0] = ppc_cached_irq_mask[0]; + sleep_save_mask[1] = ppc_cached_irq_mask[1]; + ppc_cached_irq_mask[0] = 0; + ppc_cached_irq_mask[1] = 0; + set_bit(viaint, ppc_cached_irq_mask); + out_le32(&pmac_irq_hw[0]->enable, ppc_cached_irq_mask[0]); + if (max_real_irqs > 32) + out_le32(&pmac_irq_hw[1]->enable, ppc_cached_irq_mask[1]); + mb(); +} + +void +sleep_restore_intrs(void) +{ + int i; + + out_le32(&pmac_irq_hw[0]->enable, 0); + if (max_real_irqs > 32) + out_le32(&pmac_irq_hw[1]->enable, 0); + mb(); + for (i = 0; i < max_real_irqs; ++i) + if (test_bit(i, sleep_save_mask)) + pmac_unmask_irq(i); +} +#endif /* CONFIG_PMAC_PBOOK */ diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/pmac_pic.h linux/arch/ppc/kernel/pmac_pic.h --- v2.3.19/linux/arch/ppc/kernel/pmac_pic.h Thu Apr 29 12:39:01 1999 +++ linux/arch/ppc/kernel/pmac_pic.h Thu Oct 7 10:17:08 1999 @@ -6,10 +6,7 @@ extern struct hw_interrupt_type pmac_pic; void pmac_pic_init(void); -void pmac_do_IRQ(struct pt_regs *regs, - int cpu, - int isfake); - +int pmac_get_irq(struct pt_regs *regs); +void pmac_post_irq(int); #endif /* _PPC_KERNEL_PMAC_PIC_H */ - diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/pmac_setup.c linux/arch/ppc/kernel/pmac_setup.c --- v2.3.19/linux/arch/ppc/kernel/pmac_setup.c Tue Aug 31 17:29:13 1999 +++ linux/arch/ppc/kernel/pmac_setup.c Thu Oct 7 10:17:08 1999 @@ -43,6 +43,9 @@ #include #include #include +#include +#include +#include #include #include @@ -51,9 +54,6 @@ #include #include #include -#include -#include -#include #include #include #include @@ -166,16 +166,24 @@ /* find ram info */ np = find_devices("memory"); if (np != 0) { + int n; struct reg_property *reg = (struct reg_property *) - get_property(np, "reg", NULL); + get_property(np, "reg", &n); + if (reg != 0) { - len += sprintf(buffer+len, "memory\t\t: %dMB\n", - reg->size >> 20); + unsigned long total = 0; + + for (n /= sizeof(struct reg_property); n > 0; --n) + total += (reg++)->size; + len += sprintf(buffer+len, "memory\t\t: %luMB\n", + total >> 20); } } /* Checks "l2cr-value" property in the registry */ np = find_devices("cpus"); + if (np == 0) + np = find_type_devices("cpu"); if (np != 0) { unsigned int *l2cr = (unsigned int *) get_property(np, "l2cr-value", NULL); @@ -267,6 +275,8 @@ /* Checks "l2cr-value" property in the registry */ if ( (_get_PVR() >> 16) == 8) { struct device_node *np = find_devices("cpus"); + if (np == 0) + np = find_type_devices("cpu"); if (np != 0) { unsigned int *l2cr = (unsigned int *) get_property(np, "l2cr-value", NULL); @@ -290,8 +300,12 @@ zs_kgdb_hook(0); #endif +#ifdef CONFIG_ADB_CUDA find_via_cuda(); +#endif +#ifdef CONFIG_ADB_PMU find_via_pmu(); +#endif #ifdef CONFIG_DUMMY_CONSOLE conswitchp = &dummy_con; @@ -360,9 +374,10 @@ void __init pmac_init2(void) { - adb_init(); pmac_nvram_init(); +#ifdef CONFIG_PMAC_PBOOK media_bay_init(); +#endif } #ifdef CONFIG_SCSI @@ -470,19 +485,24 @@ void pmac_restart(char *cmd) { +#ifdef CONFIG_ADB_CUDA struct adb_request req; +#endif /* CONFIG_ADB_CUDA */ - switch (adb_hardware) { - case ADB_VIACUDA: + switch (sys_ctrler) { +#ifdef CONFIG_ADB_CUDA + case SYS_CTRLER_CUDA: cuda_request(&req, NULL, 2, CUDA_PACKET, CUDA_RESET_SYSTEM); for (;;) cuda_poll(); break; - - case ADB_VIAPMU: +#endif /* CONFIG_ADB_CUDA */ +#ifdef CONFIG_ADB_PMU + case SYS_CTRLER_PMU: pmu_restart(); break; +#endif /* CONFIG_ADB_PMU */ default: } } @@ -490,19 +510,24 @@ void pmac_power_off(void) { +#ifdef CONFIG_ADB_CUDA struct adb_request req; +#endif /* CONFIG_ADB_CUDA */ - switch (adb_hardware) { - case ADB_VIACUDA: + switch (sys_ctrler) { +#ifdef CONFIG_ADB_CUDA + case SYS_CTRLER_CUDA: cuda_request(&req, NULL, 2, CUDA_PACKET, CUDA_POWERDOWN); for (;;) cuda_poll(); break; - - case ADB_VIAPMU: +#endif /* CONFIG_ADB_CUDA */ +#ifdef CONFIG_ADB_PMU + case SYS_CTRLER_PMU: pmu_shutdown(); break; +#endif /* CONFIG_ADB_PMU */ default: } } @@ -609,7 +634,7 @@ ppc_md.get_cpuinfo = pmac_get_cpuinfo; ppc_md.irq_cannonicalize = NULL; ppc_md.init_IRQ = pmac_pic_init; - ppc_md.do_IRQ = pmac_do_IRQ; + ppc_md.get_irq = pmac_get_irq; ppc_md.init = pmac_init2; ppc_md.restart = pmac_restart; @@ -621,7 +646,7 @@ ppc_md.get_rtc_time = pmac_get_rtc_time; ppc_md.calibrate_decr = pmac_calibrate_decr; -#if defined(CONFIG_VT) && defined(CONFIG_MAC_KEYBOARD) +#if defined(CONFIG_VT) && defined(CONFIG_ADB_KEYBOARD) ppc_md.kbd_setkeycode = mackbd_setkeycode; ppc_md.kbd_getkeycode = mackbd_getkeycode; ppc_md.kbd_translate = mackbd_translate; @@ -648,4 +673,3 @@ ppc_ide_md.io_base = _IO_BASE; /* actually too early for this :-( */ #endif } - diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/pmac_support.c linux/arch/ppc/kernel/pmac_support.c --- v2.3.19/linux/arch/ppc/kernel/pmac_support.c Tue Aug 31 17:29:13 1999 +++ linux/arch/ppc/kernel/pmac_support.c Thu Oct 7 10:17:08 1999 @@ -12,8 +12,8 @@ #include #include #include -#include -#include +#include +#include /* * Read and write the non-volatile RAM on PowerMacs and CHRP machines. @@ -47,7 +47,7 @@ } else if (nvram_naddrs == 2) { nvram_addr = ioremap(dp->addrs[0].address, dp->addrs[0].size); nvram_data = ioremap(dp->addrs[1].address, dp->addrs[1].size); - } else if (nvram_naddrs == 0 && adb_hardware == ADB_VIAPMU) { + } else if (nvram_naddrs == 0 && sys_ctrler == SYS_CTRLER_PMU) { nvram_naddrs = -1; } else { printk(KERN_ERR "Don't know how to access NVRAM with %d addresses\n", @@ -55,6 +55,7 @@ } } +#ifdef CONFIG_NVRAM unsigned char nvram_read_byte(int addr) { struct adb_request req; @@ -100,3 +101,4 @@ } eieio(); } +#endif /* CONFIG_NVRAM */ diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/pmac_time.c linux/arch/ppc/kernel/pmac_time.c --- v2.3.19/linux/arch/ppc/kernel/pmac_time.c Tue Aug 31 17:29:13 1999 +++ linux/arch/ppc/kernel/pmac_time.c Thu Oct 7 10:17:08 1999 @@ -15,11 +15,11 @@ #include #include #include +#include +#include +#include #include -#include -#include -#include #include #include #include @@ -55,11 +55,14 @@ unsigned long pmac_get_rtc_time(void) { +#ifdef CONFIG_ADB struct adb_request req; +#endif /* Get the time from the RTC */ - switch (adb_hardware) { - case ADB_VIACUDA: + switch (sys_ctrler) { +#ifdef CONFIG_ADB_CUDA + case SYS_CTRLER_CUDA: if (cuda_request(&req, NULL, 2, CUDA_PACKET, CUDA_GET_TIME) < 0) return 0; while (!req.complete) @@ -69,7 +72,9 @@ req.reply_len); return (req.reply[3] << 24) + (req.reply[4] << 16) + (req.reply[5] << 8) + req.reply[6] - RTC_OFFSET; - case ADB_VIAPMU: +#endif /* CONFIG_ADB_CUDA */ +#ifdef CONFIG_ADB_PMU + case SYS_CTRLER_PMU: if (pmu_request(&req, NULL, 1, PMU_READ_RTC) < 0) return 0; while (!req.complete) @@ -79,6 +84,7 @@ req.reply_len); return (req.reply[1] << 24) + (req.reply[2] << 16) + (req.reply[3] << 8) + req.reply[4] - RTC_OFFSET; +#endif /* CONFIG_ADB_PMU */ default: return 0; } @@ -141,13 +147,12 @@ /* * Reset the time after a sleep. */ -static int time_sleep_notify(struct notifier_block *this, unsigned long event, - void *x) +static int time_sleep_notify(struct pmu_sleep_notifier *self, int when) { static unsigned long time_diff; - switch (event) { - case PBOOK_SLEEP: + switch (when) { + case PBOOK_SLEEP_NOW: time_diff = xtime.tv_sec - pmac_get_rtc_time(); break; case PBOOK_WAKE: @@ -157,11 +162,11 @@ last_rtc_update = xtime.tv_sec; break; } - return NOTIFY_DONE; + return PBOOK_SLEEP_OK; } -static struct notifier_block time_sleep_notifier = { - time_sleep_notify, NULL, 100 +static struct pmu_sleep_notifier time_sleep_notifier = { + time_sleep_notify, SLEEP_LEVEL_MISC, }; #endif /* CONFIG_PMAC_PBOOK */ @@ -176,7 +181,7 @@ int freq, *fp, divisor; #ifdef CONFIG_PMAC_PBOOK - notifier_chain_register(&sleep_notifier_list, &time_sleep_notifier); + pmu_register_sleep_notifier(&time_sleep_notifier); #endif /* CONFIG_PMAC_PBOOK */ if (via_calibrate_decr()) diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/ppc8xx_pic.c linux/arch/ppc/kernel/ppc8xx_pic.c --- v2.3.19/linux/arch/ppc/kernel/ppc8xx_pic.c Thu Apr 29 12:39:01 1999 +++ linux/arch/ppc/kernel/ppc8xx_pic.c Thu Oct 7 10:17:08 1999 @@ -5,45 +5,170 @@ #include #include #include -#include +#include #include "ppc8xx_pic.h" +/* The 8xx or 82xx internal interrupt controller. It is usually + * the only interrupt controller. Some boards, like the MBX and + * Sandpoint have the 8259 as a secondary controller. Depending + * upon the processor type, the internal controller can have as + * few as 16 interrups or as many as 64. We could use the + * "clear_bit()" and "set_bit()" functions like other platforms, + * but they are overkill for us. + */ -static void mbx_mask_irq(unsigned int irq_nr) +static void m8xx_mask_irq(unsigned int irq_nr) { - if ( irq_nr == ISA_BRIDGE_INT ) return; - if ( irq_nr >= ppc8xx_pic.irq_offset ) - irq_nr -= ppc8xx_pic.irq_offset; - ppc_cached_irq_mask[0] &= ~(1 << (31-irq_nr)); - ((immap_t *)IMAP_ADDR)->im_siu_conf.sc_simask = ppc_cached_irq_mask[0]; + int bit, word; + + bit = irq_nr & 0x1f; + word = irq_nr >> 5; + + ppc_cached_irq_mask[word] &= ~(1 << (31-bit)); +#ifdef CONFIG_82xx + ((immap_t *)IMAP_ADDR)->im_siu_conf.sc_simask[word] = + ppc_cached_irq_mask[word]; +#else + ((immap_t *)IMAP_ADDR)->im_siu_conf.sc_simask = + ppc_cached_irq_mask[word]; +#endif } -static void mbx_unmask_irq(unsigned int irq_nr) +static void m8xx_unmask_irq(unsigned int irq_nr) { - if ( irq_nr >= ppc8xx_pic.irq_offset ) - irq_nr -= ppc8xx_pic.irq_offset; - ppc_cached_irq_mask[0] |= (1 << (31-irq_nr)); - ((immap_t *)IMAP_ADDR)->im_siu_conf.sc_simask = ppc_cached_irq_mask[0]; + int bit, word; + + bit = irq_nr & 0x1f; + word = irq_nr >> 5; + + ppc_cached_irq_mask[word] |= (1 << (31-bit)); +#ifdef CONFIG_82xx + ((immap_t *)IMAP_ADDR)->im_siu_conf.sc_simask[word] = + ppc_cached_irq_mask[word]; +#else + ((immap_t *)IMAP_ADDR)->im_siu_conf.sc_simask = + ppc_cached_irq_mask[word]; +#endif } -static void mbx_mask_and_ack(unsigned int irq_nr) +static void m8xx_mask_and_ack(unsigned int irq_nr) { - /* this shouldn't be masked, we mask the 8259 if we need to -- Cort */ - if ( irq_nr != ISA_BRIDGE_INT ) - mbx_mask_irq(irq_nr); - if ( irq_nr >= ppc8xx_pic.irq_offset ) - irq_nr -= ppc8xx_pic.irq_offset; - /* clear the pending bits */ - ((immap_t *)IMAP_ADDR)->im_siu_conf.sc_sipend = 1 << (31-irq_nr); + int bit, word; + + bit = irq_nr & 0x1f; + word = irq_nr >> 5; + + ppc_cached_irq_mask[word] &= ~(1 << (31-bit)); +#ifdef CONFIG_82xx + ((immap_t *)IMAP_ADDR)->im_siu_conf.sc_simask[word] = + ppc_cached_irq_mask[word]; + ((immap_t *)IMAP_ADDR)->im_siu_conf.sc_sipend[word] = 1 << (31-bit); +#else + ((immap_t *)IMAP_ADDR)->im_siu_conf.sc_simask = + ppc_cached_irq_mask[word]; + ((immap_t *)IMAP_ADDR)->im_siu_conf.sc_sipend = 1 << (31-bit); +#endif } struct hw_interrupt_type ppc8xx_pic = { " 8xx SIU ", NULL, NULL, - NULL, - mbx_unmask_irq, - mbx_mask_irq, - mbx_mask_and_ack, + m8xx_unmask_irq, + m8xx_mask_irq, + m8xx_mask_and_ack, 0 }; + +#if 0 +void +m8xx_do_IRQ(struct pt_regs *regs, + int cpu, + int isfake) +{ + int irq; + unsigned long bits = 0; + + /* For MPC8xx, read the SIVEC register and shift the bits down + * to get the irq number. */ + bits = ((immap_t *)IMAP_ADDR)->im_siu_conf.sc_sivec; + irq = bits >> 26; +#if 0 + irq += ppc8xx_pic.irq_offset; +#endif + bits = 1UL << irq; + + if (irq < 0) { + printk(KERN_DEBUG "Bogus interrupt %d from PC = %lx\n", + irq, regs->nip); + ppc_spurious_interrupts++; + } + else { + ppc_irq_dispatch_handler( regs, irq ); + } + +} +#endif + + +int +m8xx_get_irq(struct pt_regs *regs) +{ + int irq; + unsigned long bits = 0; + + /* For MPC8xx, read the SIVEC register and shift the bits down + * to get the irq number. */ + bits = ((immap_t *)IMAP_ADDR)->im_siu_conf.sc_sivec; + irq = bits >> 26; +#if 0 + irq += ppc8xx_pic.irq_offset; +#endif + return irq; +} + +/* The MBX is the only 8xx board that uses the 8259. +*/ +#ifdef CONFIG_MBX +void mbx_i8259_action(int cpl, void *dev_id, struct pt_regs *regs) +{ + int bits, irq; + + /* A bug in the QSpan chip causes it to give us 0xff always + * when doing a character read. So read 32 bits and shift. + * This doesn't seem to return useful values anyway, but + * read it to make sure things are acked. + * -- Cort + */ + irq = (inl(0x508) >> 24)&0xff; + if ( irq != 0xff ) printk("iack %d\n", irq); + + outb(0x0C, 0x20); + irq = inb(0x20) & 7; + if (irq == 2) + { + outb(0x0C, 0xA0); + irq = inb(0xA0); + irq = (irq&7) + 8; + } + bits = 1UL << irq; + irq += i8259_pic.irq_offset; + ppc_irq_dispatch_handler( regs, irq ); +} +#endif + +/* Only the MBX uses the external 8259. This allows us to catch standard + * drivers that may mess up the internal interrupt controllers, and also + * allow them to run without modification on the MBX. + */ +int request_irq(unsigned int irq, void (*handler)(int, void *, struct pt_regs *), + unsigned long irqflags, const char * devname, void *dev_id) +{ + +#ifdef CONFIG_MBX + irq += i8259_pic.irq_offset; + return (request_8xxirq(irq, handler, irqflags, devname, dev_id)); +#else + panic("request_irq"); +#endif +} diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/ppc8xx_pic.h linux/arch/ppc/kernel/ppc8xx_pic.h --- v2.3.19/linux/arch/ppc/kernel/ppc8xx_pic.h Thu Apr 29 12:39:01 1999 +++ linux/arch/ppc/kernel/ppc8xx_pic.h Thu Oct 7 10:17:08 1999 @@ -6,4 +6,16 @@ extern struct hw_interrupt_type ppc8xx_pic; +void m8xx_pic_init(void); +void m8xx_do_IRQ(struct pt_regs *regs, + int cpu, + int isfake); +int m8xx_get_irq(struct pt_regs *regs); + +#ifdef CONFIG_MBX +#include "i8259.h" +#include +void mbx_i8259_action(int cpl, void *dev_id, struct pt_regs *regs); +#endif + #endif /* _PPC_KERNEL_PPC8xx_H */ diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/ppc_htab.c linux/arch/ppc/kernel/ppc_htab.c --- v2.3.19/linux/arch/ppc/kernel/ppc_htab.c Mon Jun 28 13:40:39 1999 +++ linux/arch/ppc/kernel/ppc_htab.c Thu Oct 7 10:17:08 1999 @@ -1,5 +1,5 @@ /* - * $Id: ppc_htab.c,v 1.28 1999/06/27 10:53:32 davem Exp $ + * $Id: ppc_htab.c,v 1.29 1999/09/10 05:05:50 paulus Exp $ * * PowerPC hash table management proc entry. Will show information * about the current hash table and will allow changes to it. @@ -256,6 +256,8 @@ return 0; if (n > strlen(buffer) - *ppos) n = strlen(buffer) - *ppos; + if (n > count) + n = count; copy_to_user(buf, buffer + *ppos, n); *ppos += n; return n; @@ -533,7 +535,21 @@ int vleft, first=1, len, left, val; #define TMPBUFLEN 256 char buf[TMPBUFLEN], *p; - + static const char *sizestrings[4] = { + "unknown size", "256KB", "512KB", "1MB" + }; + static const char *clockstrings[8] = { + "clock disabled", "+1 clock", "+1.5 clock", "reserved(3)", + "+2 clock", "+2.5 clock", "+3 clock", "reserved(7)" + }; + static const char *typestrings[4] = { + "flow-through burst SRAM", "reserved SRAM", + "pipelined burst SRAM", "pipelined late-write SRAM" + }; + static const char *holdstrings[4] = { + "0.5", "1.0", "(reserved2)", "(reserved3)" + }; + if ( (_get_PVR() >> 16) != 8) return -EFAULT; if ( /*!table->maxlen ||*/ (filp->f_pos && !write)) { @@ -586,55 +602,13 @@ p += sprintf(p, " %s", (val&0x80000000)?"enabled":"disabled"); p += sprintf(p,",%sparity",(val&0x40000000)?"":"no "); - - switch( (val >> 28) & 0x3 ) - { - case 1: p += sprintf(p,",256Kb"); - break; - case 2: p += sprintf(p,",512Kb"); - break; - case 3: p += sprintf(p,",1M"); - break; - default: p += sprintf(p,",unknown size"); - break; - } - - - switch( (val >> 25) & 0x7 ) - { - case 0: p += sprintf(p,",clock disabled"); - break; - case 1: p += sprintf(p,",+1 clock"); - break; - case 2: p += sprintf(p,",+1.5 clock"); - break; - case 7: - case 3: p += sprintf(p,",reserved clock"); - break; - case 4: p += sprintf(p,",+2 clock"); - break; - case 5: p += sprintf(p,",+2.5 clock"); - break; - case 6: p += sprintf(p,",+3 clock"); - break; - } - - switch( (val >> 23) & 0x2 ) - { - case 0: p += sprintf(p,",flow-through burst SRAM"); - break; - case 1: p += sprintf(p,",reserved SRAM"); - break; - case 2: p += sprintf(p,",pipelined burst SRAM"); - break; - case 3: p += sprintf(p,",pipelined late-write SRAM"); - break; - } - - p += sprintf(p,"%s",(val>>22)?"":",data only"); - p += sprintf(p,"%s",(val>>20)?",ZZ enabled":""); - p += sprintf(p,",%s",(val>>19)?"write-through":"copy-back"); - p += sprintf(p,",%sns hold",(val>>16)?"1.0":"0.5"); + p += sprintf(p, ",%s", sizestrings[(val >> 28) & 3]); + p += sprintf(p, ",%s", clockstrings[(val >> 25) & 7]); + p += sprintf(p, ",%s", typestrings[(val >> 23) & 0x2]); + p += sprintf(p,"%s",(val>>22)&1?"":",data only"); + p += sprintf(p,"%s",(val>>20)&1?",ZZ enabled":""); + p += sprintf(p,",%s",(val>>19)&1?"write-through":"copy-back"); + p += sprintf(p,",%sns hold", holdstrings[(val>>16)&3]); p += sprintf(p,"\n"); diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/ppc_ksyms.c linux/arch/ppc/kernel/ppc_ksyms.c --- v2.3.19/linux/arch/ppc/kernel/ppc_ksyms.c Fri Sep 10 23:57:28 1999 +++ linux/arch/ppc/kernel/ppc_ksyms.c Thu Oct 7 10:17:08 1999 @@ -21,9 +21,9 @@ #include #include #include -#include -#include -#include +#include +#include +#include #include #include #include @@ -31,6 +31,9 @@ #include #include #include +#ifdef __SMP__ +#include +#endif /* __SMP__ */ /* Tell string.h we don't want memcpy etc. as cpp defines */ #define EXPORT_SYMTAB_STROPS @@ -47,6 +50,8 @@ extern void do_lost_interrupts(unsigned long); extern int do_signal(sigset_t *, struct pt_regs *); +asmlinkage long long __ashrdi3(long long, int); +asmlinkage long long __lshrdi3(long long, int); asmlinkage int abs(int); EXPORT_SYMBOL(clear_page); @@ -67,15 +72,24 @@ EXPORT_SYMBOL(disable_irq_nosync); EXPORT_SYMBOL(ppc_local_irq_count); EXPORT_SYMBOL(ppc_local_bh_count); +#ifdef __SMP__ +EXPORT_SYMBOL(kernel_flag); +#endif /* __SMP__ */ +#ifndef CONFIG_8xx EXPORT_SYMBOL(isa_io_base); EXPORT_SYMBOL(isa_mem_base); EXPORT_SYMBOL(pci_dram_offset); +#endif EXPORT_SYMBOL(ISA_DMA_THRESHOLD); EXPORT_SYMBOL(DMA_MODE_READ); EXPORT_SYMBOL(DMA_MODE_WRITE); +#ifndef CONFIG_8xx +#if defined(CONFIG_PREP) || defined(CONFIG_ALL_PPC) EXPORT_SYMBOL(_prep_type); EXPORT_SYMBOL(ucSystemType); +#endif +#endif EXPORT_SYMBOL(atomic_add); EXPORT_SYMBOL(atomic_sub); @@ -175,20 +189,30 @@ EXPORT_SYMBOL(_write_unlock); #endif +#ifndef CONFIG_MACH_SPECIFIC EXPORT_SYMBOL(_machine); +#endif EXPORT_SYMBOL(ppc_md); +#ifdef CONFIG_ADB +/* + * This could be more fine-grained, but for now assume if we have + * ADB we have it all -- Cort + */ EXPORT_SYMBOL(adb_request); EXPORT_SYMBOL(adb_register); EXPORT_SYMBOL(cuda_request); EXPORT_SYMBOL(cuda_poll); EXPORT_SYMBOL(pmu_request); EXPORT_SYMBOL(pmu_poll); +#endif /* CONFIG_ADB */ #ifdef CONFIG_PMAC_PBOOK -EXPORT_SYMBOL(sleep_notifier_list); +EXPORT_SYMBOL(pmu_register_sleep_notifier); +EXPORT_SYMBOL(pmu_unregister_sleep_notifier); EXPORT_SYMBOL(pmu_enable_irled); #endif CONFIG_PMAC_PBOOK EXPORT_SYMBOL(abort); +#ifndef CONFIG_8xx EXPORT_SYMBOL(find_devices); EXPORT_SYMBOL(find_type_devices); EXPORT_SYMBOL(find_compatible_devices); @@ -200,15 +224,18 @@ EXPORT_SYMBOL(feature_set); EXPORT_SYMBOL(feature_clear); EXPORT_SYMBOL(feature_test); +#endif #ifdef CONFIG_SCSI EXPORT_SYMBOL(note_scsi_host); #endif EXPORT_SYMBOL(kd_mksound); -#ifdef CONFIG_PMAC +#ifdef CONFIG_NVRAM EXPORT_SYMBOL(nvram_read_byte); EXPORT_SYMBOL(nvram_write_byte); -#endif /* CONFIG_PMAC */ +#endif /* CONFIG_NVRAM */ +EXPORT_SYMBOL_NOVERS(__ashrdi3); +EXPORT_SYMBOL_NOVERS(__lshrdi3); EXPORT_SYMBOL_NOVERS(memcpy); EXPORT_SYMBOL_NOVERS(memset); EXPORT_SYMBOL_NOVERS(memmove); @@ -216,8 +243,17 @@ EXPORT_SYMBOL_NOVERS(memcmp); EXPORT_SYMBOL(abs); +#ifndef CONFIG_8xx EXPORT_SYMBOL(device_is_compatible); +#endif #ifdef CONFIG_VT EXPORT_SYMBOL(screen_info); #endif + +EXPORT_SYMBOL(int_control); +EXPORT_SYMBOL(timer_interrupt_intercept); +EXPORT_SYMBOL(timer_interrupt); +extern unsigned long do_IRQ_intercept; +EXPORT_SYMBOL(do_IRQ_intercept); +EXPORT_SYMBOL(irq_desc); diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/prep_nvram.c linux/arch/ppc/kernel/prep_nvram.c --- v2.3.19/linux/arch/ppc/kernel/prep_nvram.c Tue Aug 31 17:29:13 1999 +++ linux/arch/ppc/kernel/prep_nvram.c Thu Oct 7 10:17:08 1999 @@ -29,14 +29,14 @@ unsigned char *rs_pcNvRAM; -unsigned char prep_nvram_read_val(int addr) +unsigned char __prep prep_nvram_read_val(int addr) { outb(addr, PREP_NVRAM_AS0); outb(addr>>8, PREP_NVRAM_AS1); return inb(PREP_NVRAM_DATA); } -void prep_nvram_write_val(int addr, +void __prep prep_nvram_write_val(int addr, unsigned char val) { outb(addr, PREP_NVRAM_AS0); @@ -47,12 +47,12 @@ /* * Most Radstone boards have NvRAM memory mapped at offset 8M in ISA space */ -unsigned char rs_nvram_read_val(int addr) +unsigned char __prep rs_nvram_read_val(int addr) { return rs_pcNvRAM[addr]; } -void rs_nvram_write_val(int addr, +void __prep rs_nvram_write_val(int addr, unsigned char val) { rs_pcNvRAM[addr]=val; @@ -113,7 +113,7 @@ } __prep -char *prep_nvram_get_var(const char *name) +char __prep *prep_nvram_get_var(const char *name) { char *cp; int namelen; @@ -133,7 +133,7 @@ } __prep -char *prep_nvram_first_var(void) +char __prep *prep_nvram_first_var(void) { if (nvram->Header.GELength == 0) { return NULL; @@ -144,7 +144,7 @@ } __prep -char *prep_nvram_next_var(char *name) +char __prep *prep_nvram_next_var(char *name) { char *cp; diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/prep_pci.c linux/arch/ppc/kernel/prep_pci.c --- v2.3.19/linux/arch/ppc/kernel/prep_pci.c Tue Aug 31 17:29:13 1999 +++ linux/arch/ppc/kernel/prep_pci.c Thu Oct 7 10:17:08 1999 @@ -1,5 +1,5 @@ /* - * $Id: prep_pci.c,v 1.39 1999/08/31 15:42:39 cort Exp $ + * $Id: prep_pci.c,v 1.40 1999/09/17 17:23:05 cort Exp $ * PReP pci functions. * Originally by Gary Thomas * rewritten and updated by Cort Dougan (cort@cs.nmt.edu) @@ -39,7 +39,8 @@ /* Used for Motorola to store system config register */ static unsigned long *ProcInfo; -extern void chrp_do_IRQ(struct pt_regs *,int , int); +extern int chrp_get_irq(struct pt_regs *); +extern void chrp_post_irq(int); /* Tables for known hardware */ @@ -734,7 +735,8 @@ OpenPIC_InitSenses = mvme2600_openpic_initsenses; OpenPIC_NumInitSenses = sizeof(mvme2600_openpic_initsenses); - ppc_md.do_IRQ = chrp_do_IRQ; + ppc_md.get_irq = chrp_get_irq; + ppc_md.post_irq = chrp_post_irq; /* If raven is present on Motorola store the system config register * for later use. diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/prep_setup.c linux/arch/ppc/kernel/prep_setup.c --- v2.3.19/linux/arch/ppc/kernel/prep_setup.c Tue Aug 31 17:29:13 1999 +++ linux/arch/ppc/kernel/prep_setup.c Thu Oct 7 10:17:08 1999 @@ -86,7 +86,6 @@ extern unsigned char pckbd_sysrq_xlate[128]; extern void prep_setup_pci_ptrs(void); -extern void chrp_do_IRQ(struct pt_regs *regs, int cpu, int isfake); extern char saved_command_line[256]; int _prep_type; @@ -114,8 +113,7 @@ unsigned long vgacon_remap_base; #endif -__prep -int +int __prep prep_get_cpuinfo(char *buffer) { extern char *Motherboard_map_name; @@ -312,7 +310,7 @@ * it's the only way to support both addrs from one binary. * -- Cort */ - if ( is_prep ) + if ( _machine == _MACH_prep ) { extern struct card_info snd_installed_cards[]; struct card_info *snd_ptr; @@ -486,7 +484,7 @@ count_period_den = freq / 1000000; } -void +void __prep prep_restart(char *cmd) { unsigned long i = 10000; @@ -509,7 +507,7 @@ /* * This function will restart a board regardless of port 92 functionality */ -void +void __prep prep_direct_restart(char *cmd) { u32 jumpaddr=0xfff00100; @@ -532,7 +530,7 @@ */ } -void +void __prep prep_halt(void) { unsigned long flags; @@ -552,13 +550,14 @@ */ } -void +void __prep prep_power_off(void) { prep_halt(); } -int prep_setup_residual(char *buffer) +int __prep +prep_setup_residual(char *buffer) { int len = 0; @@ -576,7 +575,7 @@ return len; } -u_int +u_int __prep prep_irq_cannonicalize(u_int irq) { if (irq == 2) @@ -589,7 +588,8 @@ } } -void +#if 0 +void __prep prep_do_IRQ(struct pt_regs *regs, int cpu, int isfake) { int irq; @@ -602,6 +602,13 @@ return; } ppc_irq_dispatch_handler( regs, irq ); +} +#endif + +int __prep +prep_get_irq(struct pt_regs *regs) +{ + return i8259_irq(smp_processor_id()); } void __init @@ -628,19 +635,19 @@ /* * IDE stuff. */ -void +void __prep prep_ide_insw(ide_ioreg_t port, void *buf, int ns) { _insw((unsigned short *)((port)+_IO_BASE), buf, ns); } -void +void __prep prep_ide_outsw(ide_ioreg_t port, void *buf, int ns) { _outsw((unsigned short *)((port)+_IO_BASE), buf, ns); } -int +int __prep prep_ide_default_irq(ide_ioreg_t base) { switch (base) { @@ -653,7 +660,7 @@ } } -ide_ioreg_t +ide_ioreg_t __prep prep_ide_default_io_base(int index) { switch (index) { @@ -666,13 +673,13 @@ } } -int +int __prep prep_ide_check_region(ide_ioreg_t from, unsigned int extent) { return check_region(from, extent); } -void +void __prep prep_ide_request_region(ide_ioreg_t from, unsigned int extent, const char *name) @@ -680,14 +687,14 @@ request_region(from, extent, name); } -void +void __prep prep_ide_release_region(ide_ioreg_t from, unsigned int extent) { release_region(from, extent); } -void +void __prep prep_ide_fix_driveid(struct hd_driveid *id) { } @@ -776,7 +783,7 @@ ppc_md.irq_cannonicalize = prep_irq_cannonicalize; ppc_md.init_IRQ = prep_init_IRQ; /* this gets changed later on if we have an OpenPIC -- Cort */ - ppc_md.do_IRQ = prep_do_IRQ; + ppc_md.get_irq = prep_get_irq; ppc_md.init = NULL; ppc_md.restart = prep_restart; diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/process.c linux/arch/ppc/kernel/process.c --- v2.3.19/linux/arch/ppc/kernel/process.c Tue Aug 31 17:29:13 1999 +++ linux/arch/ppc/kernel/process.c Thu Oct 7 10:17:08 1999 @@ -1,5 +1,5 @@ /* - * $Id: process.c,v 1.95 1999/08/31 06:54:07 davem Exp $ + * $Id: process.c,v 1.97 1999/09/14 19:07:42 cort Exp $ * * linux/arch/ppc/kernel/process.c * @@ -162,7 +162,7 @@ struct task_struct **last) { struct thread_struct *new_thread, *old_thread; - int s; + unsigned long s; __save_flags(s); __cli(); @@ -513,7 +513,7 @@ * vidmem just needs to be setup for it. * -- Cort */ - if ( ! is_prep ) + if ( _machine != _MACH_prep ) return; x = orig_x; y = orig_y; diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/prom.c linux/arch/ppc/kernel/prom.c --- v2.3.19/linux/arch/ppc/kernel/prom.c Fri Sep 10 23:57:28 1999 +++ linux/arch/ppc/kernel/prom.c Thu Oct 7 10:17:08 1999 @@ -1,5 +1,5 @@ /* - * $Id: prom.c,v 1.73 1999/09/05 11:56:32 paulus Exp $ + * $Id: prom.c,v 1.77 1999/09/14 01:13:19 cort Exp $ * * Procedures for interfacing to the Open Firmware PROM on * Power Macintosh computers. @@ -109,9 +109,9 @@ #ifdef CONFIG_BOOTX_TEXT -static void drawchar(char c); +void drawchar(char c); +void drawstring(const char *c); static void drawhex(unsigned long v); -static void drawstring(const char *c); static void scrollscreen(void); static void draw_byte(unsigned char c, long locX, long locY); @@ -138,7 +138,6 @@ unsigned long, struct device_node ***); static unsigned long finish_node(struct device_node *, unsigned long, interpret_func *); -static void relocate_nodes(void); static unsigned long check_display(unsigned long); static int prom_next_node(phandle *); static void *early_get_property(unsigned long, unsigned long, char *); @@ -287,7 +286,7 @@ gemini_prom_init(); return; #endif /* CONFIG_GEMINI */ - + /* check if we're apus, return if we are */ if ( r3 == 0x61707573 ) return; @@ -304,6 +303,8 @@ #endif RELOC(boot_infos) = PTRUNRELOC(bi); + if (!BOOT_INFO_IS_V2_COMPATIBLE(bi)) + bi->logicalDisplayBase = 0; clearscreen(); @@ -357,9 +358,13 @@ } } - space = bi->deviceTreeOffset + bi->deviceTreeSize; - if (bi->ramDisk) - space = bi->ramDisk + bi->ramDiskSize; + /* Move klimit to enclose device tree, args, ramdisk, etc... */ + if (bi->version < 5) { + space = bi->deviceTreeOffset + bi->deviceTreeSize; + if (bi->ramDisk) + space = bi->ramDisk + bi->ramDiskSize; + } else + space = bi->totalParamsSize; RELOC(klimit) = PTRUNRELOC((char *) bi + space); /* New BootX will have flushed all TLBs and enters kernel with @@ -748,8 +753,6 @@ { unsigned long mem = (unsigned long) klimit; - if (boot_infos) - relocate_nodes(); mem = finish_node(allnodes, mem, NULL); printk(KERN_INFO "device tree used %lu bytes\n", mem - (unsigned long) allnodes); @@ -843,7 +846,7 @@ * This procedure updates the pointers. */ __init -static void relocate_nodes(void) +void relocate_nodes(void) { unsigned long base; struct device_node *np; @@ -1183,6 +1186,23 @@ return 0; } + +/* + * Indicates whether the root node has a given value in its + * compatible property. + */ +__openfirmware +int +machine_is_compatible(const char *compat) +{ + struct device_node *root; + + root = find_path_device("/"); + if (root == 0) + return 0; + return device_is_compatible(root, compat); +} + /* * Construct and return a list of the device_nodes with a given type * and compatible property. @@ -1316,7 +1336,8 @@ unsigned long *outputs, ...) { va_list list; - int i, s; + int i; + unsigned long s; struct device_node *rtas; int *tokp; union { @@ -1361,19 +1382,41 @@ prom_exit(); } +#ifdef CONFIG_XMON +__init +void +map_bootx_text(void) +{ + if (boot_infos == 0) + return; + boot_infos->logicalDisplayBase = + ioremap((unsigned long) boot_infos->dispDeviceBase, + boot_infos->dispDeviceRowBytes * boot_infos->dispDeviceRect[3]); +} +#endif /* CONFIG_XMON */ + /* Calc the base address of a given point (x,y) */ -#define CALC_BASE(x,y) ((BOOT_INFO_IS_V2_COMPATIBLE(bi) ? bi->logicalDisplayBase : \ - bi->dispDeviceBase) + (bi->dispDeviceRect[0] + (x)) * \ - (bi->dispDeviceDepth >> 3) + bi->dispDeviceRowBytes * \ - ((y) + bi->dispDeviceRect[1])) +__pmac +static unsigned char * +calc_base(boot_infos_t *bi, int x, int y) +{ + unsigned char *base; -__init + base = bi->logicalDisplayBase; + if (base == 0) + base = bi->dispDeviceBase; + base += (x + bi->dispDeviceRect[0]) * (bi->dispDeviceDepth >> 3); + base += (y + bi->dispDeviceRect[1]) * bi->dispDeviceRowBytes; + return base; +} + +__pmac static void clearscreen(void) { unsigned long offset = reloc_offset(); boot_infos_t* bi = PTRRELOC(RELOC(boot_infos)); - unsigned long *base = (unsigned long *)CALC_BASE(0,0); + unsigned long *base = (unsigned long *)calc_base(bi, 0, 0); unsigned long width = ((bi->dispDeviceRect[2] - bi->dispDeviceRect[0]) * (bi->dispDeviceDepth >> 3)) >> 2; int i,j; @@ -1392,13 +1435,13 @@ __asm__ __volatile__ ("dcbst 0,%0" :: "r" (addr)); } -__init +__pmac static void flushscreen(void) { unsigned long offset = reloc_offset(); boot_infos_t* bi = PTRRELOC(RELOC(boot_infos)); - unsigned long *base = (unsigned long *)CALC_BASE(0,0); + unsigned long *base = (unsigned long *)calc_base(bi, 0, 0); unsigned long width = ((bi->dispDeviceRect[2] - bi->dispDeviceRect[0]) * (bi->dispDeviceDepth >> 3)) >> 2; int i,j; @@ -1416,14 +1459,14 @@ #ifdef CONFIG_BOOTX_TEXT -__init +__pmac static void scrollscreen(void) { unsigned long offset = reloc_offset(); boot_infos_t* bi = PTRRELOC(RELOC(boot_infos)); - unsigned long *src = (unsigned long *)CALC_BASE(0,16); - unsigned long *dst = (unsigned long *)CALC_BASE(0,0); + unsigned long *src = (unsigned long *)calc_base(bi,0,16); + unsigned long *dst = (unsigned long *)calc_base(bi,0,0); unsigned long width = ((bi->dispDeviceRect[2] - bi->dispDeviceRect[0]) * (bi->dispDeviceDepth >> 3)) >> 2; int i,j; @@ -1446,21 +1489,33 @@ } } -__init -static void +__pmac +void drawchar(char c) { unsigned long offset = reloc_offset(); - switch(c) { - case '\r': RELOC(g_loc_X) = 0; break; - case '\n': RELOC(g_loc_X) = 0; RELOC(g_loc_Y)++; break; - default: - draw_byte(c, RELOC(g_loc_X)++, RELOC(g_loc_Y)); - if (RELOC(g_loc_X) >= RELOC(g_max_loc_X)) { - RELOC(g_loc_X) = 0; - RELOC(g_loc_Y)++; - } + switch (c) { + case '\b': + if (RELOC(g_loc_X) > 0) + --RELOC(g_loc_X); + break; + case '\t': + RELOC(g_loc_X) = (RELOC(g_loc_X) & -8) + 8; + break; + case '\r': + RELOC(g_loc_X) = 0; + break; + case '\n': + RELOC(g_loc_X) = 0; + RELOC(g_loc_Y)++; + break; + default: + draw_byte(c, RELOC(g_loc_X)++, RELOC(g_loc_Y)); + } + if (RELOC(g_loc_X) >= RELOC(g_max_loc_X)) { + RELOC(g_loc_X) = 0; + RELOC(g_loc_Y)++; } while (RELOC(g_loc_Y) >= RELOC(g_max_loc_Y)) { scrollscreen(); @@ -1468,15 +1523,15 @@ } } -__init -static void +__pmac +void drawstring(const char *c) { - while(*c) - drawchar(*(c++)); + while (*c) + drawchar(*c++); } -__init +__pmac static void drawhex(unsigned long v) { @@ -1494,13 +1549,13 @@ } -__init +__pmac static void draw_byte(unsigned char c, long locX, long locY) { unsigned long offset = reloc_offset(); boot_infos_t* bi = PTRRELOC(RELOC(boot_infos)); - unsigned char *base = CALC_BASE(locX << 3, locY << 4); + unsigned char *base = calc_base(bi, locX << 3, locY << 4); unsigned char *font = &RELOC(vga_font)[((unsigned long)c) * 16]; switch(bi->dispDeviceDepth) { @@ -1518,7 +1573,7 @@ } } -__init +__pmac static unsigned long expand_bits_8[16] = { 0x00000000, 0x000000ff, @@ -1538,7 +1593,7 @@ 0xffffffff }; -__init +__pmac static unsigned long expand_bits_16[4] = { 0x00000000, 0x0000ffff, @@ -1547,7 +1602,7 @@ }; -__init +__pmac static void draw_byte_32(unsigned char *font, unsigned long *base) { @@ -1573,7 +1628,7 @@ } } -__init +__pmac static void draw_byte_16(unsigned char *font, unsigned long *base) { @@ -1595,7 +1650,7 @@ } } -__init +__pmac static void draw_byte_8(unsigned char *font, unsigned long *base) { @@ -1615,7 +1670,7 @@ } } -__init +__pmac static unsigned char vga_font[cmapsz] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x7e, 0x81, 0xa5, 0x81, 0x81, 0xbd, diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/qspan_pci.c linux/arch/ppc/kernel/qspan_pci.c --- v2.3.19/linux/arch/ppc/kernel/qspan_pci.c Wed Dec 31 16:00:00 1969 +++ linux/arch/ppc/kernel/qspan_pci.c Thu Oct 7 10:17:08 1999 @@ -0,0 +1,379 @@ +/* + * QSpan pci routines. + * Most 8xx boards use the QSpan PCI bridge. The config address register + * is located 0x500 from the base of the bridge control/status registers. + * The data register is located at 0x504. + * This is a two step operation. First, the address register is written, + * then the data register is read/written as required. + * I don't know what to do about interrupts (yet). + * + * The RPX Classic implementation shares a chip select for normal + * PCI access and QSpan control register addresses. The selection is + * further selected by a bit setting in a board control register. + * Although it should happen, we disable interrupts during this operation + * to make sure some driver doesn't accidently access the PCI while + * we have switched the chip select. + */ + +#include +#include +#include +#include +#include + +#include +#include +#include +#include + +#include "pci.h" + + +/* + * This blows...... + * When reading the configuration space, if something does not respond + * the bus times out and we get a machine check interrupt. So, the + * good ol' exception tables come to mind to trap it and return some + * value. + * + * On an error we just return a -1, since that is what the caller wants + * returned if nothing is present. I copied this from __get_user_asm, + * with the only difference of returning -1 instead of EFAULT. + * There is an associated hack in the machine check trap code. + * + * The QSPAN is also a big endian device, that is it makes the PCI + * look big endian to us. This presents a problem for the Linux PCI + * functions, which assume little endian. For example, we see the + * first 32-bit word like this: + * ------------------------ + * | Device ID | Vendor ID | + * ------------------------ + * If we read/write as a double word, that's OK. But in our world, + * when read as a word, device ID is at location 0, not location 2 as + * the little endian PCI would believe. We have to switch bits in + * the PCI addresses given to us to get the data to/from the correct + * byte lanes. + * + * The QSPAN only supports 4 bits of "slot" in the dev_fn instead of 5. + * It always forces the MS bit to zero. Therefore, dev_fn values + * greater than 128 are returned as "no device found" errors. + * + * The QSPAN can only perform long word (32-bit) configuration cycles. + * The "offset" must have the two LS bits set to zero. Read operations + * require we read the entire word and then sort out what should be + * returned. Write operations other than long word require that we + * read the long word, update the proper word or byte, then write the + * entire long word back. + * + * PCI Bridge hack. We assume (correctly) that bus 0 is the primary + * PCI bus from the QSPAN. If we are called with a bus number other + * than zero, we create a Type 1 configuration access that a downstream + * PCI bridge will interpret. + */ + +#define __get_qspan_pci_config(x, addr, op) \ + __asm__ __volatile__( \ + "1: "op" %0,0(%1)\n" \ + " eieio\n" \ + "2:\n" \ + ".section .fixup,\"ax\"\n" \ + "3: li %0,-1\n" \ + " b 2b\n" \ + ".section __ex_table,\"a\"\n" \ + " .align 2\n" \ + " .long 1b,3b\n" \ + ".text" \ + : "=r"(x) : "r"(addr)) + +#define QS_CONFIG_ADDR ((volatile uint *)(PCI_CSR_ADDR + 0x500)) +#define QS_CONFIG_DATA ((volatile uint *)(PCI_CSR_ADDR + 0x504)) + +#define mk_config_addr(bus, dev, offset) \ + (((bus)<<16) | ((dev)<<8) | (offset & 0xfc)) + +#define mk_config_type1(bus, dev, offset) \ + mk_config_addr(bus, dev, offset) | 1; + +int qspan_pcibios_read_config_byte(unsigned char bus, unsigned char dev_fn, + unsigned char offset, unsigned char *val) +{ + uint temp; + u_char *cp; +#ifdef CONFIG_RPXCLASSIC + unsigned long flags; +#endif + + if ((bus > 7) || (dev_fn > 127)) { + *val = 0xff; + return PCIBIOS_DEVICE_NOT_FOUND; + } + +#ifdef CONFIG_RPXCLASSIC + save_flags(flags); + cli(); + *((uint *)RPX_CSR_ADDR) &= ~BCSR2_QSPACESEL; + eieio(); +#endif + + if (bus == 0) + *QS_CONFIG_ADDR = mk_config_addr(bus, dev_fn, offset); + else + *QS_CONFIG_ADDR = mk_config_type1(bus, dev_fn, offset); + __get_qspan_pci_config(temp, QS_CONFIG_DATA, "lwz"); + +#ifdef CONFIG_RPXCLASSIC + *((uint *)RPX_CSR_ADDR) |= BCSR2_QSPACESEL; + eieio(); + restore_flags(flags); +#endif + + offset ^= 0x03; + cp = ((u_char *)&temp) + (offset & 0x03); + *val = *cp; + return PCIBIOS_SUCCESSFUL; +} + +int qspan_pcibios_read_config_word(unsigned char bus, unsigned char dev_fn, + unsigned char offset, unsigned short *val) +{ + uint temp; + ushort *sp; +#ifdef CONFIG_RPXCLASSIC + unsigned long flags; +#endif + + if ((bus > 7) || (dev_fn > 127)) { + *val = 0xffff; + return PCIBIOS_DEVICE_NOT_FOUND; + } + +#ifdef CONFIG_RPXCLASSIC + save_flags(flags); + cli(); + *((uint *)RPX_CSR_ADDR) &= ~BCSR2_QSPACESEL; + eieio(); +#endif + + if (bus == 0) + *QS_CONFIG_ADDR = mk_config_addr(bus, dev_fn, offset); + else + *QS_CONFIG_ADDR = mk_config_type1(bus, dev_fn, offset); + __get_qspan_pci_config(temp, QS_CONFIG_DATA, "lwz"); + offset ^= 0x02; + +#ifdef CONFIG_RPXCLASSIC + *((uint *)RPX_CSR_ADDR) |= BCSR2_QSPACESEL; + eieio(); + restore_flags(flags); +#endif + + sp = ((ushort *)&temp) + ((offset >> 1) & 1); + *val = *sp; + return PCIBIOS_SUCCESSFUL; +} + +int qspan_pcibios_read_config_dword(unsigned char bus, unsigned char dev_fn, + unsigned char offset, unsigned int *val) +{ +#ifdef CONFIG_RPXCLASSIC + unsigned long flags; +#endif + + if ((bus > 7) || (dev_fn > 127)) { + *val = 0xffffffff; + return PCIBIOS_DEVICE_NOT_FOUND; + } + +#ifdef CONFIG_RPXCLASSIC + save_flags(flags); + cli(); + *((uint *)RPX_CSR_ADDR) &= ~BCSR2_QSPACESEL; + eieio(); +#endif + + if (bus == 0) + *QS_CONFIG_ADDR = mk_config_addr(bus, dev_fn, offset); + else + *QS_CONFIG_ADDR = mk_config_type1(bus, dev_fn, offset); + __get_qspan_pci_config(*val, QS_CONFIG_DATA, "lwz"); + +#ifdef CONFIG_RPXCLASSIC + *((uint *)RPX_CSR_ADDR) |= BCSR2_QSPACESEL; + eieio(); + restore_flags(flags); +#endif + + return PCIBIOS_SUCCESSFUL; +} + +int qspan_pcibios_write_config_byte(unsigned char bus, unsigned char dev_fn, + unsigned char offset, unsigned char val) +{ + uint temp; + u_char *cp; +#ifdef CONFIG_RPXCLASSIC + unsigned long flags; +#endif + + if ((bus > 7) || (dev_fn > 127)) + return PCIBIOS_DEVICE_NOT_FOUND; + + qspan_pcibios_read_config_dword(bus, dev_fn, offset, &temp); + + offset ^= 0x03; + cp = ((u_char *)&temp) + (offset & 0x03); + *cp = val; + +#ifdef CONFIG_RPXCLASSIC + save_flags(flags); + cli(); + *((uint *)RPX_CSR_ADDR) &= ~BCSR2_QSPACESEL; + eieio(); +#endif + + if (bus == 0) + *QS_CONFIG_ADDR = mk_config_addr(bus, dev_fn, offset); + else + *QS_CONFIG_ADDR = mk_config_type1(bus, dev_fn, offset); + *QS_CONFIG_DATA = temp; + +#ifdef CONFIG_RPXCLASSIC + *((uint *)RPX_CSR_ADDR) |= BCSR2_QSPACESEL; + eieio(); + restore_flags(flags); +#endif + + return PCIBIOS_SUCCESSFUL; +} + +int qspan_pcibios_write_config_word(unsigned char bus, unsigned char dev_fn, + unsigned char offset, unsigned short val) +{ + uint temp; + ushort *sp; +#ifdef CONFIG_RPXCLASSIC + unsigned long flags; +#endif + + if ((bus > 7) || (dev_fn > 127)) + return PCIBIOS_DEVICE_NOT_FOUND; + + qspan_pcibios_read_config_dword(bus, dev_fn, offset, &temp); + + offset ^= 0x02; + sp = ((ushort *)&temp) + ((offset >> 1) & 1); + *sp = val; + +#ifdef CONFIG_RPXCLASSIC + save_flags(flags); + cli(); + *((uint *)RPX_CSR_ADDR) &= ~BCSR2_QSPACESEL; + eieio(); +#endif + + if (bus == 0) + *QS_CONFIG_ADDR = mk_config_addr(bus, dev_fn, offset); + else + *QS_CONFIG_ADDR = mk_config_type1(bus, dev_fn, offset); + *QS_CONFIG_DATA = temp; + +#ifdef CONFIG_RPXCLASSIC + *((uint *)RPX_CSR_ADDR) |= BCSR2_QSPACESEL; + eieio(); + restore_flags(flags); +#endif + + return PCIBIOS_SUCCESSFUL; +} + +int qspan_pcibios_write_config_dword(unsigned char bus, unsigned char dev_fn, + unsigned char offset, unsigned int val) +{ +#ifdef CONFIG_RPXCLASSIC + unsigned long flags; +#endif + + if ((bus > 7) || (dev_fn > 127)) + return PCIBIOS_DEVICE_NOT_FOUND; + +#ifdef CONFIG_RPXCLASSIC + save_flags(flags); + cli(); + *((uint *)RPX_CSR_ADDR) &= ~BCSR2_QSPACESEL; + eieio(); +#endif + + if (bus == 0) + *QS_CONFIG_ADDR = mk_config_addr(bus, dev_fn, offset); + else + *QS_CONFIG_ADDR = mk_config_type1(bus, dev_fn, offset); + *(unsigned int *)QS_CONFIG_DATA = val; + +#ifdef CONFIG_RPXCLASSIC + *((uint *)RPX_CSR_ADDR) |= BCSR2_QSPACESEL; + eieio(); + restore_flags(flags); +#endif + + return PCIBIOS_SUCCESSFUL; +} + +int qspan_pcibios_find_device(unsigned short vendor, unsigned short dev_id, + unsigned short index, unsigned char *bus_ptr, + unsigned char *dev_fn_ptr) +{ + int num, devfn; + unsigned int x, vendev; + + if (vendor == 0xffff) + return PCIBIOS_BAD_VENDOR_ID; + vendev = (dev_id << 16) + vendor; + num = 0; + for (devfn = 0; devfn < 32; devfn++) { + qspan_pcibios_read_config_dword(0, devfn<<3, PCI_VENDOR_ID, &x); + if (x == vendev) { + if (index == num) { + *bus_ptr = 0; + *dev_fn_ptr = devfn<<3; + return PCIBIOS_SUCCESSFUL; + } + ++num; + } + } + return PCIBIOS_DEVICE_NOT_FOUND; +} + +int qspan_pcibios_find_class(unsigned int class_code, unsigned short index, + unsigned char *bus_ptr, unsigned char *dev_fn_ptr) +{ + int devnr, x, num; + + num = 0; + for (devnr = 0; devnr < 32; devnr++) { + qspan_pcibios_read_config_dword(0, devnr<<3, PCI_CLASS_REVISION, &x); + if ((x>>8) == class_code) { + if (index == num) { + *bus_ptr = 0; + *dev_fn_ptr = devnr<<3; + return PCIBIOS_SUCCESSFUL; + } + ++num; + } + } + return PCIBIOS_DEVICE_NOT_FOUND; +} + +void __init +m8xx_pcibios_fixup(void)) +{ + /* Lots to do here, all board and configuration specific. */ +} + +void __init +m8xx_setup_pci_ptrs(void)) +{ + set_config_access_method(qspan); + + ppc_md.pcibios_fixup = m8xx_pcibios_fixup; +} + diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/residual.c linux/arch/ppc/kernel/residual.c --- v2.3.19/linux/arch/ppc/kernel/residual.c Sat May 22 13:03:00 1999 +++ linux/arch/ppc/kernel/residual.c Thu Oct 7 10:17:08 1999 @@ -1,5 +1,5 @@ /* - * $Id: residual.c,v 1.15 1999/05/14 07:24:27 davem Exp $ + * $Id: residual.c,v 1.16 1999/09/17 17:23:09 cort Exp $ * * Code to deal with the PReP residual data. * @@ -49,6 +49,9 @@ #include #include + +unsigned char __res[sizeof(RESIDUAL)] __prepdata = {0,}; +RESIDUAL *res = (RESIDUAL *)&__res; const char * PnP_BASE_TYPES[] __initdata = { "Reserved", diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/setup.c linux/arch/ppc/kernel/setup.c --- v2.3.19/linux/arch/ppc/kernel/setup.c Fri Sep 10 23:57:28 1999 +++ linux/arch/ppc/kernel/setup.c Thu Oct 7 10:17:08 1999 @@ -1,5 +1,5 @@ /* - * $Id: setup.c,v 1.148 1999/09/05 11:56:34 paulus Exp $ + * $Id: setup.c,v 1.159 1999/09/18 18:40:38 dmalek Exp $ * Common prep/pmac/chrp boot and setup code. */ @@ -13,9 +13,6 @@ #include #include -#include -#include -#include #include #include #include @@ -27,8 +24,8 @@ #include #include #include -#ifdef CONFIG_MBX -#include +#ifdef CONFIG_8xx +#include #include #endif #include @@ -52,7 +49,7 @@ unsigned long r6, unsigned long r7); -extern void mbx_init(unsigned long r3, +extern void m8xx_init(unsigned long r3, unsigned long r4, unsigned long r5, unsigned long r6, @@ -74,18 +71,17 @@ extern char cmd_line[512]; char saved_command_line[256]; unsigned char aux_device_present; - +struct int_control_struct int_control; struct ide_machdep_calls ppc_ide_md; unsigned long ISA_DMA_THRESHOLD; unsigned long DMA_MODE_READ, DMA_MODE_WRITE; -/* Temporary hacks until machdep.h is fully done. */ +#ifndef CONFIG_MACH_SPECIFIC int _machine = 0; -/* do we have OF? */ int have_of = 0; -int is_prep = 0; -int is_chrp = 0; +#endif /* CONFIG_MACH_SPECIFIC */ + #ifdef CONFIG_MAGIC_SYSRQ unsigned long SYSRQ_KEY; #endif /* CONFIG_MAGIC_SYSRQ */ @@ -98,21 +94,19 @@ /* copy of the residual data */ -#ifndef CONFIG_MBX -unsigned char __res[sizeof(RESIDUAL)] __prepdata = {0,}; +#ifndef CONFIG_8xx +extern unsigned char __res[sizeof(RESIDUAL)]; #else -unsigned char __res[sizeof(bd_t)] = {0,}; +extern unsigned char __res[sizeof(bd_t)]; #endif -RESIDUAL *res = (RESIDUAL *)&__res; - /* * Perhaps we can put the pmac screen_info[] here * on pmac as well so we don't need the ifdef's. * Until we get multiple-console support in here * that is. -- Cort */ -#ifndef CONFIG_MBX +#ifndef CONFIG_8xx struct screen_info screen_info = { 0, 25, /* orig-x, orig-y */ 0, /* unused */ @@ -136,7 +130,7 @@ { } -#else /* CONFIG_MBX */ +#else /* CONFIG_8xx */ /* We need this to satisfy some external references until we can * strip the kernel down. @@ -152,7 +146,7 @@ 0, /* orig-video-isVGA */ 16 /* orig-video-points */ }; -#endif /* CONFIG_MBX */ +#endif /* CONFIG_8xx */ void machine_restart(char *cmd) { @@ -267,6 +261,7 @@ * Assume here that all clock rates are the same in a * smp system. -- Cort */ +#ifndef CONFIG_8xx if ( have_of ) { struct device_node *cpu_node; @@ -290,6 +285,7 @@ len += sprintf(len+buffer, "clock\t\t: %dMHz\n", *fp / 1000000); } +#endif if (ppc_md.setup_residual != NULL) { @@ -345,9 +341,8 @@ identify_machine(unsigned long r3, unsigned long r4, unsigned long r5, unsigned long r6, unsigned long r7) { -#ifdef __SMP__ - if ( first_cpu_booted ) return 0; -#endif /* __SMP__ */ + +#ifndef CONFIG_8xx if ( ppc_md.progress ) ppc_md.progress("id mach(): start", 0x100); #ifndef CONFIG_MACH_SPECIFIC @@ -358,68 +353,46 @@ r3 = 0; } /* prep boot loader tells us if we're prep or not */ - else if ( *(unsigned long *)(KERNELBASE) == (0xdeadc0de) ) { + else if ( *(unsigned long *)(KERNELBASE) == (0xdeadc0de) ) + { _machine = _MACH_prep; - is_prep = 1; - } else { + } else + { char *model; + struct device_node *root; have_of = 1; - + /* prom_init has already been called from __start */ - finish_device_tree(); + if (boot_infos) + relocate_nodes(); + /* ask the OF info if we're a chrp or pmac */ - model = get_property(find_path_device("/"), "device_type", NULL); - if ( model && !strncmp("chrp",model,4) ) - { - _machine = _MACH_chrp; - is_chrp = 1; - } - else - { - model = get_property(find_path_device("/"), - "model", NULL); - if ( model && !strncmp(model, "IBM", 3)) - { + /* we need to set _machine before calling finish_device_tree */ + root = find_path_device("/"); + if (root != 0) { + /* assume pmac unless proven to be chrp -- Cort */ + _machine = _MACH_Pmac; + model = get_property(root, "device_type", NULL); + if (model && !strncmp("chrp", model, 4)) _machine = _MACH_chrp; - is_chrp = 1; - } - else - { - _machine = _MACH_Pmac; + else { + model = get_property(root, "model", NULL); + if (model && !strncmp(model, "IBM", 3)) + _machine = _MACH_chrp; } } + finish_device_tree(); } -#else /* CONFIG_MACH_SPECIFIC */ - -#ifdef CONFIG_PREP - _machine = _MACH_prep; - is_prep = 1; -#elif defined(CONFIG_CHRP) - _machine = _MACH_chrp; - is_chrp = 1; - have_of = 1; -#elif defined(CONFIG_PMAC) - _machine = _MACH_Pmac; - have_of = 1; -#elif defined(CONFIG_MBX) - _machine = _MACH_mbx; -#elif defined(CONFIG_FADS) - _machine = _MACH_fads; -#elif defined(CONFIG_APUS) - _machine = _MACH_apus; -#elif defined(CONFIG_GEMINI) - _machine = _MACH_gemini; -#else -#error "Machine not defined correctly" -#endif /* CONFIG_APUS */ #endif /* CONFIG_MACH_SPECIFIC */ if ( have_of ) { #ifdef CONFIG_MACH_SPECIFIC /* prom_init has already been called from __start */ + if (boot_infos) + relocate_nodes(); finish_device_tree(); #endif /* CONFIG_MACH_SPECIFIC */ /* @@ -473,6 +446,11 @@ cmd_line[sizeof(cmd_line) - 1] = 0; } + int_control.int_sti = __no_use_sti; + int_control.int_cli = __no_use_cli; + int_control.int_save_flags = __no_use_save_flags; + int_control.int_restore_flags = __no_use_restore_flags; + switch (_machine) { case _MACH_Pmac: @@ -489,14 +467,11 @@ apus_init(r3, r4, r5, r6, r7); break; #endif -#ifdef CONFIG_MBX - case _MACH_mbx: - mbx_init(r3, r4, r5, r6, r7); - break; -#endif +#ifdef CONFIG_GEMINI case _MACH_gemini: gemini_init(r3, r4, r5, r6, r7); break; +#endif default: printk("Unknown machine type in identify_machine!\n"); } @@ -505,6 +480,17 @@ extern int __map_without_bats; __map_without_bats = 1; } +#else /* CONFIG_8xx */ + int_control.int_sti = __no_use_sti; + int_control.int_cli = __no_use_cli; + int_control.int_save_flags = __no_use_save_flags; + int_control.int_restore_flags = __no_use_restore_flags; + + m8xx_init(r3, r4, r5, r6, r7); +#endif + + /* this is for modules since _machine can be a define -- Cort */ + ppc_md.ppc_machine = _machine; if ( ppc_md.progress ) ppc_md.progress("id mach(): done", 0x200); return 0; diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/sleep.S linux/arch/ppc/kernel/sleep.S --- v2.3.19/linux/arch/ppc/kernel/sleep.S Wed Dec 31 16:00:00 1969 +++ linux/arch/ppc/kernel/sleep.S Thu Oct 7 10:17:08 1999 @@ -0,0 +1,264 @@ +/* + * This file contains sleep low-level functions for PowerBook G3. + * Copyright (C) 1999 Benjamin Herrenschmidt (bh40@calva.net) + * and Paul Mackerras (paulus@cs.anu.edu.au). + * + * 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 "ppc_asm.tmpl" +#include +#include + +#define MAGIC 0x4c617273 /* 'Lars' */ + +/* + * Structure for storing CPU registers on the stack. + */ +#define SL_SP 0 +#define SL_PC 4 +#define SL_MSR 8 +#define SL_SDR1 0xc +#define SL_SPRG0 0x10 /* 4 sprg's */ +#define SL_DBAT0 0x20 +#define SL_IBAT0 0x28 +#define SL_DBAT1 0x30 +#define SL_IBAT1 0x38 +#define SL_DBAT2 0x40 +#define SL_IBAT2 0x48 +#define SL_DBAT3 0x50 +#define SL_IBAT3 0x58 +#define SL_TB 0x60 +#define SL_HID0 0x68 +#define SL_R2 0x6c +#define SL_R12 0x70 /* r12 to r31 */ +#define SL_SIZE (SL_R12 + 80) + +#define tophys(rd,rs) addis rd,rs,-KERNELBASE@h +#define tovirt(rd,rs) addis rd,rs,KERNELBASE@h + + .text + +_GLOBAL(low_sleep_handler) + mflr r0 + stw r0,4(r1) + stwu r1,-SL_SIZE(r1) + stw r2,SL_R2(r1) + stmw r12,SL_R12(r1) + + /* Save MSR, SDR1, TB */ + mfmsr r4 + stw r4,SL_MSR(r1) + mfsdr1 r4 + stw r4,SL_SDR1(r1) +1: + mftbu r4 + stw r4,SL_TB(r1) + mftb r5 + stw r5,SL_TB+4(r1) + mftbu r3 + cmpw r3,r4 + bne 1b + + /* Save SPRGs */ + mfsprg r4,0 + stw r4,SL_SPRG0(r1) + mfsprg r4,1 + stw r4,SL_SPRG0+4(r1) + mfsprg r4,2 + stw r4,SL_SPRG0+8(r1) + mfsprg r4,3 + stw r4,SL_SPRG0+12(r1) + + /* Save BATs */ + mfdbatu r4,0 + stw r4,SL_DBAT0(r1) + mfdbatl r4,0 + stw r4,SL_DBAT0+4(r1) + mfdbatu r4,1 + stw r4,SL_DBAT1(r1) + mfdbatl r4,1 + stw r4,SL_DBAT1+4(r1) + mfdbatu r4,2 + stw r4,SL_DBAT2(r1) + mfdbatl r4,2 + stw r4,SL_DBAT2+4(r1) + mfdbatu r4,3 + stw r4,SL_DBAT3(r1) + mfdbatl r4,3 + stw r4,SL_DBAT3+4(r1) + mfibatu r4,0 + stw r4,SL_IBAT0(r1) + mfibatl r4,0 + stw r4,SL_IBAT0+4(r1) + mfibatu r4,1 + stw r4,SL_IBAT1(r1) + mfibatl r4,1 + stw r4,SL_IBAT1+4(r1) + mfibatu r4,2 + stw r4,SL_IBAT2(r1) + mfibatl r4,2 + stw r4,SL_IBAT2+4(r1) + mfibatu r4,3 + stw r4,SL_IBAT3(r1) + mfibatl r4,3 + stw r4,SL_IBAT3+4(r1) + + /* Save HID0 */ + mfspr r4,HID0 + stw r4,SL_HID0(r1) + + /* Set up stuff at address 0 */ + lis r5,wake_up@ha + addi r5,r5,wake_up@l + tophys(r5,r5) + stw r5,SL_PC(r1) + lis r4,KERNELBASE@h + tophys(r5,r1) + addi r5,r5,SL_PC + lis r6,MAGIC@ha + addi r6,r6,MAGIC@l + stw r5,0(r4) + stw r6,4(r4) + +/* + * Flush the L1 data cache by reading the first 64kB of RAM + * and then flushing the same area with the dcbf instruction. + * The L2 cache has already been disabled. + */ + li r4,0x0800 /* 64kB / 32B */ + mtctr r4 + lis r4,KERNELBASE@h +1: + lwz r0,0(r4) + addi r4,r4,0x0020 /* Go to start of next cache line */ + bdnz 1b + sync + + li r4,0x0800 /* 64k */ + mtctr r4 + lis r4,KERNELBASE@h +1: + dcbf r0,r4 + addi r4,r4,0x0020 /* Go to start of next cache line */ + bdnz 1b + sync + +/* + * Set the HID0 and MSR for sleep. + */ + mfspr r2,HID0 + rlwinm r2,r2,0,10,7 /* clear doze, nap */ + oris r2,r2,HID0_SLEEP@h + sync + mtspr HID0,r2 + sync + + mfmsr r2 + oris r2,r2,MSR_POW@h +1: sync + mtmsr r2 + isync + b 1b + +/* + * Here is the resume code. + * r1 has the physical address of SL_PC(sp). + */ + +wake_up: + /* Restore the HID0 register. This turns on the L1 caches. */ + subi r1,r1,SL_PC + lwz r3,SL_HID0(r1) + sync + isync + mtspr HID0,r3 + sync + + /* Restore the kernel's segment registers, the + BATs, and SDR1. Then we can turn on the MMU. */ + li r0,16 /* load up segment register values */ + mtctr r0 /* for context 0 */ + lis r3,0x2000 /* Ku = 1, VSID = 0 */ + li r4,0 +3: mtsrin r3,r4 + addi r3,r3,1 /* increment VSID */ + addis r4,r4,0x1000 /* address of next segment */ + bdnz 3b + + lwz r4,SL_SDR1(r1) + mtsdr1 r4 + lwz r4,SL_SPRG0(r1) + mtsprg 0,r4 + lwz r4,SL_SPRG0+4(r1) + mtsprg 1,r4 + lwz r4,SL_SPRG0+8(r1) + mtsprg 2,r4 + lwz r4,SL_SPRG0+12(r1) + mtsprg 3,r4 + + lwz r4,SL_DBAT0(r1) + mtdbatu 0,r4 + lwz r4,SL_DBAT0+4(r1) + mtdbatl 0,r4 + lwz r4,SL_DBAT1(r1) + mtdbatu 1,r4 + lwz r4,SL_DBAT1+4(r1) + mtdbatl 1,r4 + lwz r4,SL_DBAT2(r1) + mtdbatu 2,r4 + lwz r4,SL_DBAT2+4(r1) + mtdbatl 2,r4 + lwz r4,SL_DBAT3(r1) + mtdbatu 3,r4 + lwz r4,SL_DBAT3+4(r1) + mtdbatl 3,r4 + lwz r4,SL_IBAT0(r1) + mtibatu 0,r4 + lwz r4,SL_IBAT0+4(r1) + mtibatl 0,r4 + lwz r4,SL_IBAT1(r1) + mtibatu 1,r4 + lwz r4,SL_IBAT1+4(r1) + mtibatl 1,r4 + lwz r4,SL_IBAT2(r1) + mtibatu 2,r4 + lwz r4,SL_IBAT2+4(r1) + mtibatl 2,r4 + lwz r4,SL_IBAT3(r1) + mtibatu 3,r4 + lwz r4,SL_IBAT3+4(r1) + mtibatl 3,r4 + + /* restore the MSR and turn on the MMU */ + lwz r3,SL_MSR(r1) + bl turn_on_mmu + + /* get back the stack pointer */ + tovirt(r1,r1) + + /* Restore TB */ + lwz r3,SL_TB(r1) + lwz r4,SL_TB+4(r1) + mttbu r3 + mttbl r4 + + /* Restore the callee-saved registers and return */ + lwz r2,SL_R2(r1) + lmw r12,SL_R12(r1) + addi r1,r1,SL_SIZE + lwz r0,4(r1) + mtlr r0 + blr + +turn_on_mmu: + mflr r4 + tovirt(r4,r4) + mtsrr0 r4 + mtsrr1 r3 + sync + rfi diff -u --recursive --new-file v2.3.19/linux/arch/ppc/kernel/smp.c linux/arch/ppc/kernel/smp.c --- v2.3.19/linux/arch/ppc/kernel/smp.c Fri Sep 10 23:57:28 1999 +++ linux/arch/ppc/kernel/smp.c Thu Oct 7 10:17:08 1999 @@ -1,11 +1,13 @@ /* - * $Id: smp.c,v 1.62 1999/09/05 11:56:34 paulus Exp $ + * $Id: smp.c,v 1.68 1999/09/17 19:38:05 cort Exp $ * * Smp support for ppc. * * Written by Cort Dougan (cort@cs.nmt.edu) borrowing a great * deal of code from the sparc and intel versions. * + * Copyright (C) 1999 Cort Dougan + * * Support for PReP (Motorola MTX/MVME) SMP by Troy Benjegerdes * (troy@microux.com, hozer@drgw.net) */ @@ -34,9 +36,9 @@ #include #include #include +#include #include "time.h" -int first_cpu_booted = 0; int smp_threads_ready = 0; volatile int smp_commenced = 0; int smp_num_cpus = 1; @@ -251,7 +253,6 @@ printk("Entering SMP Mode...\n"); /* let other processors know to not do certain initialization */ - first_cpu_booted = 1; smp_num_cpus = 1; smp_store_cpu_info(0); @@ -276,7 +277,7 @@ */ cacheflush_time = 5 * 1024; - if ( !(_machine & (_MACH_Pmac|_MACH_chrp)) ) + if ( !(_machine & (_MACH_Pmac|_MACH_chrp|_MACH_gemini)) ) { printk("SMP not supported on this machine.\n"); return; @@ -297,6 +298,10 @@ #endif cpu_nr = smp_chrp_cpu_nr; break; + case _MACH_gemini: + cpu_nr = (readb(GEMINI_CPUSTAT) & GEMINI_CPU_COUNT_MASK)>>2; + cpu_nr = (cpu_nr == 0) ? 4 : cpu_nr; + break; } /* @@ -307,7 +312,6 @@ { int c; struct pt_regs regs; - struct task_struct *idle; /* create a process for the processor */ /* we don't care about the values in regs since we'll @@ -359,6 +363,10 @@ *(ulong *)get_property(device, "reg", NULL), __pa(__secondary_start_chrp), i); #endif + break; + case _MACH_gemini: + openpic_init_processor( 1<dar); return; -#endif /* CONFIG_MBX */ +#endif #if defined(CONFIG_XMON) || defined(CONFIG_KGDB) if (debugger_fault_handler) { debugger_fault_handler(regs); @@ -241,10 +241,14 @@ panic("Kernel Mode Software FPU Emulation"); } +#ifdef CONFIG_MATH_EMULATION if ((errcode = do_mathemu(regs))) { +#else + if ((errcode = Soft_emulate_8xx(regs))) { +#endif if (errcode > 0) _exception(SIGFPE, regs); - else if (errcode == -EFAULT; + else if (errcode == -EFAULT) _exception(SIGSEGV, regs); else _exception(SIGILL, regs); diff -u --recursive --new-file v2.3.19/linux/arch/ppc/lib/locks.c linux/arch/ppc/lib/locks.c --- v2.3.19/linux/arch/ppc/lib/locks.c Fri Sep 10 23:57:28 1999 +++ linux/arch/ppc/lib/locks.c Thu Oct 7 10:17:08 1999 @@ -1,5 +1,5 @@ /* - * $Id: locks.c,v 1.24 1999/08/03 19:16:47 cort Exp $ + * $Id: locks.c,v 1.25 1999/09/10 10:40:13 davem Exp $ * * Locks for smp ppc * diff -u --recursive --new-file v2.3.19/linux/arch/ppc/mbxboot/Makefile linux/arch/ppc/mbxboot/Makefile --- v2.3.19/linux/arch/ppc/mbxboot/Makefile Fri Mar 19 10:50:03 1999 +++ linux/arch/ppc/mbxboot/Makefile Thu Oct 7 10:17:08 1999 @@ -1,5 +1,5 @@ # -# arch/ppc/boot/Makefile +# arch/ppc/mbxboot/Makefile # # This file is subject to the terms and conditions of the GNU General Public # License. See the file "COPYING" in the main directory of this archive @@ -14,7 +14,7 @@ .s.o: $(AS) -o $*.o $< .c.o: - $(CC) $(CFLAGS) -DINITRD_OFFSET=$(IOFF) -DINITRD_SIZE=$(ISZ) -DZIMAGE_OFFSET=$(ZOFF) -DZIMAGE_SIZE=$(ZSZ) -DKERNELBASE=$(KERNELBASE) -c -o $*.o $< + $(CC) $(CFLAGS) -DINITRD_OFFSET=$(IOFF) -DINITRD_SIZE=$(ISZ) -DZIMAGE_OFFSET=$(ZOFF) -DZIMAGE_SIZE=$(ZSZ) -c -o $*.o $< .S.s: $(CC) -D__ASSEMBLY__ -traditional -E -o $*.o $< .S.o: @@ -29,30 +29,46 @@ ZLINKFLAGS = -T ../vmlinux.lds -Ttext 0x00100000 GZIP_FLAGS = -v9 -OBJECTS := head.o misc.o ../coffboot/zlib.o mbxtty.o -CFLAGS = -O2 -DSTDC_HEADERS -fno-builtin -I$(TOPDIR)/include -DCONFIG_MBX +OBJECTS := head.o misc.o ../coffboot/zlib.o m8xx_tty.o +CFLAGS = -O2 -DSTDC_HEADERS -fno-builtin -I$(TOPDIR)/include -DCONFIG_8xx OBJCOPY = $(CROSS_COMPILE)objcopy OBJCOPY_ARGS = -O elf32-powerpc +ifeq ($(CONFIG_MBX),y) +OBJECTS += pci.o qspan_pci.o +CFLAGS += -DCONFIG_MBX +endif +ifeq ($(CONFIG_RPXLITE),y) +CFLAGS += -DCONFIG_RPXLITE +OBJECTS += iic.o embed_config.o +endif +ifeq ($(CONFIG_RPXCLASSIC),y) +CFLAGS += -DCONFIG_RPXCLASSIC +OBJECTS += iic.o embed_config.o pci.o qspan_pci.o +endif +ifeq ($(CONFIG_BSEIP),y) +CFLAGS += -DCONFIG_BSEIP +OBJECTS += iic.o embed_config.o +endif + all: zImage zvmlinux.initrd: zvmlinux - $(LD) $(ZLINKFLAGS) -o zvmlinux.initrd.tmp $(OBJECTS) + $(LD) $(ZLINKFLAGS) -o zvmlinux.initrd.tmp1 $(OBJECTS) $(OBJCOPY) $(OBJCOPY_ARGS) -R .comment \ --add-section=initrd=ramdisk.image.gz \ --add-section=image=../coffboot/vmlinux.gz \ - zvmlinux.initrd.tmp zvmlinux.initrd - $(CC) $(CFLAGS) -DINITRD_OFFSET=`sh offset $(OBJDUMP) zvmlinux.initrd initrd` \ - -DINITRD_SIZE=`sh size $(OBJDUMP) zvmlinux.initrd initrd` \ - -DZIMAGE_OFFSET=`sh offset $(OBJDUMP) zvmlinux.initrd image` \ - -DZIMAGE_SIZE=`sh size $(OBJDUMP) zvmlinux.initrd image` \ - -DKERNELBASE=$(KERNELBASE) -c -o misc.o misc.c + zvmlinux.initrd.tmp1 zvmlinux.initrd1 + $(CC) $(CFLAGS) -DINITRD_OFFSET=`sh offset $(OBJDUMP) zvmlinux.initrd1 initrd` \ + -DINITRD_SIZE=`sh size $(OBJDUMP) zvmlinux.initrd1 initrd` \ + -DZIMAGE_OFFSET=`sh offset $(OBJDUMP) zvmlinux.initrd1 image` \ + -DZIMAGE_SIZE=`sh size $(OBJDUMP) zvmlinux.initrd1 image` \ + -c -o misc.o misc.c $(LD) $(ZLINKFLAGS) -o zvmlinux.initrd.tmp $(OBJECTS) $(OBJCOPY) $(OBJCOPY_ARGS) -R .comment \ --add-section=initrd=ramdisk.image.gz \ --add-section=image=../coffboot/vmlinux.gz \ zvmlinux.initrd.tmp $@ - rm zvmlinux.initrd.tmp zImage: zvmlinux ln -sf zvmlinux zImage @@ -73,7 +89,7 @@ # $(CC) $(CFLAGS) -DINITRD_OFFSET=0 -DINITRD_SIZE=0 \ -DZIMAGE_OFFSET=`sh offset $(OBJDUMP) zvmlinux image` \ - -DZIMAGE_SIZE=`sh size $(OBJDUMP) zvmlinux image` -DKERNELBASE=$(KERNELBASE) \ + -DZIMAGE_SIZE=`sh size $(OBJDUMP) zvmlinux image` \ -c -o misc.o misc.c $(LD) $(ZLINKFLAGS) -o zvmlinux.tmp $(OBJECTS) $(OBJCOPY) $(OBJCOPY_ARGS) -R .comment --add-section=image=../coffboot/vmlinux.gz \ diff -u --recursive --new-file v2.3.19/linux/arch/ppc/mbxboot/embed_config.c linux/arch/ppc/mbxboot/embed_config.c --- v2.3.19/linux/arch/ppc/mbxboot/embed_config.c Wed Dec 31 16:00:00 1969 +++ linux/arch/ppc/mbxboot/embed_config.c Thu Oct 7 10:17:08 1999 @@ -0,0 +1,207 @@ + +/* Board specific functions for those embedded 8xx boards that do + * not have boot monitor support for board information. + */ +#include +#include "asm/mpc8xx.h" + + +/* IIC functions. + * These are just the basic master read/write operations so we can + * examine serial EEPROM. + */ +extern void iic_read(uint devaddr, u_char *buf, uint offset, uint count); +extern u_char aschex_to_byte(u_char *cp); + +static void rpx_eth(bd_t *bd, u_char *cp); +static void rpx_brate(bd_t *bd, u_char *cp); +static void rpx_memsize(bd_t *bd, u_char *cp); +static void rpx_cpuspeed(bd_t *bd, u_char *cp); + +/* Read the EEPROM on the RPX-Lite board. +*/ +void +rpx_cfg(bd_t *bd) +{ + u_char eebuf[256], *cp; + + /* Read the first 256 bytes of the EEPROM. I think this + * is really all there is, and I hope if it gets bigger the + * info we want is still up front. + */ +#if 1 + iic_read(0xa8, eebuf, 0, 128); + iic_read(0xa8, &eebuf[128], 128, 128); + { + int i; + cp = (u_char *)0xfa000000; + + for (i=0; i<256; i++) + *cp++ = eebuf[i]; + } + + /* We look for two things, the Ethernet address and the + * serial baud rate. The records are separated by + * newlines. + */ + cp = eebuf; + for (;;) { + if (*cp == 'E') { + cp++; + if (*cp == 'A') { + cp += 2; + rpx_eth(bd, cp); + } + } + if (*cp == 'S') { + cp++; + if (*cp == 'B') { + cp += 2; + rpx_brate(bd, cp); + } + } + if (*cp == 'D') { + cp++; + if (*cp == '1') { + cp += 2; + rpx_memsize(bd, cp); + } + } + if (*cp == 'H') { + cp++; + if (*cp == 'Z') { + cp += 2; + rpx_cpuspeed(bd, cp); + } + } + + /* Scan to the end of the record. + */ + while ((*cp != '\n') && (*cp != 0xff)) + cp++; + + /* If the next character is a 0 or ff, we are done. + */ + cp++; + if ((*cp == 0) || (*cp == 0xff)) + break; + } + bd->bi_memstart = 0; + +#else + bd->bi_memstart = 0; + bd->bi_memsize = (4 * 1024 * 1024); + bd->bi_intfreq = 48; + bd->bi_busfreq = 48; + bd->bi_baudrate = 9600; +#endif +} + +static void +rpx_eth(bd_t *bd, u_char *cp) +{ + int i; + + for (i=0; i<6; i++) { + bd->bi_enetaddr[i] = aschex_to_byte(cp); + cp += 2; + } +} + +static void +rpx_brate(bd_t *bd, u_char *cp) +{ + uint rate; + + rate = 0; + + while (*cp != '\n') { + rate *= 10; + rate += (*cp) - '0'; + cp++; + } + + bd->bi_baudrate = rate * 100; +} + +static void +rpx_memsize(bd_t *bd, u_char *cp) +{ + uint size; + + size = 0; + + while (*cp != '\n') { + size *= 10; + size += (*cp) - '0'; + cp++; + } + + bd->bi_memsize = size * 1024 * 1024; +} + +static void +rpx_cpuspeed(bd_t *bd, u_char *cp) +{ + uint num, den; + + num = den = 0; + + while (*cp != '\n') { + num *= 10; + num += (*cp) - '0'; + cp++; + if (*cp == '/') { + cp++; + den = (*cp) - '0'; + break; + } + } + + /* I don't know why the RPX just can't state the actual + * CPU speed..... + */ + if (den) { + num /= den; + num *= den; + } + bd->bi_intfreq = bd->bi_busfreq = num; + + /* The 8xx can only run a maximum 50 MHz bus speed (until + * Motorola changes this :-). Greater than 50 MHz parts + * run internal/2 for bus speed. + */ + if (num > 50) + bd->bi_busfreq /= 2; +} + +/* Build a board information structure for the BSE ip-Engine. + * There is more to come since we will add some environment + * variables and a function to read them. + */ +void +bseip_cfg(bd_t *bd) +{ + u_char *cp; + int i; + + /* Baud rate and processor speed will eventually come + * from the environment variables. + */ + bd->bi_baudrate = 9600; + + /* Get the Ethernet station address from the Flash ROM. + */ + cp = (u_char *)0xfe003ffa; + for (i=0; i<6; i++) { + bd->bi_enetaddr[i] = *cp++; + } + + /* The rest of this should come from the environment as well. + */ + bd->bi_memstart = 0; + bd->bi_memsize = (16 * 1024 * 1024); + bd->bi_intfreq = 48; + bd->bi_busfreq = 48; +} + diff -u --recursive --new-file v2.3.19/linux/arch/ppc/mbxboot/head.S linux/arch/ppc/mbxboot/head.S --- v2.3.19/linux/arch/ppc/mbxboot/head.S Thu Apr 29 12:39:01 1999 +++ linux/arch/ppc/mbxboot/head.S Thu Oct 7 10:17:08 1999 @@ -1,3 +1,4 @@ +#include #include "../kernel/ppc_defs.h" #include "../kernel/ppc_asm.tmpl" #include @@ -6,37 +7,101 @@ .text /* - * $Id: head.S,v 1.4 1999/04/22 06:32:09 davem Exp $ + * $Id: head.S,v 1.6 1999/09/15 00:02:25 dmalek Exp $ * * This code is loaded by the ROM loader at some arbitrary location. * Move it to high memory so that it can load the kernel at 0x0000. * - * The MBX EPPC-Bug understands ELF, so it loads us into the location - * specified in the header. This is a two step process. First, EPPC-Bug - * loads the file into the intermediate buffer memory location specified - * by the environment parameters. When it discovers this is an ELF - * binary, it relocates to the link address for us. Unfortunately, the - * header does not move with the file, so we have to find the - * intermediate load location and read the header from there. From - * information provided by Motorola (thank you), we know this intermediate - * location can be found from the NVRAM environment. - * All of these addresses must be somewhat carefully chosen to make sure - * we don't overlap the regions. I chose to load the kernel at 0, the - * compressed image loads at 0x00100000, and the MBX intermediate buffer - * was set to 0x00200000. Provided the loaded kernel image never grows - * over one megabyte (which I am going to ensure never happens :-), these - * will work fine. When we get called from EPPC-Bug, registers are: + * This is a three step process that will also work when booting from + * a Flash PROM normally located in high memory. + * + * First, the entire image is loaded into some high memory address. + * This is usually at or above 0x02000000. This is done by a network + * boot function supported by the board or a debugger over BDM port. + * + * Second, the start up function here will relocate the decompress + * function to run at the link address of 0x01000000. + * + * Last, the decompression function will reloate the initrd, zImage, and + * the residual data to locations under 8 Meg. This is necessary because + * the embedded kernel start up uses 8 Meg translations to access physical + * space before the MMU is enabled. Finally, the zImage is uncompressed + * to location 0 and we jump to it. + * + * On the MBX, * R1 - Stack pointer at a high memory address. * R3 - Pointer to Board Information Block. * R4 - Pointer to argument string. * Interrupts masked, cache and MMU disabled. + * + * ...and the first and second functions listed above are + * done for us (it knows ELF images). + * + * For other embedded boards we build the Board Information Block. */ .globl start start: bl start_ start_: - mr r11,r3 /* Save pointer to residual/board data */ +#ifndef CONFIG_MBX + lis r11, local_bd_info@h + ori r11, r11, local_bd_info@l +#else + mr r11, r3 +#endif + + mfmsr r3 /* Turn off interrupts */ + li r4,0 + ori r4,r4,MSR_EE + andc r3,r3,r4 + mtmsr r3 + +/* check if we need to relocate ourselves to the link addr or were we + loaded there to begin with -- Cort */ + lis r4,start@h + ori r4,r4,start@l + mflr r3 + subi r3,r3,4 /* we get the nip, not the ip of the branch */ + mr r8,r3 +#if 0 + cmp 0,r3,r4 + beq start_ldr /* Branch if loaded OK */ +#endif + +/* + * no matter where we're loaded, move ourselves to -Ttext address + * This computes the sizes we need to determine other things. + */ + lis r5,end@h + ori r5,r5,end@l + addi r5,r5,3 /* Round up - just in case */ + sub r5,r5,r4 /* Compute # longwords to move */ + srwi r5,r5,2 + mtctr r5 + mr r7,r5 + li r6,0 + subi r3,r3,4 /* Set up for loop */ + subi r4,r4,4 +00: lwzu r5,4(r3) + stwu r5,4(r4) + xor r6,r6,r5 + bdnz 00b + + lis r3,start_ldr@h + ori r3,r3,start_ldr@l + mtlr r3 /* Easiest way to do an absolute jump */ + blr + +start_ldr: +/* Most 8xx boards don't boot up with the I-cache enabled. Do that + * now because the decompress runs much faster that way. + */ + lis r3, IDC_INVALL@h + mtspr IC_CST, r3 + lis r3, IDC_ENABLE@h + mtspr IC_CST, r3 + /* Clear all of BSS */ lis r3,edata@h ori r3,r3,edata@l @@ -48,39 +113,60 @@ 50: stwu r0,4(r3) cmp 0,r3,r4 bne 50b -90: mr r9,r1 /* Save old stack pointer (in case it matters) */ + lis r1,.stack@h ori r1,r1,.stack@l addi r1,r1,4096*2 subi r1,r1,256 li r2,0x000F /* Mask pointer to 16-byte boundary */ andc r1,r1,r2 -/* Run loader */ + + /* Perform configuration of the various boards. This is done + * by reading some configuration data from EEPROM and building + * the board information structure. + */ mr r3, r11 mr r21, r11 + mr r22, r8 + mr r23, r7 + mr r24, r6 + +#if defined(CONFIG_RPXLITE) || defined(CONFIG_RPXCLASSIC) + bl rpx_cfg + mr r3, r21 +#endif +#ifdef CONFIG_BSEIP + bl bseip_cfg + mr r3, r21 +#endif bl serial_init /* Init MBX serial port */ - lis r8, 0xfa200000@h /* Disable Ethernet SCC */ + mr r11, r21 + mr r8, r22 + mr r7, r23 + mr r6, r24 + +#ifdef CONFIG_MBX + lis r18, 0xfa200000@h /* Disable Ethernet SCC */ li r0, 0 - stw r0, 0x0a00(r8) + stw r0, 0x0a00(r18) - mr r11, r21 - lis r8,start@h - ori r8,r8,start@l - lis r9,end@h - ori r9,r9,end@l - sub r7,r8,r9 - srwi r7,r7,2 + /* On the MBX (or anything that will TFTP load an ELF image), + * we have to find the intermediate address. The ELF loader + * only moves the Linux boostrap/decompress, not the zImage. + */ #define ILAP_ADDRESS 0xfa000020 lis r8, ILAP_ADDRESS@h lwz r8, ILAP_ADDRESS@l(r8) addis r8, r8, 1 /* Add 64K */ +#endif + mr r3,r8 /* Load point */ mr r4,r7 /* Program length */ mr r5,r6 /* Checksum */ mr r6,r11 /* Residual data */ bl decompress_kernel - + /* changed to use r3 (as firmware does) for kernel as ptr to residual -- Cort*/ lis r6,cmd_line@h @@ -99,14 +185,17 @@ ori r2,r2,initrd_end@l lwz r5,0(r2) - /* tell kernel we're prep */ - /* - * get start address of kernel code which is stored as a coff - * entry. see boot/head.S -- Cort - */ + /* The world starts from the beginning. + */ li r9,0x0 - lwz r9,0(r9) mtlr r9 + + /* Invalidate the instruction cache because we just copied a + * bunch of kernel instructions. + */ + lis r9, IDC_INVALL@h + mtspr IC_CST, r9 + blr hang: b hang @@ -117,19 +206,6 @@ */ .globl udelay udelay: - mfspr r4,PVR - srwi r4,r4,16 - cmpi 0,r4,1 /* 601 ? */ - bne .udelay_not_601 -00: li r0,86 /* Instructions / microsecond? */ - mtctr r0 -10: addi r0,r0,0 /* NOP */ - bdnz 10b - subic. r3,r3,1 - bne 00b - blr - -.udelay_not_601: mulli r4,r3,1000 /* nanoseconds */ addi r4,r4,59 li r5,60 @@ -150,16 +226,6 @@ blt 2b 3: blr -.globl _get_HID0 -_get_HID0: - mfspr r3,HID0 - blr - -.globl _put_HID0 -_put_HID0: - mtspr HID0,r3 - blr - .globl _get_MSR _get_MSR: mfmsr r3 @@ -170,31 +236,14 @@ mtmsr r3 blr -/* - * Flush instruction cache - * *** I'm really paranoid here! - */ -_GLOBAL(flush_instruction_cache) - mflr r5 - bl flush_data_cache - mtlr r5 - blr - -#define NUM_CACHE_LINES 128*8 -#define CACHE_LINE_SIZE 32 -#define cache_flush_buffer 0x1000 - -/* - * Flush data cache - * *** I'm really paranoid here! - */ -_GLOBAL(flush_data_cache) - lis r3,cache_flush_buffer@h - ori r3,r3,cache_flush_buffer@l - li r4,NUM_CACHE_LINES - mtctr r4 -00: lwz r4,0(r3) - addi r3,r3,CACHE_LINE_SIZE /* Next line, please */ - bdnz 00b -10: blr .comm .stack,4096*2,4 +#ifndef CONFIG_MBX +local_bd_info: + .long 0 + .long 0x01000000 + .long 64 + .long 64 + .long 0 + .long 0 + .long 0 +#endif diff -u --recursive --new-file v2.3.19/linux/arch/ppc/mbxboot/iic.c linux/arch/ppc/mbxboot/iic.c --- v2.3.19/linux/arch/ppc/mbxboot/iic.c Wed Dec 31 16:00:00 1969 +++ linux/arch/ppc/mbxboot/iic.c Thu Oct 7 10:17:08 1999 @@ -0,0 +1,250 @@ + +/* Minimal support functions to read configuration from IIC EEPROMS + * on MPC8xx boards. Originally written for RPGC RPX-Lite. + * Dan Malek (dmalek@jlc.net). + */ +#include +#include +#include "asm/mpc8xx.h" +#include "../8xx_io/commproc.h" + + +/* IIC functions. + * These are just the basic master read/write operations so we can + * examine serial EEPROM. + */ +void iic_read(uint devaddr, u_char *buf, uint offset, uint count); +u_char aschex_to_byte(u_char *cp); + +static int iic_init_done; + +static void +iic_init() +{ + volatile iic_t *iip; + volatile i2c8xx_t *i2c; + volatile cbd_t *tbdf, *rbdf; + volatile cpm8xx_t *cp; + volatile immap_t *immap; + uint dpaddr; + + immap = (immap_t *)IMAP_ADDR; + cp = (cpm8xx_t *)&(immap->im_cpm); + + /* Reset the CPM. This is necessary on the 860 processors + * that may have started the SCC1 ethernet without relocating + * the IIC. + * This also stops the Ethernet in case we were loaded by a + * BOOTP rom monitor. + */ + cp->cp_cpcr = (CPM_CR_RST | CPM_CR_FLG); + + /* Wait for it. + */ + while (cp->cp_cpcr & (CPM_CR_RST | CPM_CR_FLG)); + + iip = (iic_t *)&cp->cp_dparam[PROFF_IIC]; + i2c = (i2c8xx_t *)&(immap->im_i2c); + + /* Initialize Port B IIC pins. + */ + cp->cp_pbpar |= 0x00000030; + cp->cp_pbdir |= 0x00000030; + cp->cp_pbodr |= 0x00000030; + + /* Initialize the parameter ram. + */ + + /* Allocate space for a two transmit and one receive buffer + * descriptor in the DP ram. + * For now, this address seems OK, but it may have to + * change with newer versions of the firmware. + */ + dpaddr = 0x0840; + + /* Set up the IIC parameters in the parameter ram. + */ + iip->iic_tbase = dpaddr; + iip->iic_rbase = dpaddr + (2 * sizeof(cbd_t)); + + iip->iic_tfcr = SMC_EB; + iip->iic_rfcr = SMC_EB; + + /* This should really be done by the reader/writer. + */ + iip->iic_mrblr = 128; + + /* Initialize Tx/Rx parameters. + */ + cp->cp_cpcr = mk_cr_cmd(CPM_CR_CH_I2C, CPM_CR_INIT_TRX) | CPM_CR_FLG; + while (cp->cp_cpcr & CPM_CR_FLG); + + /* Select an arbitrary address. Just make sure it is unique. + */ + i2c->i2c_i2add = 0x34; + + /* Make clock run maximum slow. + */ + i2c->i2c_i2brg = 7; + + /* Disable interrupts. + */ + i2c->i2c_i2cmr = 0; + i2c->i2c_i2cer = 0xff; + + /* Enable SDMA. + */ + immap->im_siu_conf.sc_sdcr = 1; + + iic_init_done = 1; +} + +/* Read from IIC. + * Caller provides device address, memory buffer, and byte count. + */ +static u_char iitemp[32]; + +void +iic_read(uint devaddr, u_char *buf, uint offset, uint count) +{ + volatile iic_t *iip; + volatile i2c8xx_t *i2c; + volatile cbd_t *tbdf, *rbdf; + volatile cpm8xx_t *cp; + volatile immap_t *immap; + u_char *tb; + uint dpaddr, temp; + + /* If the interface has not been initialized, do that now. + */ + if (!iic_init_done) + iic_init(); + + immap = (immap_t *)IMAP_ADDR; + cp = (cpm8xx_t *)&(immap->im_cpm); + + iip = (iic_t *)&cp->cp_dparam[PROFF_IIC]; + i2c = (i2c8xx_t *)&(immap->im_i2c); + + tbdf = (cbd_t *)&cp->cp_dpmem[iip->iic_tbase]; + rbdf = (cbd_t *)&cp->cp_dpmem[iip->iic_rbase]; + + /* Send a "dummy write" operation. This is a write request with + * only the offset sent, followed by another start condition. + * This will ensure we start reading from the first location + * of the EEPROM. + */ + tb = iitemp; + tb = (u_char *)(((uint)tb + 15) & ~15); + tbdf->cbd_bufaddr = tb; + *tb = devaddr & 0xfe; /* Device address */ + *(tb+1) = offset; /* Offset */ + tbdf->cbd_datlen = 2; /* Length */ + tbdf->cbd_sc = + BD_SC_READY | BD_SC_LAST | BD_SC_WRAP | BD_IIC_START; + + i2c->i2c_i2mod = 1; /* Enable */ + i2c->i2c_i2cer = 0xff; + i2c->i2c_i2com = 0x81; /* Start master */ + + /* Wait for IIC transfer. + */ +#if 0 + while ((i2c->i2c_i2cer & 3) == 0); + + if (tbdf->cbd_sc & BD_SC_READY) + printf("IIC ra complete but tbuf ready\n"); +#else + temp = 10000000; + while ((tbdf->cbd_sc & BD_SC_READY) && (temp != 0)) + temp--; +#if 0 + /* We can't do this...there is no serial port yet! + */ + if (temp == 0) { + printf("Timeout reading EEPROM\n"); + return; + } +#endif +#endif + + /* Chip errata, clear enable. + */ + i2c->i2c_i2mod = 0; + + /* To read, we need an empty buffer of the proper length. + * All that is used is the first byte for address, the remainder + * is just used for timing (and doesn't really have to exist). + */ + tbdf->cbd_bufaddr = tb; + *tb = devaddr | 1; /* Device address */ + rbdf->cbd_bufaddr = (uint)buf; /* Desination buffer */ + tbdf->cbd_datlen = rbdf->cbd_datlen = count + 1; /* Length */ + tbdf->cbd_sc = BD_SC_READY | BD_SC_LAST | BD_SC_WRAP | BD_IIC_START; + rbdf->cbd_sc = BD_SC_EMPTY | BD_SC_WRAP; + + /* Chip bug, set enable here. + */ + i2c->i2c_i2mod = 1; /* Enable */ + i2c->i2c_i2cer = 0xff; + i2c->i2c_i2com = 0x81; /* Start master */ + + /* Wait for IIC transfer. + */ +#if 0 + while ((i2c->i2c_i2cer & 1) == 0); + + if (rbdf->cbd_sc & BD_SC_EMPTY) + printf("IIC read complete but rbuf empty\n"); +#else + temp = 10000000; + while ((tbdf->cbd_sc & BD_SC_READY) && (temp != 0)) + temp--; +#endif + + /* Chip errata, clear enable. + */ + i2c->i2c_i2mod = 0; +} + +/* Because I didn't find anything that would do this....... +*/ +u_char +aschex_to_byte(u_char *cp) +{ + u_char byte, c; + + c = *cp++; + + if ((c >= 'A') && (c <= 'F')) { + c -= 'A'; + c += 10; + } + else if ((c >= 'a') && (c <= 'f')) { + c -= 'a'; + c += 10; + } + else { + c -= '0'; + } + + byte = c * 16; + + c = *cp; + + if ((c >= 'A') && (c <= 'F')) { + c -= 'A'; + c += 10; + } + else if ((c >= 'a') && (c <= 'f')) { + c -= 'a'; + c += 10; + } + else { + c -= '0'; + } + + byte += c; + + return(byte); +} diff -u --recursive --new-file v2.3.19/linux/arch/ppc/mbxboot/m8xx_tty.c linux/arch/ppc/mbxboot/m8xx_tty.c --- v2.3.19/linux/arch/ppc/mbxboot/m8xx_tty.c Wed Dec 31 16:00:00 1969 +++ linux/arch/ppc/mbxboot/m8xx_tty.c Thu Oct 7 10:17:08 1999 @@ -0,0 +1,253 @@ + + +/* Minimal serial functions needed to send messages out the serial + * port on the MBX console. + * + * The MBX uxes SMC1 for the serial port. We reset the port and use + * only the first BD that EPPC-Bug set up as a character FIFO. + * + * Later versions (at least 1.4, maybe earlier) of the MBX EPPC-Bug + * use COM1 instead of SMC1 as the console port. This kinda sucks + * for the rest of the kernel, so here we force the use of SMC1 again. + */ +#include +#include +#include +#include +#include "../8xx_io/commproc.h" + +#ifdef CONFIG_MBX +#define MBX_CSR1 ((volatile u_char *)0xfa100000) +#define CSR1_COMEN (u_char)0x02 +#endif + +static cpm8xx_t *cpmp = (cpm8xx_t *)&(((immap_t *)IMAP_ADDR)->im_cpm); + +void +serial_init(bd_t *bd) +{ + volatile smc_t *sp; + volatile smc_uart_t *up; + volatile cbd_t *tbdf, *rbdf; + volatile cpm8xx_t *cp; + uint dpaddr, memaddr; + + cp = cpmp; + sp = (smc_t*)&(cp->cp_smc[0]); + up = (smc_uart_t *)&cp->cp_dparam[PROFF_SMC1]; + + /* Disable transmitter/receiver. + */ + sp->smc_smcmr &= ~(SMCMR_REN | SMCMR_TEN); + +#ifndef CONFIG_MBX + { + /* Initialize SMC1 and use it for the console port. + */ + + /* Enable SDMA. + */ + ((immap_t *)IMAP_ADDR)->im_siu_conf.sc_sdcr = 1; + + /* Use Port B for SMCs instead of other functions. + */ + cp->cp_pbpar |= 0x00000cc0; + cp->cp_pbdir &= ~0x00000cc0; + cp->cp_pbodr &= ~0x00000cc0; + + /* Allocate space for two buffer descriptors in the DP ram. + * For now, this address seems OK, but it may have to + * change with newer versions of the firmware. + */ + dpaddr = 0x0800; + + /* Grab a few bytes from the top of memory. EPPC-Bug isn't + * running any more, so we can do this. + */ + memaddr = (bd->bi_memsize - 32) & ~15; + + /* Set the physical address of the host memory buffers in + * the buffer descriptors. + */ + rbdf = (cbd_t *)&cp->cp_dpmem[dpaddr]; + rbdf->cbd_bufaddr = memaddr; + rbdf->cbd_sc = 0; + tbdf = rbdf + 1; + tbdf->cbd_bufaddr = memaddr+4; + tbdf->cbd_sc = 0; + + /* Set up the uart parameters in the parameter ram. + */ + up->smc_rbase = dpaddr; + up->smc_tbase = dpaddr+sizeof(cbd_t); + up->smc_rfcr = SMC_EB; + up->smc_tfcr = SMC_EB; + + /* Set UART mode, 8 bit, no parity, one stop. + * Enable receive and transmit. + */ + sp->smc_smcmr = smcr_mk_clen(9) | SMCMR_SM_UART; + + /* Mask all interrupts and remove anything pending. + */ + sp->smc_smcm = 0; + sp->smc_smce = 0xff; + + /* Set up the baud rate generator. + * See 8xx_io/commproc.c for details. + */ + cp->cp_simode = 0x10000000; + cp->cp_brgc1 = + ((((bd->bi_intfreq * 1000000)/16) / bd->bi_baudrate) << 1) | CPM_BRG_EN; + +#else /* CONFIG_MBX */ + if (*MBX_CSR1 & CSR1_COMEN) { + /* COM1 is enabled. Initialize SMC1 and use it for + * the console port. + */ + + /* Enable SDMA. + */ + ((immap_t *)IMAP_ADDR)->im_siu_conf.sc_sdcr = 1; + + /* Use Port B for SMCs instead of other functions. + */ + cp->cp_pbpar |= 0x00000cc0; + cp->cp_pbdir &= ~0x00000cc0; + cp->cp_pbodr &= ~0x00000cc0; + + /* Allocate space for two buffer descriptors in the DP ram. + * For now, this address seems OK, but it may have to + * change with newer versions of the firmware. + */ + dpaddr = 0x0800; + + /* Grab a few bytes from the top of memory. EPPC-Bug isn't + * running any more, so we can do this. + */ + memaddr = (bd->bi_memsize - 32) & ~15; + + /* Set the physical address of the host memory buffers in + * the buffer descriptors. + */ + rbdf = (cbd_t *)&cp->cp_dpmem[dpaddr]; + rbdf->cbd_bufaddr = memaddr; + rbdf->cbd_sc = 0; + tbdf = rbdf + 1; + tbdf->cbd_bufaddr = memaddr+4; + tbdf->cbd_sc = 0; + + /* Set up the uart parameters in the parameter ram. + */ + up->smc_rbase = dpaddr; + up->smc_tbase = dpaddr+sizeof(cbd_t); + up->smc_rfcr = SMC_EB; + up->smc_tfcr = SMC_EB; + + /* Set UART mode, 8 bit, no parity, one stop. + * Enable receive and transmit. + */ + sp->smc_smcmr = smcr_mk_clen(9) | SMCMR_SM_UART; + + /* Mask all interrupts and remove anything pending. + */ + sp->smc_smcm = 0; + sp->smc_smce = 0xff; + + /* Set up the baud rate generator. + * See 8xx_io/commproc.c for details. + */ + cp->cp_simode = 0x10000000; + cp->cp_brgc1 = + ((((bd->bi_intfreq * 1000000)/16) / 9600) << 1) | CPM_BRG_EN; + + /* Enable SMC1 for console output. + */ + *MBX_CSR1 &= ~CSR1_COMEN; + } + else { +#endif /* ndef CONFIG_MBX */ + /* SMC1 is used as console port. + */ + tbdf = (cbd_t *)&cp->cp_dpmem[up->smc_tbase]; + rbdf = (cbd_t *)&cp->cp_dpmem[up->smc_rbase]; + + /* Issue a stop transmit, and wait for it. + */ + cp->cp_cpcr = mk_cr_cmd(CPM_CR_CH_SMC1, + CPM_CR_STOP_TX) | CPM_CR_FLG; + while (cp->cp_cpcr & CPM_CR_FLG); + } + + /* Make the first buffer the only buffer. + */ + tbdf->cbd_sc |= BD_SC_WRAP; + rbdf->cbd_sc |= BD_SC_EMPTY | BD_SC_WRAP; + + /* Single character receive. + */ + up->smc_mrblr = 1; + up->smc_maxidl = 0; + + /* Initialize Tx/Rx parameters. + */ + cp->cp_cpcr = mk_cr_cmd(CPM_CR_CH_SMC1, CPM_CR_INIT_TRX) | CPM_CR_FLG; + while (cp->cp_cpcr & CPM_CR_FLG); + + /* Enable transmitter/receiver. + */ + sp->smc_smcmr |= SMCMR_REN | SMCMR_TEN; +} + +void +serial_putchar(const char c) +{ + volatile cbd_t *tbdf; + volatile char *buf; + volatile smc_uart_t *up; + + up = (smc_uart_t *)&cpmp->cp_dparam[PROFF_SMC1]; + tbdf = (cbd_t *)&cpmp->cp_dpmem[up->smc_tbase]; + + /* Wait for last character to go. + */ + buf = (char *)tbdf->cbd_bufaddr; + while (tbdf->cbd_sc & BD_SC_READY); + + *buf = c; + tbdf->cbd_datlen = 1; + tbdf->cbd_sc |= BD_SC_READY; +} + +char +serial_getc() +{ + volatile cbd_t *rbdf; + volatile char *buf; + volatile smc_uart_t *up; + char c; + + up = (smc_uart_t *)&cpmp->cp_dparam[PROFF_SMC1]; + rbdf = (cbd_t *)&cpmp->cp_dpmem[up->smc_rbase]; + + /* Wait for character to show up. + */ + buf = (char *)rbdf->cbd_bufaddr; + while (rbdf->cbd_sc & BD_SC_EMPTY); + c = *buf; + rbdf->cbd_sc |= BD_SC_EMPTY; + + return(c); +} + +int +serial_tstc() +{ + volatile cbd_t *rbdf; + volatile smc_uart_t *up; + + up = (smc_uart_t *)&cpmp->cp_dparam[PROFF_SMC1]; + rbdf = (cbd_t *)&cpmp->cp_dpmem[up->smc_rbase]; + + return(!(rbdf->cbd_sc & BD_SC_EMPTY)); +} diff -u --recursive --new-file v2.3.19/linux/arch/ppc/mbxboot/misc.c linux/arch/ppc/mbxboot/misc.c --- v2.3.19/linux/arch/ppc/mbxboot/misc.c Fri Mar 19 10:50:03 1999 +++ linux/arch/ppc/mbxboot/misc.c Thu Oct 7 10:17:09 1999 @@ -1,7 +1,7 @@ /* * misc.c * - * $Id: misc.c,v 1.1 1999/02/17 05:00:06 cort Exp $ + * $Id: misc.c,v 1.2 1999/09/14 05:55:29 dmalek Exp $ * * Adapted for PowerPC by Gary Thomas * @@ -17,11 +17,8 @@ #include #include #include -#ifdef CONFIG_MBX -#include -#endif -#ifdef CONFIG_FADS -#include +#ifdef CONFIG_8xx +#include #endif /* @@ -34,41 +31,37 @@ char *avail_ram; char *end_avail; -/* Because of the limited amount of memory on the MBX, it presents +/* See comment below..... +*/ +unsigned int initrd_offset, initrd_size; + +/* Because of the limited amount of memory on embedded, it presents * loading problems. The biggest is that we load this boot program * into a relatively low memory address, and the Linux kernel Bss often * extends into this space when it get loaded. When the kernel starts * and zeros the BSS space, it also writes over the information we * save here and pass to the kernel (command line and board info). - * On the MBX we grab some known memory holes to hold this information. + * On these boards, we grab some known memory holes to hold this information. */ -#if defined(CONFIG_SERIAL_CONSOLE) -char cmd_preset[] = "console=ttyS0,9600n8"; -#else -char cmd_preset[] = ""; -#endif char cmd_buf[256]; char *cmd_line = cmd_buf; -char *root_string = "root=/dev/nfs"; +char *root_string = "root=/dev/nfs rw"; char *nfsaddrs_string = "nfsaddrs="; char *nfsroot_string = "nfsroot="; char *defroot_string = "/sys/mbxroot"; +char *ramroot_string = "root=/dev/ram"; int do_ipaddrs(char **cmd_cp, int echo); void do_nfsroot(char **cmd_cp, char *dp); int strncmp(const char * cs,const char * ct,size_t count); char *strrchr(const char * s, int c); -RESIDUAL hold_resid_buf; -RESIDUAL *hold_residual = &hold_resid_buf; +bd_t hold_resid_buf; +bd_t *hold_residual = &hold_resid_buf; unsigned long initrd_start = 0, initrd_end = 0; char *zimage_start; int zimage_size; -char *vidmem = (char *)0xC00B8000; -int lines, cols; -int orig_x, orig_y; - void puts(const char *); void putc(const char c); void puthex(unsigned long val); @@ -88,7 +81,7 @@ while(1); } -/* The MBX is just the serial port. +/* The MPC8xx is just the serial port. */ tstc(void) { @@ -119,7 +112,6 @@ } } - void * memcpy(void * __dest, __const void * __src, int __n) { @@ -231,45 +223,43 @@ unsigned char sanity[0x2000]; unsigned long -decompress_kernel(unsigned long load_addr, int num_words, unsigned long cksum, RESIDUAL *residual) +decompress_kernel(unsigned long load_addr, int num_words, unsigned long cksum, bd_t *bp) { int timer; extern unsigned long start; char *cp, ch; - unsigned long i, motorola_id = 0; - char needs_reloc = 0; - BATU *u; - BATL *l; + unsigned long i; char *dp; - lines = 25; - cols = 80; - orig_x = 0; - orig_y = 24; + /* These values must be variables. If not, the compiler optimizer + * will remove some code, causing the size of the code to vary + * when these values are zero. This is bad because we first + * compile with these zero to determine the size and offsets + * in an image, than compile again with these set to the proper + * discovered value.....Ya know, we used to read these from the + * header a long time ago..... + */ + initrd_offset = INITRD_OFFSET; + initrd_size = INITRD_SIZE; /* Grab some space for the command line and board info. Since * we no longer use the ELF header, but it was loaded, grab * that space. */ +#ifdef CONFIG_MBX cmd_line = (char *)(load_addr - 0x10000); - hold_residual = (RESIDUAL *)(cmd_line + sizeof(cmd_buf)); +#else + cmd_line = (char *)(0x200000); +#endif + hold_residual = (bd_t *)(cmd_line + sizeof(cmd_buf)); /* copy board data */ - if (residual) - memcpy(hold_residual,residual,sizeof(bd_t)); + if (bp) + memcpy(hold_residual,bp,sizeof(bd_t)); - /* MBX/prep sometimes put the residual/board info at the end of mem - * assume 16M for now -- Cort - * To boot on standard MBX boards with 4M, we can't use initrd, - * and we have to assume less memory. -- Dan + /* Set end of memory available to us. It is always the highest + * memory address provided by the board information. */ - if ( INITRD_OFFSET ) - end_avail = (char *)0x01000000; - else - end_avail = (char *)0x00400000; - - /* let residual data tell us it's higher */ - if ( (unsigned long)residual > 0x00800000 ) - end_avail = (char *)PAGE_ALIGN((unsigned long)residual); + end_avail = (char *)(bp->bi_memsize); puts("loaded at: "); puthex(load_addr); puts(" "); puthex((unsigned long)(load_addr + (4*num_words))); puts("\n"); @@ -281,11 +271,11 @@ puts("\n"); } - if ( residual ) + if ( bp ) { - puts("board data at: "); puthex((unsigned long)residual); + puts("board data at: "); puthex((unsigned long)bp); puts(" "); - puthex((unsigned long)((unsigned long)residual + sizeof(bd_t))); + puthex((unsigned long)((unsigned long)bp + sizeof(bd_t))); puts("\n"); puts("relocated to: "); puthex((unsigned long)hold_residual); @@ -299,11 +289,11 @@ zimage_start = (char *)(load_addr - 0x10000 + ZIMAGE_OFFSET); zimage_size = ZIMAGE_SIZE; - if ( INITRD_OFFSET ) - initrd_start = load_addr - 0x10000 + INITRD_OFFSET; + if ( initrd_offset ) + initrd_start = load_addr - 0x10000 + initrd_offset; else initrd_start = 0; - initrd_end = INITRD_SIZE + initrd_start; + initrd_end = initrd_size + initrd_start; /* * setup avail_ram - this is the first part of ram usable @@ -321,66 +311,49 @@ puts("zimage at: "); puthex((unsigned long)zimage_start); puts(" "); puthex((unsigned long)(zimage_size+zimage_start)); puts("\n"); /* - * don't relocate the zimage if it was loaded above 16M since - * things get weird if we try to relocate -- Cort - * We don't relocate zimage on a base MBX board because of - * insufficient memory. In this case we don't have initrd either, - * so use that as an indicator. -- Dan + * There is no reason (yet) to relocate zImage for embedded boards. + * To support boot from flash rom on 8xx embedded boards, I + * assume if zimage start is over 16M we are booting from flash. + * In this case, avilable ram will start just above the space we + * have allocated for the command buffer and board information. */ - - /* Determine if we have a Motorola board */ - needs_reloc = 0; - if ( (( (unsigned long)zimage_start <= 0x01000000 ) && initrd_start) - || needs_reloc) - { - memcpy ((void *)PAGE_ALIGN(-PAGE_SIZE+(unsigned long)end_avail-zimage_size), - (void *)zimage_start, zimage_size ); - zimage_start = (char *)PAGE_ALIGN(-PAGE_SIZE+(unsigned long)end_avail-zimage_size); - end_avail = (char *)zimage_start; - puts("relocated to: "); puthex((unsigned long)zimage_start); - puts(" "); - puthex((unsigned long)zimage_size+(unsigned long)zimage_start); - puts("\n"); - } + if ((unsigned long)zimage_start > 0x01000000) + avail_ram = (char *)PAGE_ALIGN((unsigned long)hold_residual + sizeof(bd_t)); /* relocate initrd */ if ( initrd_start ) { puts("initrd at: "); puthex(initrd_start); puts(" "); puthex(initrd_end); puts("\n"); - /* - * Memory is really tight on the MBX (we can assume 4M) - * so put the initrd at the TOP of ram, and set end_avail - * to right after that. - * - * I should do something like this for prep, too and keep - * a variable end_of_DRAM to keep track of what we think the - * max ram is. - * -- Cort + + /* We only have to relocate initrd if we find it is in Flash + * rom. This is because the kernel thinks it can toss the + * pages into the free memory pool after it is done. Use + * the same 16M test. */ - if (needs_reloc) - { - memcpy ((void *)PAGE_ALIGN(-PAGE_SIZE+ - (unsigned long)end_avail-INITRD_SIZE), + if ((unsigned long)initrd_start > 0x01000000) { + memcpy ((void *)PAGE_ALIGN(-PAGE_SIZE+(unsigned long)end_avail-INITRD_SIZE), (void *)initrd_start, - INITRD_SIZE ); - initrd_start = PAGE_ALIGN(-PAGE_SIZE+ - (unsigned long)end_avail-INITRD_SIZE); - initrd_end = initrd_start + INITRD_SIZE; + initrd_size ); + initrd_start = PAGE_ALIGN(-PAGE_SIZE+(unsigned long)end_avail-INITRD_SIZE); + initrd_end = initrd_start + initrd_size; end_avail = (char *)initrd_start; puts("relocated to: "); puthex(initrd_start); puts(" "); puthex(initrd_end); puts("\n"); } + else { + avail_ram = (char *)PAGE_ALIGN((unsigned long)initrd_end); + } } + puts("avail ram: "); puthex((unsigned long)avail_ram); puts(" "); puthex((unsigned long)end_avail); puts("\n"); puts("\nLinux/PPC load: "); timer = 0; cp = cmd_line; - memcpy (cmd_line, cmd_preset, sizeof(cmd_preset)); - while ( *cp ) putc(*cp++); + while (timer++ < 5*1000) { if (tstc()) { while ((ch = getc()) != '\n' && ch != '\r') { @@ -389,11 +362,6 @@ cp--; puts("\b \b"); } - } else if (ch == '?') { - if (!do_ipaddrs(&cp, 1)) { - *cp++ = ch; - putc(ch); - } } else { *cp++ = ch; putc(ch); @@ -404,188 +372,33 @@ udelay(1000); /* 1 msec */ } *cp = 0; - /* The MBX does not currently have any default boot strategy. - * If the command line is not filled in, we will automatically - * create the default network boot. + + /* If the command line is not filled in, we will automatically + * create the default boot. */ if (cmd_line[0] == 0) { - dp = root_string; - while (*dp != 0) - *cp++ = *dp++; - *cp++ = ' '; - dp = nfsaddrs_string; + /* An initrd on these boards means we booted from Flash + * ROM and want to use the ramdisk as the root file system. + * Otherwise, we perform a diskless NFS boot. + */ + if (initrd_start) + dp = ramroot_string; + else + dp = root_string; while (*dp != 0) *cp++ = *dp++; - dp = cp; - do_ipaddrs(&cp, 0); - *cp++ = ' '; - - /* Add the server address to the root file system path. - */ - dp = strrchr(dp, ':'); - dp++; - do_nfsroot(&cp, dp); *cp = 0; } + puts("\n"); - /* mappings on early boot can only handle 16M */ - if ( (int)(cmd_line[0]) > (16<<20)) - puts("cmd_line located > 16M\n"); - if ( (int)hold_residual > (16<<20)) - puts("hold_residual located > 16M\n"); - if ( initrd_start > (16<<20)) - puts("initrd_start located > 16M\n"); - puts("Uncompressing Linux..."); gunzip(0, 0x400000, zimage_start, &zimage_size); puts("done.\n"); puts("Now booting the kernel\n"); return (unsigned long)hold_residual; -} - -int -do_ipaddrs(char **cmd_cp, int echo) -{ - char *cp, *ip, ch; - unsigned char ipd; - int i, j, retval; - - /* We need to create the string: - * : - */ - cp = *cmd_cp; - retval = 0; - - if ((cp - 9) >= cmd_line) { - if (strncmp(cp - 9, "nfsaddrs=", 9) == 0) { - ip = (char *)0xfa000060; - retval = 1; - for (j=0; j<2; j++) { - for (i=0; i<4; i++) { - ipd = *ip++; - - ch = ipd/100; - if (ch) { - ch += '0'; - if (echo) - putc(ch); - *cp++ = ch; - ipd -= 100 * (ch - '0'); - } - - ch = ipd/10; - if (ch) { - ch += '0'; - if (echo) - putc(ch); - *cp++ = ch; - ipd -= 10 * (ch - '0'); - } - - ch = ipd + '0'; - if (echo) - putc(ch); - *cp++ = ch; - - ch = '.'; - if (echo) - putc(ch); - *cp++ = ch; - } - - /* At the end of the string, remove the - * '.' and replace it with a ':'. - */ - *(cp - 1) = ':'; - if (echo) { - putc('\b'); putc(':'); - } - } - - /* At the end of the second string, remove the - * '.' from both the command line and the - * screen. - */ - --cp; - putc('\b'); putc(' '); putc('\b'); - } - } - *cmd_cp = cp; - return(retval); -} - -void -do_nfsroot(char **cmd_cp, char *dp) -{ - char *cp, *rp, *ep; - - /* The boot argument (i.e /sys/mbxroot/zImage) is stored - * at offset 0x0078 in NVRAM. We use this path name to - * construct the root file system path. - */ - cp = *cmd_cp; - - /* build command string. - */ - rp = nfsroot_string; - while (*rp != 0) - *cp++ = *rp++; - - /* Add the server address to the path. - */ - while (*dp != ' ') - *cp++ = *dp++; - *cp++ = ':'; - - rp = (char *)0xfa000078; - ep = strrchr(rp, '/'); - - if (ep != 0) { - while (rp < ep) - *cp++ = *rp++; - } - else { - rp = defroot_string; - while (*rp != 0) - *cp++ = *rp++; - } - - *cmd_cp = cp; -} - -size_t strlen(const char * s) -{ - const char *sc; - - for (sc = s; *sc != '\0'; ++sc) - /* nothing */; - return sc - s; -} - -int strncmp(const char * cs,const char * ct,size_t count) -{ - register signed char __res = 0; - - while (count) { - if ((__res = *cs - *ct++) != 0 || !*cs++) - break; - count--; - } - - return __res; -} - -char * strrchr(const char * s, int c) -{ - const char *p = s + strlen(s); - do { - if (*p == (char)c) - return (char *)p; - } while (--p >= s); - return NULL; } void puthex(unsigned long val) diff -u --recursive --new-file v2.3.19/linux/arch/ppc/mbxboot/pci.c linux/arch/ppc/mbxboot/pci.c --- v2.3.19/linux/arch/ppc/mbxboot/pci.c Wed Dec 31 16:00:00 1969 +++ linux/arch/ppc/mbxboot/pci.c Thu Oct 7 10:17:09 1999 @@ -0,0 +1,251 @@ +/* Stand alone funtions for QSpan Tundra support. + */ +#include +#include +#include + +/* To map PCI devices, you first write 0xffffffff into the device + * base address registers. When the register is read back, the + * number of most significant '1' bits describes the amount of address + * space needed for mapping. If the most significant bit is not set, + * either the device does not use that address register, or it has + * a fixed address that we can't change. After the address is assigned, + * the command register has to be written to enable the card. + */ +typedef struct { + u_char pci_bus; + u_char pci_devfn; + ushort pci_command; + uint pci_addrs[6]; +} pci_map_t; + +/* We should probably dynamically allocate these structures. +*/ +#define MAX_PCI_DEVS 32 +int pci_dev_cnt; +pci_map_t pci_map[MAX_PCI_DEVS]; + +void pci_conf_write(int bus, int device, int func, int reg, uint writeval); +void pci_conf_read(int bus, int device, int func, int reg, void *readval); +void probe_addresses(int bus, int devfn); +void map_pci_addrs(void); + +/* This is a really stripped version of PCI bus scan. All we are + * looking for are devices that exist. + */ +pci_scanner(int addr_probe) +{ + unsigned int devfn, l, max, class, bus_number; + unsigned char cmd, irq, tmp, hdr_type, is_multi; + int reg; + + is_multi = 0; + bus_number = 0; + for (devfn = 0; devfn < 0xff; ++devfn) { + /* The device numbers are comprised of upper 5 bits of + * device number and lower 3 bits of multi-function number. + */ + if ((devfn & 7) && !is_multi) { + /* Don't scan multifunction addresses if this is + * not a multifunction device. + */ + continue; + } + + /* Read the header to determine card type. + */ + qs_pci_read_config_byte(bus_number, devfn, PCI_HEADER_TYPE, + &hdr_type); + + /* If this is a base device number, check the header to + * determine if it is mulifunction. + */ + if ((devfn & 7) == 0) + is_multi = hdr_type & 0x80; + + /* Check to see if the board is really in the slot. + */ + qs_pci_read_config_dword(bus_number, devfn, PCI_VENDOR_ID, &l); + /* some broken boards return 0 if a slot is empty: */ + if (l == 0xffffffff || l == 0x00000000 || l == 0x0000ffff || + l == 0xffff0000) { + /* Nothing there. + */ + is_multi = 0; + continue; + } + + /* If we are not performing an address probe, + * just simply print out some information. + */ + if (!addr_probe) { + qs_pci_read_config_dword(bus_number, devfn, + PCI_CLASS_REVISION, &class); + + class >>= 8; /* upper 3 bytes */ + +#if 0 + printf("Found (%3d:%d): vendor 0x%04x, device 0x%04x, class 0x%06x\n", + (devfn >> 3), (devfn & 7), + (l & 0xffff), (l >> 16) & 0xffff, class); +#else + puts("Found ("); puthex(devfn >> 3); + puts(":"); puthex(devfn & 7); + puts("): vendor "); puthex(l & 0xffff); + puts(", device "); puthex((l >> 16) & 0xffff); + puts(", class "); puthex(class); puts("\n"); +#endif + } + else { + /* If this is a "normal" device, build address list. + */ + if ((hdr_type & 0x7f) == PCI_HEADER_TYPE_NORMAL) + probe_addresses(bus_number, devfn); + } + } + + /* Now map the boards. + */ + if (addr_probe) + map_pci_addrs(); +} + +/* Probe addresses for the specified device. This is a destructive + * operation because it writes the registers. + */ +void +probe_addresses(bus, devfn) +{ + int i; + uint pciaddr; + ushort pcicmd; + pci_map_t *pm; + + if (pci_dev_cnt >= MAX_PCI_DEVS) { + puts("Too many PCI devices\n"); + return; + } + + pm = &pci_map[pci_dev_cnt++]; + + pm->pci_bus = bus; + pm->pci_devfn = devfn; + + for (i=0; i<6; i++) { + qs_pci_write_config_dword(bus, devfn, PCI_BASE_ADDRESS_0 + (i * 4), -1); + qs_pci_read_config_dword(bus, devfn, PCI_BASE_ADDRESS_0 + (i * 4), + &pciaddr); + pm->pci_addrs[i] = pciaddr; + qs_pci_read_config_word(bus, devfn, PCI_COMMAND, &pcicmd); + pm->pci_command = pcicmd; + } +} + +/* Map the cards into the PCI space. The PCI has separate memory + * and I/O spaces. In addition, some memory devices require mapping + * below 1M. The least significant 4 bits of the address register + * provide information. If this is an I/O device, only the LS bit + * is used to indicate that, so I/O devices can be mapped to a two byte + * boundard. Memory addresses can be mapped to a 32 byte boundary. + * The QSpan implementations usually have a 1Gbyte space for each + * memory and I/O spaces. + * + * This isn't a terribly fancy algorithm. I just map the spaces from + * the top starting with the largest address space. When finished, + * the registers are written and the card enabled. + * + * While the Tundra can map a large address space on most boards, we + * need to be careful because it may overlap other devices (like IMMR). + */ +#define MEMORY_SPACE_SIZE 0x20000000 +#define IO_SPACE_SIZE 0x20000000 + +void +map_pci_addrs() +{ + uint pci_mem_top, pci_mem_low; + uint pci_io_top; + uint addr_mask, reg_addr, space; + int i, j; + pci_map_t *pm; + + pci_mem_top = MEMORY_SPACE_SIZE; + pci_io_top = IO_SPACE_SIZE; + pci_mem_low = (1 * 1024 * 1024); /* Below one meg addresses */ + + /* We can't map anything more than the maximum space, but test + * for it anyway to catch devices out of range. + */ + addr_mask = 0x80000000; + + do { + space = (~addr_mask) + 1; /* Size of the space */ + for (i=0; ipci_addrs[j]; + if ((reg_addr & 0x80000000) == 0) + continue; + if (reg_addr & PCI_BASE_ADDRESS_SPACE_IO) { + if ((reg_addr & PCI_BASE_ADDRESS_IO_MASK) != addr_mask) + continue; + if (pci_io_top < space) { + puts("Out of PCI I/O space\n"); + } + else { + pci_io_top -= space; + pm->pci_addrs[j] = pci_io_top; + pm->pci_command |= PCI_COMMAND_IO; + } + } + else { + if ((reg_addr & PCI_BASE_ADDRESS_MEM_MASK) != addr_mask) + continue; + + /* Memory space. Test if below 1M. + */ + if (reg_addr & PCI_BASE_ADDRESS_MEM_TYPE_1M) { + if (pci_mem_low < space) { + puts("Out of PCI 1M space\n"); + } + else { + pci_mem_low -= space; + pm->pci_addrs[j] = pci_mem_low; + } + } + else { + if (pci_mem_top < space) { + puts("Out of PCI Mem space\n"); + } + else { + pci_mem_top -= space; + pm->pci_addrs[j] = pci_mem_top; + } + } + pm->pci_command |= PCI_COMMAND_MEMORY; + } + } + } + addr_mask >>= 1; + addr_mask |= 0x80000000; + } while (addr_mask != 0xfffffffe); + + /* Now, run the list one more time and map everything. + */ + for (i=0; ipci_bus, pm->pci_devfn, + PCI_BASE_ADDRESS_0 + (j * 4), pm->pci_addrs[j]); + } + + /* Enable memory or address mapping. + */ + qs_pci_write_config_word(pm->pci_bus, pm->pci_devfn, PCI_COMMAND, + pm->pci_command); + } +} + diff -u --recursive --new-file v2.3.19/linux/arch/ppc/mbxboot/qspan_pci.c linux/arch/ppc/mbxboot/qspan_pci.c --- v2.3.19/linux/arch/ppc/mbxboot/qspan_pci.c Wed Dec 31 16:00:00 1969 +++ linux/arch/ppc/mbxboot/qspan_pci.c Thu Oct 7 10:17:09 1999 @@ -0,0 +1,267 @@ +/* + * LinuxPPC arch/ppc/kernel/qspan_pci.c Dan Malek (dmalek@jlc.net) + * + * QSpan Motorola bus to PCI bridge. The config address register + * is located 0x500 from the base of the bridge control/status registers. + * The data register is located at 0x504. + * This is a two step operation. First, the address register is written, + * then the data register is read/written as required. + * I don't know what to do about interrupts (yet). + */ + +#include +#include +#include + +/* + * When reading the configuration space, if something does not respond + * the bus times out and we get a machine check interrupt. So, the + * good ol' exception tables come to mind to trap it and return some + * value. + * + * On an error we just return a -1, since that is what the caller wants + * returned if nothing is present. I copied this from __get_user_asm, + * with the only difference of returning -1 instead of EFAULT. + * There is an associated hack in the machine check trap code. + * + * The QSPAN is also a big endian device, that is it makes the PCI + * look big endian to us. This presents a problem for the Linux PCI + * functions, which assume little endian. For example, we see the + * first 32-bit word like this: + * ------------------------ + * | Device ID | Vendor ID | + * ------------------------ + * If we read/write as a double word, that's OK. But in our world, + * when read as a word, device ID is at location 0, not location 2 as + * the little endian PCI would believe. We have to switch bits in + * the PCI addresses given to us to get the data to/from the correct + * byte lanes. + * + * The QSPAN only supports 4 bits of "slot" in the dev_fn instead of 5. + * It always forces the MS bit to zero. Therefore, dev_fn values + * greater than 128 are returned as "no device found" errors. + * + * The QSPAN can only perform long word (32-bit) configuration cycles. + * The "offset" must have the two LS bits set to zero. Read operations + * require we read the entire word and then sort out what should be + * returned. Write operations other than long word require that we + * read the long word, update the proper word or byte, then write the + * entire long word back. + * + * PCI Bridge hack. We assume (correctly) that bus 0 is the primary + * PCI bus from the QSPAN. If we are called with a bus number other + * than zero, we create a Type 1 configuration access that a downstream + * PCI bridge will interpret. + */ + +#define __get_pci_config(x, addr, op) \ + __asm__ __volatile__( \ + "1: "op" %0,0(%1)\n" \ + " eieio\n" \ + "2:\n" \ + ".section .fixup,\"ax\"\n" \ + "3: li %0,-1\n" \ + " b 2b\n" \ + ".section __ex_table,\"a\"\n" \ + " .align 2\n" \ + " .long 1b,3b\n" \ + ".text" \ + : "=r"(x) : "r"(addr)) + +#define QS_CONFIG_ADDR ((volatile uint *)(PCI_CSR_ADDR + 0x500)) +#define QS_CONFIG_DATA ((volatile uint *)(PCI_CSR_ADDR + 0x504)) + +#define mk_config_addr(bus, dev, offset) \ + (((bus)<<16) | ((dev)<<8) | (offset & 0xfc)) + +#define mk_config_type1(bus, dev, offset) \ + mk_config_addr(bus, dev, offset) | 1; + +/* Initialize the QSpan device registers after power up. +*/ +qspan_init() +{ + uint *qptr; + + + + qptr = (uint *)PCI_CSR_ADDR; + + /* PCI Configuration/status. Upper bits written to clear + * pending interrupt or status. Lower bits enable QSPAN as + * PCI master, enable memory and I/O cycles, and enable PCI + * parity error checking. + * IMPORTANT: The last two bits of this word enable PCI + * master cycles into the QBus. The QSpan is broken and can't + * meet the timing specs of the PQ bus for this to work. Therefore, + * if you don't have external bus arbitration, you can't use + * this function. + */ +#ifdef EXTERNAL_PQ_ARB + qptr[1] = 0xf9000147; +#else + qptr[1] = 0xf9000144; +#endif + + /* PCI Misc configuration. Set PCI latency timer resolution + * of 8 cycles, set cache size to 4 x 32. + */ + qptr[3] = 0; + + /* Set up PCI Target address mapping. Enable, Posted writes, + * 2Gbyte space (processor memory controller determines actual size). + */ + qptr[64] = 0x8f000080; + + /* Map processor 0x80000000 to PCI 0x00000000. + * Processor address bit 1 determines I/O type access (0x80000000) + * or memory type access (0xc0000000). + */ + qptr[65] = 0x80000000; + + /* Enable error logging and clear any pending error status. + */ + qptr[80] = 0x90000000; + + qptr[512] = 0x000c0003; + + /* Set up Qbus slave image. + */ + qptr[960] = 0x01000000; + qptr[961] = 0x000000d1; + qptr[964] = 0x00000000; + qptr[965] = 0x000000d1; + +} + +/* Functions to support PCI bios-like features to read/write configuration + * space. If the function fails for any reason, a -1 (0xffffffff) value + * must be returned. + */ +#define DEVICE_NOT_FOUND (-1) +#define SUCCESSFUL 0 + +int qs_pci_read_config_byte(unsigned char bus, unsigned char dev_fn, + unsigned char offset, unsigned char *val) +{ + uint temp; + u_char *cp; + + if ((bus > 7) || (dev_fn > 127)) { + *val = 0xff; + return DEVICE_NOT_FOUND; + } + + if (bus == 0) + *QS_CONFIG_ADDR = mk_config_addr(bus, dev_fn, offset); + else + *QS_CONFIG_ADDR = mk_config_type1(bus, dev_fn, offset); + __get_pci_config(temp, QS_CONFIG_DATA, "lwz"); + + offset ^= 0x03; + cp = ((u_char *)&temp) + (offset & 0x03); + *val = *cp; + return SUCCESSFUL; +} + +int qs_pci_read_config_word(unsigned char bus, unsigned char dev_fn, + unsigned char offset, unsigned short *val) +{ + uint temp; + ushort *sp; + + if ((bus > 7) || (dev_fn > 127)) { + *val = 0xffff; + return DEVICE_NOT_FOUND; + } + + if (bus == 0) + *QS_CONFIG_ADDR = mk_config_addr(bus, dev_fn, offset); + else + *QS_CONFIG_ADDR = mk_config_type1(bus, dev_fn, offset); + __get_pci_config(temp, QS_CONFIG_DATA, "lwz"); + offset ^= 0x02; + + sp = ((ushort *)&temp) + ((offset >> 1) & 1); + *val = *sp; + return SUCCESSFUL; +} + +int qs_pci_read_config_dword(unsigned char bus, unsigned char dev_fn, + unsigned char offset, unsigned int *val) +{ + if ((bus > 7) || (dev_fn > 127)) { + *val = 0xffffffff; + return DEVICE_NOT_FOUND; + } + if (bus == 0) + *QS_CONFIG_ADDR = mk_config_addr(bus, dev_fn, offset); + else + *QS_CONFIG_ADDR = mk_config_type1(bus, dev_fn, offset); + __get_pci_config(*val, QS_CONFIG_DATA, "lwz"); + return SUCCESSFUL; +} + +int qs_pci_write_config_byte(unsigned char bus, unsigned char dev_fn, + unsigned char offset, unsigned char val) +{ + uint temp; + u_char *cp; + + if ((bus > 7) || (dev_fn > 127)) + return DEVICE_NOT_FOUND; + + qs_pci_read_config_dword(bus, dev_fn, offset, &temp); + + offset ^= 0x03; + cp = ((u_char *)&temp) + (offset & 0x03); + *cp = val; + + if (bus == 0) + *QS_CONFIG_ADDR = mk_config_addr(bus, dev_fn, offset); + else + *QS_CONFIG_ADDR = mk_config_type1(bus, dev_fn, offset); + *QS_CONFIG_DATA = temp; + + return SUCCESSFUL; +} + +int qs_pci_write_config_word(unsigned char bus, unsigned char dev_fn, + unsigned char offset, unsigned short val) +{ + uint temp; + ushort *sp; + + if ((bus > 7) || (dev_fn > 127)) + return DEVICE_NOT_FOUND; + + qs_pci_read_config_dword(bus, dev_fn, offset, &temp); + + offset ^= 0x02; + sp = ((ushort *)&temp) + ((offset >> 1) & 1); + *sp = val; + + if (bus == 0) + *QS_CONFIG_ADDR = mk_config_addr(bus, dev_fn, offset); + else + *QS_CONFIG_ADDR = mk_config_type1(bus, dev_fn, offset); + *QS_CONFIG_DATA = temp; + + return SUCCESSFUL; +} + +int qs_pci_write_config_dword(unsigned char bus, unsigned char dev_fn, + unsigned char offset, unsigned int val) +{ + if ((bus > 7) || (dev_fn > 127)) + return DEVICE_NOT_FOUND; + + if (bus == 0) + *QS_CONFIG_ADDR = mk_config_addr(bus, dev_fn, offset); + else + *QS_CONFIG_ADDR = mk_config_type1(bus, dev_fn, offset); + *(unsigned int *)QS_CONFIG_DATA = val; + + return SUCCESSFUL; +} + diff -u --recursive --new-file v2.3.19/linux/arch/ppc/mm/fault.c linux/arch/ppc/mm/fault.c --- v2.3.19/linux/arch/ppc/mm/fault.c Tue Aug 31 17:29:13 1999 +++ linux/arch/ppc/mm/fault.c Thu Oct 7 10:17:09 1999 @@ -181,38 +181,6 @@ } #ifdef CONFIG_8xx -/* - * I need a va to pte function for the MPC8xx so I can set the cache - * attributes on individual pages used by the Communication Processor - * Module. - */ -pte_t *va_to_pte(struct task_struct *tsk, unsigned long address) -{ - pgd_t *dir; - pmd_t *pmd; - pte_t *pte; - - dir = pgd_offset(tsk->mm, address & PAGE_MASK); - if (dir) - { - pmd = pmd_offset(dir, address & PAGE_MASK); - if (pmd && pmd_present(*pmd)) - { - pte = pte_offset(pmd, address & PAGE_MASK); - if (pte && pte_present(*pte)) - { - return(pte); - } - } else - { - return (0); - } - } else - { - return (0); - } - return (0); -} unsigned long va_to_phys(unsigned long address) { diff -u --recursive --new-file v2.3.19/linux/arch/ppc/mm/init.c linux/arch/ppc/mm/init.c --- v2.3.19/linux/arch/ppc/mm/init.c Fri Sep 10 23:57:28 1999 +++ linux/arch/ppc/mm/init.c Thu Oct 7 10:17:09 1999 @@ -1,5 +1,5 @@ /* - * $Id: init.c,v 1.183 1999/09/05 19:29:44 cort Exp $ + * $Id: init.c,v 1.188 1999/09/18 18:40:44 dmalek Exp $ * * PowerPC version * Copyright (C) 1995-1996 Gary Thomas (gdt@linuxppc.org) @@ -47,7 +47,7 @@ #include #include #include -#include +#include #include #include #include @@ -73,7 +73,7 @@ unsigned long ioremap_bot; unsigned long avail_start; extern int num_memory; -extern struct mem_info memory[NUM_MEMINFO]; +extern struct mem_info memory[]; extern boot_infos_t *boot_infos; #ifndef __SMP__ struct pgtable_cache_struct quicklists; @@ -86,9 +86,9 @@ unsigned long *apus_find_end_of_memory(void); unsigned long *gemini_find_end_of_memory(void); extern unsigned long *find_end_of_memory(void); -#ifdef CONFIG_MBX -unsigned long *mbx_find_end_of_memory(void); -#endif /* CONFIG_MBX */ +#ifdef CONFIG_8xx +unsigned long *m8xx_find_end_of_memory(void); +#endif /* CONFIG_8xx */ static void mapin_ram(void); void map_page(unsigned long va, unsigned long pa, int flags); extern void die_if_kernel(char *,struct pt_regs *,long); @@ -997,9 +997,6 @@ */ void __init MMU_init(void) { -#ifdef __SMP__ - if ( first_cpu_booted ) return; -#endif /* __SMP__ */ if ( ppc_md.progress ) ppc_md.progress("MMU:enter", 0x111); #ifndef CONFIG_8xx if (have_of) @@ -1054,9 +1051,6 @@ setbat(0, 0xfff00000, 0xfff00000, 0x00020000, RAM_PAGE); /* Map chip and ZorroII memory */ setbat(1, zTwoBase, 0x00000000, 0x01000000, IO_PAGE); - /* Note: a temporary hack in arch/ppc/amiga/setup.c - (kernel_map) remaps individual IO regions to - 0x90000000. */ break; case _MACH_gemini: setbat(0, 0xf0000000, 0xf0000000, 0x10000000, IO_PAGE); @@ -1065,9 +1059,9 @@ } ioremap_bot = ioremap_base; #else /* CONFIG_8xx */ -#ifdef CONFIG_MBX - end_of_DRAM = mbx_find_end_of_memory(); -#endif /* CONFIG_MBX */ + + end_of_DRAM = m8xx_find_end_of_memory(); + /* Map in all of RAM starting at KERNELBASE */ mapin_ram(); @@ -1076,13 +1070,25 @@ * All of this fits into the same 4Mbyte region, so it only * requires one page table page. */ + ioremap(IMAP_ADDR, IMAP_SIZE); +#ifdef CONFIG_MBX ioremap(NVRAM_ADDR, NVRAM_SIZE); ioremap(MBX_CSR_ADDR, MBX_CSR_SIZE); - ioremap(IMAP_ADDR, IMAP_SIZE); ioremap(PCI_CSR_ADDR, PCI_CSR_SIZE); - /* ide needs to be able to get at PCI space -- Cort */ - ioremap(0x80000000, 0x4000); - ioremap(0x81000000, 0x4000); + + /* Map some of the PCI/ISA I/O space to get the IDE interface. + */ + ioremap(PCI_ISA_IO_ADDR, 0x4000); + ioremap(PCI_IDE_ADDR, 0x4000); +#endif +#ifdef CONFIG_RPXLITE + ioremap(RPX_CSR_ADDR, RPX_CSR_SIZE); + ioremap(HIOX_CSR_ADDR, HIOX_CSR_SIZE); +#endif +#ifdef CONFIG_RPXCLASSIC + ioremap(PCI_CSR_ADDR, PCI_CSR_SIZE); + ioremap(RPX_CSR_ADDR, RPX_CSR_SIZE); +#endif #endif /* CONFIG_8xx */ if ( ppc_md.progress ) ppc_md.progress("MMU:exit", 0x211); } @@ -1231,55 +1237,8 @@ mem_init_done = 1; } -#ifdef CONFIG_MBX -/* - * This is a big hack right now, but it may turn into something real - * someday. - * - * For the MBX860 (at this time anyway), there is nothing to initialize - * associated the PROM. Rather than include all of the prom.c - * functions in the image just to get prom_init, all we really need right - * now is the initialization of the physical memory region. - */ -unsigned long __init *mbx_find_end_of_memory(void) -{ - unsigned long kstart, ksize; - bd_t *binfo; - volatile memctl8xx_t *mcp; - unsigned long *ret; - - binfo = (bd_t *)res; - - /* - * The MBX does weird things with the mmaps for ram. - * If there's no DIMM, it puts the onboard DRAM at - * 0, if there is a DIMM it sticks it at 0 and puts - * the DRAM at the end of the DIMM. - * - * In fact, it might be the best idea to just read the DRAM - * config registers and set the mem areas accordingly. - */ - mcp = (memctl8xx_t *)(&(((immap_t *)IMAP_ADDR)->im_memctl)); - append_mem_piece(&phys_mem, 0, binfo->bi_memsize); -#if 0 - phys_mem.regions[0].address = 0; - phys_mem.regions[0].size = binfo->bi_memsize; - phys_mem.n_regions = 1; -#endif - - ret = __va(phys_mem.regions[0].address+ - phys_mem.regions[0].size); - - phys_avail = phys_mem; - - kstart = __pa(_stext); /* should be 0 */ - ksize = PAGE_ALIGN(_end - _stext); - remove_mem_piece(&phys_avail, kstart, ksize, 0); - return ret; -} -#endif /* CONFIG_MBX */ - #ifndef CONFIG_8xx +#if defined(CONFIG_PMAC) || defined(CONFIG_PPC_ALL) /* * On systems with Open Firmware, collect information about * physical RAM and which pieces are already in use. @@ -1372,7 +1331,9 @@ #undef RAM_LIMIT return __va(total); } +#endif /* defined(CONFIG_PMAC) || defined(CONFIG_PPC_ALL) */ +#if defined(CONFIG_PREP) || defined(CONFIG_PPC_ALL) /* * This finds the amount of physical ram and does necessary * setup for prep. This is pretty architecture specific so @@ -1404,7 +1365,10 @@ return (__va(total)); } +#endif /* defined(CONFIG_PREP) || defined(CONFIG_PPC_ALL) */ + +#if defined(CONFIG_GEMINI) || defined(CONFIG_PPC_ALL) unsigned long __init *gemini_find_end_of_memory(void) { unsigned long total, kstart, ksize, *ret; @@ -1425,6 +1389,7 @@ remove_mem_piece( &phys_avail, kstart, ksize, 0 ); return ret; } +#endif /* defined(CONFIG_GEMINI) || defined(CONFIG_PPC_ALL) */ #ifdef CONFIG_APUS #define HARDWARE_MAPPED_SIZE (512*1024) @@ -1601,5 +1566,38 @@ (unsigned long) &hash_page[1]); } if ( ppc_md.progress ) ppc_md.progress("hash:done", 0x205); +} +#else /* CONFIG_8xx */ +/* + * This is a big hack right now, but it may turn into something real + * someday. + * + * For the 8xx boards (at this time anyway), there is nothing to initialize + * associated the PROM. Rather than include all of the prom.c + * functions in the image just to get prom_init, all we really need right + * now is the initialization of the physical memory region. + */ +unsigned long __init *m8xx_find_end_of_memory(void) +{ + unsigned long kstart, ksize; + bd_t *binfo; + unsigned long *ret; + extern unsigned char __res[]; + + binfo = (bd_t *)__res; + + phys_mem.regions[0].address = 0; + phys_mem.regions[0].size = binfo->bi_memsize; + phys_mem.n_regions = 1; + + ret = __va(phys_mem.regions[0].address+ + phys_mem.regions[0].size); + + phys_avail = phys_mem; + + kstart = __pa(_stext); /* should be 0 */ + ksize = PAGE_ALIGN(_end - _stext); + remove_mem_piece(&phys_avail, kstart, ksize, 0); + return ret; } #endif /* ndef CONFIG_8xx */ diff -u --recursive --new-file v2.3.19/linux/arch/ppc/vmlinux.lds linux/arch/ppc/vmlinux.lds --- v2.3.19/linux/arch/ppc/vmlinux.lds Tue Aug 31 17:29:13 1999 +++ linux/arch/ppc/vmlinux.lds Thu Oct 7 10:17:09 1999 @@ -88,6 +88,7 @@ __initcall_end = .; . = ALIGN(4096); __init_end = .; + . = ALIGN(4096); __pmac_begin = .; .text.pmac : { *(.text.pmac) } @@ -101,6 +102,13 @@ .data.prep : { *(.data.prep) } . = ALIGN(4096); __prep_end = .; + + . = ALIGN(4096); + __apus_begin = .; + .text.apus : { *(.text.apus) } + .data.apus : { *(.data.apus) } + . = ALIGN(4096); + __apus_end = .; . = ALIGN(4096); __apus_begin = .; diff -u --recursive --new-file v2.3.19/linux/arch/ppc/xmon/start.c linux/arch/ppc/xmon/start.c --- v2.3.19/linux/arch/ppc/xmon/start.c Tue Aug 31 17:29:13 1999 +++ linux/arch/ppc/xmon/start.c Thu Oct 7 10:17:09 1999 @@ -1,19 +1,26 @@ /* * Copyright (C) 1996 Paul Mackerras. */ +#include #include #include #include #include #include -#include +#include +#include #include +#include static volatile unsigned char *sccc, *sccd; unsigned long TXRDY, RXRDY; extern void xmon_printf(const char *fmt, ...); +extern void map_bootx_text(void); +extern void drawchar(char); +extern void drawstring(const char *str); -static int console = 1; +static int console = 0; +static int use_screen = 0; void buf_access(void) { @@ -29,10 +36,21 @@ if ( _machine == _MACH_Pmac ) { struct device_node *np; + extern boot_infos_t *boot_infos; + unsigned long addr; + +#ifdef CONFIG_BOOTX_TEXT + if (boot_infos != 0 && find_via_pmu()) { + printk(KERN_INFO "xmon uses screen and keyboard\n"); + use_screen = 1; + map_bootx_text(); + return; + } +#endif #ifdef CHRP_ESCC - unsigned long addr = 0xc1013020; + addr = 0xc1013020; #else - unsigned long addr = 0xf3013020; + addr = 0xf3013020; #endif TXRDY = 4; RXRDY = 1; @@ -73,11 +91,19 @@ char *p = ptr; int i, ct; +#ifdef CONFIG_BOOTX_TEXT + if (use_screen) { + /* write it on the screen */ + for (i = 0; i < nb; ++i) + drawchar(*p++); + return nb; + } +#endif if (!scc_initialized) xmon_init_scc(); for (i = 0; i < nb; ++i) { while ((*sccc & TXRDY) == 0) - if (adb_hardware == ADB_VIAPMU) + if (sys_ctrler == SYS_CTRLER_PMU) pmu_poll(); buf_access(); if ( console && (*p != '\r')) @@ -92,17 +118,85 @@ return i; } +int xmon_wants_key; +int xmon_pmu_keycode; + +#ifdef CONFIG_BOOTX_TEXT +static int xmon_pmu_shiftstate; + +static unsigned char xmon_keytab[128] = + "asdfhgzxcv\000bqwer" /* 0x00 - 0x0f */ + "yt123465=97-80o]" /* 0x10 - 0x1f */ + "u[ip\rlj'k;\\,/nm." /* 0x20 - 0x2f */ + "\t `\177\0\033\0\0\0\0\0\0\0\0\0\0" /* 0x30 - 0x3f */ + "\0.\0*\0+\0\0\0\0\0/\r\0-\0" /* 0x40 - 0x4f */ + "\0\0000123456789\0\0\0"; /* 0x50 - 0x5f */ + +static unsigned char xmon_shift_keytab[128] = + "ASDFHGZXCV\000BQWER" /* 0x00 - 0x0f */ + "YT!@#$^%+(&=*)}O" /* 0x10 - 0x1f */ + "U{IP\rLJ\"K:|" /* 0x20 - 0x2f */ + "\t ~\177\0\033\0\0\0\0\0\0\0\0\0\0" /* 0x30 - 0x3f */ + "\0.\0*\0+\0\0\0\0\0/\r\0-\0" /* 0x40 - 0x4f */ + "\0\0000123456789\0\0\0"; /* 0x50 - 0x5f */ + +static int +xmon_get_pmu_key(void) +{ + int k, t, on; + + xmon_wants_key = 1; + for (;;) { + xmon_pmu_keycode = -1; + t = 0; + on = 0; + do { + if (--t < 0) { + on = 1 - on; + drawchar(on? 0xdb: 0x20); + drawchar('\b'); + t = 200000; + } + pmu_poll(); + } while (xmon_pmu_keycode == -1); + k = xmon_pmu_keycode; + if (on) + drawstring(" \b"); + + /* test for shift keys */ + if ((k & 0x7f) == 0x38 || (k & 0x7f) == 0x7b) { + xmon_pmu_shiftstate = (k & 0x80) == 0; + continue; + } + if (k >= 0x80) + continue; /* ignore up transitions */ + k = (xmon_pmu_shiftstate? xmon_shift_keytab: xmon_keytab)[k]; + if (k != 0) + break; + } + xmon_wants_key = 0; + return k; +} +#endif /* CONFIG_BOOTX_TEXT */ + int xmon_read(void *handle, void *ptr, int nb) { char *p = ptr; int i; +#ifdef CONFIG_BOOTX_TEXT + if (use_screen) { + for (i = 0; i < nb; ++i) + *p++ = xmon_get_pmu_key(); + return i; + } +#endif if (!scc_initialized) xmon_init_scc(); for (i = 0; i < nb; ++i) { while ((*sccc & RXRDY) == 0) - if (adb_hardware == ADB_VIAPMU) + if (sys_ctrler == SYS_CTRLER_PMU) pmu_poll(); buf_access(); #if 0 diff -u --recursive --new-file v2.3.19/linux/arch/sparc64/config.in linux/arch/sparc64/config.in --- v2.3.19/linux/arch/sparc64/config.in Fri Sep 10 23:57:28 1999 +++ linux/arch/sparc64/config.in Thu Oct 7 12:50:23 1999 @@ -146,14 +146,10 @@ if [ "$CONFIG_PCI" != "n" ]; then dep_tristate 'Adaptec AIC7xxx support' CONFIG_SCSI_AIC7XXX $CONFIG_SCSI if [ "$CONFIG_SCSI_AIC7XXX" != "n" ]; then - bool ' Enable tagged command queueing' CONFIG_AIC7XXX_TAGGED_QUEUEING Y - bool ' Override driver defaults for commands per LUN' CONFIG_OVERRIDE_CMDS N - if [ "$CONFIG_OVERRIDE_CMDS" != "n" ]; then - int ' Maximum number of commands per LUN' CONFIG_AIC7XXX_CMDS_PER_LUN 8 - fi - bool ' Enable SCB paging' CONFIG_AIC7XXX_PAGE_ENABLE N + bool ' Enable Tagged Command Queueing (TCQ) by default' CONFIG_AIC7XXX_TCQ_ON_BY_DEFAULT + int ' Maximum number of TCQ commands per device' CONFIG_AIC7XXX_CMDS_PER_DEVICE 8 bool ' Collect statistics to report in /proc' CONFIG_AIC7XXX_PROC_STATS N - int ' Delay in seconds after SCSI bus reset' CONFIG_AIC7XXX_RESET_DELAY 15 + int ' Delay in seconds after SCSI bus reset' CONFIG_AIC7XXX_RESET_DELAY 5 fi dep_tristate 'NCR53C8XX SCSI support' CONFIG_SCSI_NCR53C8XX $CONFIG_SCSI if [ "$CONFIG_SCSI_NCR53C8XX" != "n" ]; then diff -u --recursive --new-file v2.3.19/linux/arch/sparc64/defconfig linux/arch/sparc64/defconfig --- v2.3.19/linux/arch/sparc64/defconfig Fri Sep 10 23:57:28 1999 +++ linux/arch/sparc64/defconfig Thu Oct 7 12:50:23 1999 @@ -207,10 +207,9 @@ CONFIG_SCSI_SUNESP=y CONFIG_SCSI_QLOGICPTI=m CONFIG_SCSI_AIC7XXX=y -# CONFIG_AIC7XXX_TAGGED_QUEUEING is not set -# CONFIG_OVERRIDE_CMDS is not set -# CONFIG_AIC7XXX_PAGE_ENABLE is not set -# CONFIG_AIC7XXX_PROC_STATS is not set +# CONFIG_AIC7XXX_TCQ_ON_BY_DEFAULT is not set +# CONFIG_CMDS_PER_DEVICE is not set +CONFIG_AIC7XXX_PROC_STATS=y CONFIG_AIC7XXX_RESET_DELAY=5 CONFIG_SCSI_NCR53C8XX=y CONFIG_SCSI_NCR53C8XX_DEFAULT_TAGS=4 diff -u --recursive --new-file v2.3.19/linux/arch/sparc64/kernel/pci.c linux/arch/sparc64/kernel/pci.c --- v2.3.19/linux/arch/sparc64/kernel/pci.c Fri Sep 10 23:57:28 1999 +++ linux/arch/sparc64/kernel/pci.c Thu Oct 7 12:23:21 1999 @@ -202,11 +202,6 @@ { } -int pcibios_assign_resource(struct pci_dev *pdev, int resource) -{ - return 0; -} - char * __init pcibios_setup(char *str) { if (!strcmp(str, "onboardfirst")) { diff -u --recursive --new-file v2.3.19/linux/drivers/Makefile linux/drivers/Makefile --- v2.3.19/linux/drivers/Makefile Tue Sep 7 12:14:06 1999 +++ linux/drivers/Makefile Thu Oct 7 14:53:43 1999 @@ -11,7 +11,7 @@ MOD_SUB_DIRS := $(SUB_DIRS) ALL_SUB_DIRS := $(SUB_DIRS) pci sgi scsi sbus cdrom isdn pnp i2o \ macintosh video dio zorro fc4 usb \ - nubus tc ap1000 atm + nubus tc ap1000 atm pcmcia ifdef CONFIG_DIO SUB_DIRS += dio @@ -22,8 +22,12 @@ SUB_DIRS += pci endif -ifdef CONFIG_PCMCIA +ifeq ($(CONFIG_PCMCIA),y) SUB_DIRS += pcmcia +else + ifeq ($(CONFIG_PCMCIA),m) + MOD_SUB_DIRS += pcmcia + endif endif ifdef CONFIG_SBUS @@ -117,7 +121,6 @@ ifeq ($(CONFIG_AP1000),y) SUB_DIRS += ap1000 -ALL_SUB_DIRS += ap1000 endif ifeq ($(CONFIG_FC4),y) diff -u --recursive --new-file v2.3.19/linux/drivers/atm/Config.in linux/drivers/atm/Config.in --- v2.3.19/linux/drivers/atm/Config.in Fri Sep 10 23:57:28 1999 +++ linux/drivers/atm/Config.in Thu Oct 7 10:17:09 1999 @@ -4,44 +4,44 @@ mainmenu_option next_comment comment 'ATM drivers' if [ "$CONFIG_INET" = "y" ]; then - tristate 'ATM over TCP' CONFIG_ATM_TCP y + tristate 'ATM over TCP' CONFIG_ATM_TCP fi if [ "$CONFIG_PCI" = "y" ]; then - tristate 'Efficient Networks ENI155P' CONFIG_ATM_ENI y - if [ ! "$CONFIG_ATM_ENI" = "n" ]; then - bool ' Enable extended debugging' CONFIG_ATM_ENI_DEBUG n - bool ' Fine-tune burst settings' CONFIG_ATM_ENI_TUNE_BURST n - if [ "$CONFIG_ATM_ENI_TUNE_BURST" = "y" ]; then - bool ' Enable 16W TX bursts (discouraged)' CONFIG_ATM_ENI_BURST_TX_16W n - bool ' Enable 8W TX bursts (recommended)' CONFIG_ATM_ENI_BURST_TX_8W y - bool ' Enable 4W TX bursts (optional)' CONFIG_ATM_ENI_BURST_TX_4W n - bool ' Enable 2W TX bursts (optional)' CONFIG_ATM_ENI_BURST_TX_2W n - bool ' Enable 16W RX bursts (discouraged)' CONFIG_ATM_ENI_BURST_RX_16W n - bool ' Enable 8W RX bursts (discouraged)' CONFIG_ATM_ENI_BURST_RX_8W n - bool ' Enable 4W RX bursts (recommended)' CONFIG_ATM_ENI_BURST_RX_4W y - bool ' Enable 2W RX bursts (optional)' CONFIG_ATM_ENI_BURST_RX_2W n - fi - fi - tristate 'ZeitNet ZN1221/ZN1225' CONFIG_ATM_ZATM y - if [ ! "$CONFIG_ATM_ZATM" = "n" ]; then - bool ' Enable extended debugging' CONFIG_ATM_ZATM_DEBUG n - bool ' Enable usec resolution timestamps' CONFIG_ATM_ZATM_EXACT_TS y - fi -# bool 'Rolfs TI TNETA1570' CONFIG_ATM_TNETA1570 y -# if [ "$CONFIG_ATM_TNETA1570" = "y" ]; then -# bool ' Enable extended debugging' CONFIG_ATM_TNETA1570_DEBUG n -# fi - tristate 'IDT 77201 (NICStAR)' CONFIG_ATM_NICSTAR - if [ "$CONFIG_ATM_NICSTAR" != "n" ]; then - bool ' Use suni PHY driver' CONFIG_ATM_NICSTAR_USE_SUNI - fi - tristate 'Madge Ambassador (Collage PCI 155 Server)' CONFIG_ATM_AMBASSADOR - if [ "$CONFIG_ATM_AMBASSADOR" != "n" ]; then - bool ' Enable debugging messages' CONFIG_ATM_AMBASSADOR_DEBUG - fi - tristate 'Madge Horizon [Ultra] (Collage PCI 25 and Collage PCI 155 Client)' CONFIG_ATM_HORIZON y - if [ "$CONFIG_ATM_HORIZON" != "n" ]; then - bool ' Enable debugging messages' CONFIG_ATM_HORIZON_DEBUG - fi + tristate 'Efficient Networks ENI155P' CONFIG_ATM_ENI + if [ ! "$CONFIG_ATM_ENI" = "n" ]; then + bool ' Enable extended debugging' CONFIG_ATM_ENI_DEBUG + bool ' Fine-tune burst settings' CONFIG_ATM_ENI_TUNE_BURST + if [ "$CONFIG_ATM_ENI_TUNE_BURST" = "y" ]; then + bool ' Enable 16W TX bursts (discouraged)' CONFIG_ATM_ENI_BURST_TX_16W + bool ' Enable 8W TX bursts (recommended)' CONFIG_ATM_ENI_BURST_TX_8W + bool ' Enable 4W TX bursts (optional)' CONFIG_ATM_ENI_BURST_TX_4W + bool ' Enable 2W TX bursts (optional)' CONFIG_ATM_ENI_BURST_TX_2W + bool ' Enable 16W RX bursts (discouraged)' CONFIG_ATM_ENI_BURST_RX_16W + bool ' Enable 8W RX bursts (discouraged)' CONFIG_ATM_ENI_BURST_RX_8W + bool ' Enable 4W RX bursts (recommended)' CONFIG_ATM_ENI_BURST_RX_4W + bool ' Enable 2W RX bursts (optional)' CONFIG_ATM_ENI_BURST_RX_2W + fi + fi + tristate 'ZeitNet ZN1221/ZN1225' CONFIG_ATM_ZATM + if [ ! "$CONFIG_ATM_ZATM" = "n" ]; then + bool ' Enable extended debugging' CONFIG_ATM_ZATM_DEBUG + bool ' Enable usec resolution timestamps' CONFIG_ATM_ZATM_EXACT_TS + fi +# bool 'Rolfs TI TNETA1570' CONFIG_ATM_TNETA1570 y +# if [ "$CONFIG_ATM_TNETA1570" = "y" ]; then +# bool ' Enable extended debugging' CONFIG_ATM_TNETA1570_DEBUG n +# fi + tristate 'IDT 77201 (NICStAR)' CONFIG_ATM_NICSTAR + if [ "$CONFIG_ATM_NICSTAR" != "n" ]; then + bool ' Use suni PHY driver' CONFIG_ATM_NICSTAR_USE_SUNI + fi + tristate 'Madge Ambassador (Collage PCI 155 Server)' CONFIG_ATM_AMBASSADOR + if [ "$CONFIG_ATM_AMBASSADOR" != "n" ]; then + bool ' Enable debugging messages' CONFIG_ATM_AMBASSADOR_DEBUG + fi + tristate 'Madge Horizon [Ultra] (Collage PCI 25 and Collage PCI 155 Client)' CONFIG_ATM_HORIZON + if [ "$CONFIG_ATM_HORIZON" != "n" ]; then + bool ' Enable debugging messages' CONFIG_ATM_HORIZON_DEBUG + fi fi endmenu diff -u --recursive --new-file v2.3.19/linux/drivers/block/ide-pci.c linux/drivers/block/ide-pci.c --- v2.3.19/linux/drivers/block/ide-pci.c Tue Aug 31 17:29:13 1999 +++ linux/drivers/block/ide-pci.c Fri Oct 8 10:06:21 1999 @@ -507,7 +507,7 @@ if ((hwif = ide_match_hwif(base, d->bootable, d->name)) == NULL) continue; /* no room in ide_hwifs[] */ if (hwif->io_ports[IDE_DATA_OFFSET] != base) { - ide_init_hwif_ports(&hwif->hw, base, (ctl + 2), NULL); + ide_init_hwif_ports(&hwif->hw, base, (ctl | 2), NULL); memcpy(hwif->io_ports, hwif->hw.io_ports, sizeof(hwif->io_ports)); hwif->noprobe = !hwif->io_ports[IDE_DATA_OFFSET]; } diff -u --recursive --new-file v2.3.19/linux/drivers/char/defkeymap.c linux/drivers/char/defkeymap.c --- v2.3.19/linux/drivers/char/defkeymap.c Thu Aug 12 10:17:17 1999 +++ linux/drivers/char/defkeymap.c Thu Oct 7 10:17:09 1999 @@ -233,7 +233,6 @@ {'A', 'A', '\305'}, {'a', 'a', '\345'}, {'A', 'E', '\306'}, {'a', 'e', '\346'}, {',', 'C', '\307'}, {',', 'c', '\347'}, - {'\'', 'C', '\307'}, {'\'', 'c', '\347'}, {'`', 'E', '\310'}, {'`', 'e', '\350'}, {'\'', 'E', '\311'}, {'\'', 'e', '\351'}, {'^', 'E', '\312'}, {'^', 'e', '\352'}, @@ -260,4 +259,4 @@ {'s', 'z', '\337'}, {'i', 'j', '\377'}, }; -unsigned int accent_table_size = 70; +unsigned int accent_table_size = 68; diff -u --recursive --new-file v2.3.19/linux/drivers/char/mem.c linux/drivers/char/mem.c --- v2.3.19/linux/drivers/char/mem.c Fri Sep 10 23:57:29 1999 +++ linux/drivers/char/mem.c Thu Oct 7 10:17:09 1999 @@ -50,7 +50,7 @@ #ifdef CONFIG_MDA_CONSOLE extern void mda_console_init(void); #endif -#if defined(CONFIG_PPC) || defined(CONFIG_MAC) +#if defined(CONFIG_ADB) extern void adbdev_init(void); #endif #ifdef CONFIG_USB @@ -667,7 +667,7 @@ #ifdef CONFIG_VIDEO_BT848 i2c_init(); #endif -#if defined(CONFIG_PPC) || defined(CONFIG_MAC) +#if defined(CONFIG_ADB) adbdev_init(); #endif #ifdef CONFIG_VIDEO_DEV diff -u --recursive --new-file v2.3.19/linux/drivers/char/pms.c linux/drivers/char/pms.c --- v2.3.19/linux/drivers/char/pms.c Wed Jun 2 11:29:13 1999 +++ linux/drivers/char/pms.c Fri Oct 8 10:06:12 1999 @@ -22,6 +22,7 @@ #include #include #include +#include #include #include #include @@ -1024,21 +1025,11 @@ return 0; } -static void shutdown_mediavision(void) -{ - release_region(io_port,3); - release_region(0x9A01, 1); -} - /* - * Module stuff + * Initialization and module stuff */ -#ifdef MODULE -int init_module(void) -#else -int init_pms_cards(struct video_init *v) -#endif +static int __init init_pms_cards(void) { printk(KERN_INFO "Mediavision Pro Movie Studio driver 0.02\n"); @@ -1057,15 +1048,21 @@ return video_register_device((struct video_device *)&pms_device, VFL_TYPE_GRABBER); } -#ifdef MODULE - MODULE_PARM(io_port,"i"); MODULE_PARM(mem_base,"i"); -void cleanup_module(void) +static void __exit shutdown_mediavision(void) +{ + release_region(io_port,3); + release_region(0x9A01, 1); +} + +static void __exit cleanup_pms_module(void) { shutdown_mediavision(); video_unregister_device((struct video_device *)&pms_device); } -#endif +module_init(init_pms_cards); +module_exit(cleanup_pms_module); + diff -u --recursive --new-file v2.3.19/linux/drivers/char/ppdev.c linux/drivers/char/ppdev.c --- v2.3.19/linux/drivers/char/ppdev.c Tue Aug 31 17:29:13 1999 +++ linux/drivers/char/ppdev.c Thu Oct 7 14:10:06 1999 @@ -34,8 +34,12 @@ * YIELD parport_yield_blocking * WCTLONIRQ on interrupt, set control lines * CLRIRQ clear (and return) interrupt count + * SETTIME sets device timeout (struct timeval) + * GETTIME gets device timeout (struct timeval) * read/write read or write in current IEEE 1284 protocol * select wait for interrupt (in readfds) + * + * Added SETTIME/GETTIME ioctl, Fred Barnes 1999. */ #include @@ -74,6 +78,9 @@ #define PP_BUFFER_SIZE 256 #define PARDEVICE_MAX 8 +/* ROUND_UP macro from fs/select.c */ +#define ROUND_UP(x,y) (((x)+(y)-1)/(y)) + static inline void enable_irq (struct pp_struct *pp) { struct parport *port = pp->pdev->port; @@ -356,6 +363,8 @@ unsigned char mask; int mode; int ret; + struct timeval par_timeout; + long to_jiffies; case PPRSTATUS: reg = parport_read_status (port); @@ -449,6 +458,33 @@ if (copy_to_user ((int *) arg, &ret, sizeof (ret))) return -EFAULT; atomic_sub (ret, &pp->irqc); + return 0; + + case PPSETTIME: + if (copy_from_user (&par_timeout, (struct timeval *)arg, + sizeof(struct timeval))) { + return -EFAULT; + } + /* Convert to jiffies, place in pp->pdev->timeout */ + if ((par_timeout.tv_sec < 0) || (par_timeout.tv_usec < 0)) { + return -EINVAL; + } + to_jiffies = ROUND_UP(par_timeout.tv_usec, 1000000/HZ); + to_jiffies += par_timeout.tv_sec * (long)HZ; + if (to_jiffies <= 0) { + return -EINVAL; + } + pp->pdev->timeout = to_jiffies; + return 0; + + case PPGETTIME: + to_jiffies = pp->pdev->timeout; + par_timeout.tv_sec = to_jiffies / HZ; + par_timeout.tv_usec = (to_jiffies % (long)HZ) * (1000000/HZ); + if (copy_to_user ((struct timeval *)arg, &par_timeout, + sizeof(struct timeval))) { + return -EFAULT; + } return 0; default: diff -u --recursive --new-file v2.3.19/linux/drivers/char/ppdev.h linux/drivers/char/ppdev.h --- v2.3.19/linux/drivers/char/ppdev.h Fri Jul 30 12:28:26 1999 +++ linux/drivers/char/ppdev.h Thu Oct 7 14:10:06 1999 @@ -10,6 +10,7 @@ * as published by the Free Software Foundation; either version * 2 of the License, or (at your option) any later version. * + * Added PPGETTIME/PPSETTIME, Fred Barnes, 1999 */ #define PP_MAJOR 99 @@ -72,3 +73,9 @@ /* Set the IEEE 1284 phase that we're in (e.g. IEEE1284_PH_FWD_IDLE) */ #define PPSETPHASE _IOW(PP_IOCTL, 0x94, int) + +/* Set and get port timeout (struct timeval's) */ +#define PPGETTIME _IOW(PP_IOCTL, 0x95, struct timeval) +#define PPSETTIME _IOR(PP_IOCTL, 0x96, struct timeval) + + diff -u --recursive --new-file v2.3.19/linux/drivers/macintosh/Makefile linux/drivers/macintosh/Makefile --- v2.3.19/linux/drivers/macintosh/Makefile Mon Jun 7 12:12:32 1999 +++ linux/drivers/macintosh/Makefile Thu Oct 7 10:17:09 1999 @@ -13,13 +13,11 @@ MOD_SUB_DIRS := $(SUB_DIRS) L_TARGET := macintosh.a +L_OBJS := M_OBJS := -ifndef CONFIG_MBX -L_OBJS := via-cuda.o macio-adb.o via-pmu.o mediabay.o -endif -ifeq ($(CONFIG_MAC_KEYBOARD),y) -LX_OBJS := adb.o +ifeq ($(CONFIG_PMAC_PBOOK),y) + L_OBJS += mediabay.o endif ifeq ($(CONFIG_MAC_SERIAL),y) @@ -38,8 +36,36 @@ endif endif -ifdef CONFIG_MAC_KEYBOARD -L_OBJS += mac_keyb.o +ifdef CONFIG_ADB + LX_OBJS := adb.o +endif + +ifdef CONFIG_ADB_KEYBOARD + L_OBJS += mac_keyb.o +endif + +ifdef CONFIG_ADB_MACII + L_OBJS += via-macii.o +endif + +ifdef CONFIG_ADB_MACIISI + L_OBJS += via-maciisi.o +endif + +ifdef CONFIG_ADB_CUDA + L_OBJS += via-cuda.o +endif + +ifdef CONFIG_ADB_IOP + L_OBJS += adb-iop.o +endif + +ifdef CONFIG_ADB_PMU + L_OBJS += via-pmu.o +endif + +ifdef CONFIG_ADB_MACIO + L_OBJS += macio-adb.o endif include $(TOPDIR)/Rules.make diff -u --recursive --new-file v2.3.19/linux/drivers/macintosh/adb.c linux/drivers/macintosh/adb.c --- v2.3.19/linux/drivers/macintosh/adb.c Wed Aug 4 16:36:41 1999 +++ linux/drivers/macintosh/adb.c Thu Oct 7 10:17:09 1999 @@ -24,29 +24,59 @@ #include #include #include +#include +#include +#include +#include #include -#include -#include -#include -#include +#include #include +#ifdef CONFIG_PPC +#include #include -#include +#endif EXPORT_SYMBOL(adb_controller); EXPORT_SYMBOL(adb_client_list); -EXPORT_SYMBOL(adb_hardware); -struct adb_controller *adb_controller = NULL; +extern struct adb_driver via_macii_driver; +extern struct adb_driver via_maciisi_driver; +extern struct adb_driver via_cuda_driver; +extern struct adb_driver adb_iop_driver; +extern struct adb_driver via_pmu_driver; +extern struct adb_driver macio_adb_driver; + +static struct adb_driver *adb_driver_list[] = { +#ifdef CONFIG_ADB_MACII + &via_macii_driver, +#endif +#ifdef CONFIG_ADB_MACIISI + &via_maciisi_driver, +#endif +#ifdef CONFIG_ADB_CUDA + &via_cuda_driver, +#endif +#ifdef CONFIG_ADB_IOP + &adb_iop_driver, +#endif +#ifdef CONFIG_ADB_PMU + &via_pmu_driver, +#endif +#ifdef CONFIG_ADB_MACIO + &macio_adb_driver, +#endif + NULL +}; + +struct adb_driver *adb_controller; struct notifier_block *adb_client_list = NULL; -enum adb_hw adb_hardware = ADB_NONE; +static int adb_got_sleep = 0; #ifdef CONFIG_PMAC_PBOOK -static int adb_notify_sleep(struct notifier_block *, unsigned long, void *); -static struct notifier_block adb_sleep_notifier = { +static int adb_notify_sleep(struct pmu_sleep_notifier *self, int when); +static struct pmu_sleep_notifier adb_sleep_notifier = { adb_notify_sleep, - NULL, - 0 + SLEEP_LEVEL_ADB, }; #endif @@ -109,6 +139,15 @@ adb_request(&req, NULL, ADBREQ_SYNC, 3, (i<< 4) | 0xb, (highFree | 0x60), 0xfe); /* + * See if anybody actually moved. This is suggested + * by HW TechNote 01: + * + * http://developer.apple.com/technotes/hw/hw_01.html + */ + adb_request(&req, NULL, ADBREQ_SYNC | ADBREQ_REPLY, 1, + (highFree << 4) | 0xf); + if (req.reply_len <= 1) continue; + /* * Test whether there are any device(s) left * at address i. */ @@ -159,49 +198,73 @@ return devmask; } -void adb_init(void) +int __init adb_init(void) { + struct adb_driver *driver; + int i; + +#ifdef CONFIG_PPC if ( (_machine != _MACH_chrp) && (_machine != _MACH_Pmac) ) - return; + return 0; +#endif +#ifdef CONFIG_MAC + if (!MACH_IS_MAC) + return 0; +#endif - via_cuda_init(); - via_pmu_init(); - macio_adb_init(); - - if (adb_controller == NULL) + adb_controller = NULL; + + i = 0; + while ((driver = adb_driver_list[i++]) != NULL) { + if (!driver->probe()) { + adb_controller = driver; + break; + } + } + if ((adb_controller == NULL) || adb_controller->init()) { printk(KERN_WARNING "Warning: no ADB interface detected\n"); - else - { - adb_hardware = adb_controller->kind; + } else { #ifdef CONFIG_PMAC_PBOOK - notifier_chain_register(&sleep_notifier_list, - &adb_sleep_notifier); + pmu_register_sleep_notifier(&adb_sleep_notifier); #endif /* CONFIG_PMAC_PBOOK */ adb_reset_bus(); } + return 0; } +__initcall(adb_init); #ifdef CONFIG_PMAC_PBOOK /* * notify clients before sleep and reset bus afterwards */ int -adb_notify_sleep(struct notifier_block *this, unsigned long code, void *x) +adb_notify_sleep(struct pmu_sleep_notifier *self, int when) { int ret; - switch (code) { - case PBOOK_SLEEP: - ret = notifier_call_chain(&adb_client_list, ADB_MSG_POWERDOWN, NULL); - if (ret & NOTIFY_STOP_MASK) - return -EBUSY; - case PBOOK_WAKE: + switch (when) { + case PBOOK_SLEEP_REQUEST: + adb_got_sleep = 1; + ret = notifier_call_chain(&adb_client_list, ADB_MSG_POWERDOWN, NULL); + if (ret & NOTIFY_STOP_MASK) + return PBOOK_SLEEP_REFUSE; + break; + case PBOOK_SLEEP_REJECT: + if (adb_got_sleep) { + adb_got_sleep = 0; adb_reset_bus(); - break; + } + break; + + case PBOOK_SLEEP_NOW: + break; + case PBOOK_WAKE: + adb_reset_bus(); + break; } - return NOTIFY_DONE; + return PBOOK_SLEEP_OK; } #endif /* CONFIG_PMAC_PBOOK */ @@ -277,6 +340,9 @@ req->data[i+1] = va_arg(list, int); va_end(list); + if (flags & ADBREQ_NOSEND) + return 0; + return adb_controller->send_request(req, flags & ADBREQ_SYNC); } @@ -413,7 +479,7 @@ { struct adbdev_state *state; - if (MINOR(inode->i_rdev) > 0 || (adb_controller == NULL)/*adb_hardware == ADB_NONE*/) + if (MINOR(inode->i_rdev) > 0 || adb_controller == NULL) return -ENXIO; state = kmalloc(sizeof(struct adbdev_state), GFP_KERNEL); if (state == 0) @@ -540,6 +606,7 @@ goto out; atomic_inc(&state->n_pending); + if (adb_controller == NULL) return -ENXIO; /* Special case for ADB_BUSRESET request, all others are sent to the controller */ @@ -582,8 +649,15 @@ void adbdev_init() { +#ifdef CONFIG_PPC if ( (_machine != _MACH_chrp) && (_machine != _MACH_Pmac) ) - return; + return; +#endif +#ifdef CONFIG_MAC + if (!MACH_IS_MAC) + return; +#endif + if (register_chrdev(ADB_MAJOR, "adb", &adb_fops)) printk(KERN_ERR "adb: unable to get major %d\n", ADB_MAJOR); } diff -u --recursive --new-file v2.3.19/linux/drivers/macintosh/mac_keyb.c linux/drivers/macintosh/mac_keyb.c --- v2.3.19/linux/drivers/macintosh/mac_keyb.c Tue Aug 31 17:29:13 1999 +++ linux/drivers/macintosh/mac_keyb.c Thu Oct 7 10:17:09 1999 @@ -39,12 +39,13 @@ #include #include #include +#include #include -#include -#include -#include +#include +#include +#include #include #include @@ -239,7 +240,7 @@ static void init_turbomouse(int id); static void init_microspeed(int id); -#ifdef CONFIG_ADBMOUSE +#ifdef CONFIG_ADB_MOUSE /* XXX: Hook for mouse driver */ void (*adb_mouse_interrupt_hook)(unsigned char *, int); int adb_emulate_buttons = 0; @@ -250,6 +251,7 @@ extern int console_loglevel; extern struct kbd_struct kbd_table[]; +extern wait_queue_head_t keypress_wait; extern void handle_scancode(unsigned char, int); @@ -334,7 +336,7 @@ if (!repeat) del_timer(&repeat_timer); -#ifdef CONFIG_ADBMOUSE +#ifdef CONFIG_ADB_MOUSE /* * XXX: Add mouse button 2+3 fake codes here if mouse open. * Keep track of 'button' states here as we only send @@ -364,7 +366,7 @@ } return; } -#endif /* CONFIG_ADBMOUSE */ +#endif /* CONFIG_ADB_MOUSE */ if (kbd->kbdmode != VC_RAW) { if (!up_flag && !dont_repeat[keycode]) { @@ -420,7 +422,7 @@ } } -#ifdef CONFIG_ADBMOUSE +#ifdef CONFIG_ADB_MOUSE static void mouse_input(unsigned char *data, int nb, struct pt_regs *regs, int autopoll) { @@ -552,7 +554,7 @@ } } } -#endif /* CONFIG_ADBMOUSE */ +#endif /* CONFIG_ADB_MOUSE */ /* XXX Needs to get rid of this, see comments in pmu.c */ extern int backlight_level; @@ -566,7 +568,11 @@ */ /* Ignore data from register other than 0 */ +#if 0 if ((adb_hardware != ADB_VIAPMU) || (data[0] & 0x3) || (nb < 2)) +#else + if ((data[0] & 0x3) || (nb < 2)) +#endif return; switch (data[1]&0xf ) @@ -592,22 +598,26 @@ /* brightness decrease */ case 0xa: /* down event */ +#ifdef CONFIG_PPC if ( data[1] == (data[1]&0xf) ) { if (backlight_level > 2) pmu_set_brightness(backlight_level-2); else pmu_set_brightness(0); } +#endif break; /* brightness increase */ case 0x9: /* down event */ +#ifdef CONFIG_PPC if ( data[1] == (data[1]&0xf) ) { if (backlight_level < 0x1e) pmu_set_brightness(backlight_level+2); else pmu_set_brightness(0x1f); } +#endif break; } } @@ -672,8 +682,14 @@ void __init mackbd_init_hw(void) { +#ifdef CONFIG_PPC if ( (_machine != _MACH_chrp) && (_machine != _MACH_Pmac) ) - return; + return; +#endif +#ifdef CONFIG_MAC + if (!MACH_IS_MAC) + return; +#endif /* setup key map */ memcpy(key_maps[0], macplain_map, sizeof(plain_map)); @@ -684,7 +700,7 @@ memcpy(key_maps[8], macalt_map, sizeof(plain_map)); memcpy(key_maps[12], macctrl_alt_map, sizeof(plain_map)); -#ifdef CONFIG_ADBMOUSE +#ifdef CONFIG_ADB_MOUSE /* initialize mouse interrupt hook */ adb_mouse_interrupt_hook = NULL; #endif @@ -720,9 +736,9 @@ struct adb_request req; int i; -#ifdef CONFIG_ADBMOUSE +#ifdef CONFIG_ADB_MOUSE adb_register(ADB_MOUSE, 0, &mouse_ids, mouse_input); -#endif /* CONFIG_ADBMOUSE */ +#endif /* CONFIG_ADB_MOUSE */ adb_register(ADB_KEYBOARD, 0, &keyboard_ids, keyboard_input); adb_register(0x07, 0x1F, &buttons_ids, buttons_input); diff -u --recursive --new-file v2.3.19/linux/drivers/macintosh/macio-adb.c linux/drivers/macintosh/macio-adb.c --- v2.3.19/linux/drivers/macintosh/macio-adb.c Tue Aug 31 17:29:13 1999 +++ linux/drivers/macintosh/macio-adb.c Thu Oct 7 10:17:09 1999 @@ -8,7 +8,7 @@ #include #include #include -#include +#include #include #include #include @@ -59,28 +59,38 @@ static struct adb_request *current_req, *last_req; static unsigned char adb_rbuf[16]; +static int macio_probe(void); +static int macio_init(void); static void macio_adb_interrupt(int irq, void *arg, struct pt_regs *regs); -static int macio_adb_send_request(struct adb_request *req, int sync); +static int macio_send_request(struct adb_request *req, int sync); static int macio_adb_autopoll(int devs); static void macio_adb_poll(void); static int macio_adb_reset_bus(void); static void completed(void); -static struct adb_controller macio_controller = { - ADB_MACIO, - macio_adb_send_request, +struct adb_driver macio_adb_driver = { + "MACIO", + macio_probe, + macio_init, + macio_send_request, + /*macio_write,*/ macio_adb_autopoll, - macio_adb_reset_bus, - macio_adb_poll + macio_adb_poll, + macio_adb_reset_bus }; -void macio_adb_init(void) +int macio_probe(void) +{ + return find_compatible_devices("adb", "chrp,adb0")? 0: -ENODEV; +} + +int macio_init(void) { struct device_node *adbs; adbs = find_compatible_devices("adb", "chrp,adb0"); if (adbs == 0) - return; + return -ENXIO; #if 0 { int i; @@ -101,7 +111,7 @@ 0, "ADB", (void *)0)) { printk(KERN_ERR "ADB: can't get irq %d\n", adbs->intrs[0].line); - return; + return -EAGAIN; } out_8(&adb->ctrl.r, 0); @@ -112,12 +122,7 @@ out_8(&adb->autopoll.r, APE); out_8(&adb->intr_enb.r, DFB | TAG); - adb_controller = &macio_controller; -// adb_hardware = ADB_MACIO; - -// adb_send_request = macio_adb_send_request; -// adb_autopoll = macio_adb_autopoll; -// adb_reset_bus = macio_reset_bus; + return 0; } static int macio_adb_autopoll(int devs) @@ -143,7 +148,7 @@ } /* Send an ADB command */ -static int macio_adb_send_request(struct adb_request *req, int sync) +static int macio_send_request(struct adb_request *req, int sync) { unsigned long mflags; int i; diff -u --recursive --new-file v2.3.19/linux/drivers/macintosh/macserial.c linux/drivers/macintosh/macserial.c --- v2.3.19/linux/drivers/macintosh/macserial.c Fri Sep 10 23:57:29 1999 +++ linux/drivers/macintosh/macserial.c Thu Oct 7 10:17:09 1999 @@ -36,14 +36,22 @@ #include #include #include -#include -#include +#include +#include #ifdef CONFIG_KGDB #include #endif #include "macserial.h" +#ifdef CONFIG_PMAC_PBOOK +static int serial_notify_sleep(struct pmu_sleep_notifier *self, int when); +static struct pmu_sleep_notifier serial_sleep_notifier = { + serial_notify_sleep, + SLEEP_LEVEL_MISC, +}; +#endif + /* * It would be nice to dynamically allocate everything that * depends on NUM_SERIAL, so we could support any number of @@ -1909,6 +1917,10 @@ } *pp = 0; zs_channels_found = n; +#ifdef CONFIG_PMAC_PBOOK + if (n) + pmu_register_sleep_notifier(&serial_sleep_notifier); +#endif /* CONFIG_PMAC_PBOOK */ } /* rs_init inits the driver */ @@ -2470,3 +2482,40 @@ set_debug_traps(); /* init stub */ } #endif /* ifdef CONFIG_KGDB */ + +#ifdef CONFIG_PMAC_PBOOK +/* + * notify clients before sleep and reset bus afterwards + */ +int +serial_notify_sleep(struct pmu_sleep_notifier *self, int when) +{ + int i; + + switch (when) { + case PBOOK_SLEEP_REQUEST: + case PBOOK_SLEEP_REJECT: + break; + + case PBOOK_SLEEP_NOW: + for (i=0; iflags & ZILOG_INITIALIZED) { + shutdown(info); + info->flags |= ZILOG_SLEEPING; + } + } + break; + case PBOOK_WAKE: + for (i=0; iflags & ZILOG_SLEEPING) { + info->flags &= ~ZILOG_SLEEPING; + startup(info, 0); + } + } + break; + } + return PBOOK_SLEEP_OK; +} +#endif /* CONFIG_PMAC_PBOOK */ diff -u --recursive --new-file v2.3.19/linux/drivers/macintosh/macserial.h linux/drivers/macintosh/macserial.h --- v2.3.19/linux/drivers/macintosh/macserial.h Sat May 15 15:05:36 1999 +++ linux/drivers/macintosh/macserial.h Thu Oct 7 10:17:09 1999 @@ -68,6 +68,7 @@ #define ZILOG_CLOSING 0x08000000 /* Serial port is closing */ #define ZILOG_CTS_FLOW 0x04000000 /* Do CTS flow control */ #define ZILOG_CHECK_CD 0x02000000 /* i.e., CLOCAL */ +#define ZILOG_SLEEPING 0x01000000 /* have shut it down for sleep */ /* Software state per channel */ diff -u --recursive --new-file v2.3.19/linux/drivers/macintosh/mediabay.c linux/drivers/macintosh/mediabay.c --- v2.3.19/linux/drivers/macintosh/mediabay.c Fri Sep 10 23:57:29 1999 +++ linux/drivers/macintosh/mediabay.c Thu Oct 7 10:17:09 1999 @@ -26,7 +26,16 @@ #include #include #include +#include +#include +#ifdef CONFIG_PMAC_PBOOK +static int mb_notify_sleep(struct pmu_sleep_notifier *self, int when); +static struct pmu_sleep_notifier mb_sleep_notifier = { + mb_notify_sleep, + SLEEP_LEVEL_MEDIABAY, +}; +#endif #undef MB_USE_INTERRUPTS @@ -77,13 +86,13 @@ * Hold the media-bay reset signal true for this many ticks * after a device is inserted before releasing it. */ -#define MB_RESET_COUNT 20 +#define MB_RESET_COUNT 40 /* * Wait this many ticks after an IDE device (e.g. CD-ROM) is inserted * (or until the device is ready) before registering the IDE interface. */ -#define MB_IDE_WAIT 1000 +#define MB_IDE_WAIT 1500 static void poll_media_bay(int which); static void set_media_bay(int which, int id); @@ -157,6 +166,10 @@ { printk(KERN_INFO "Registered %d media-bay(s)\n", media_bay_count); +#ifdef CONFIG_PMAC_PBOOK + pmu_register_sleep_notifier(&mb_sleep_notifier); +#endif /* CONFIG_PMAC_PBOOK */ + kernel_thread(media_bay_task, NULL, 0); } } @@ -298,9 +311,16 @@ int id = MB_CONTENTS(which); if (id == media_bays[which].last_value) { - if (id != media_bays[which].content_id - && ++media_bays[which].value_count >= MB_STABLE_COUNT) - set_media_bay(which, id); + if (id != media_bays[which].content_id + && ++media_bays[which].value_count >= MB_STABLE_COUNT) { + /* If the device type changes without going thru "MB_NO", we force + a pass by "MB_NO" to make sure things are properly reset */ + if ((id != MB_NO) && (media_bays[which].content_id != MB_NO)) { + set_media_bay(which, MB_NO); + udelay(500); + } + set_media_bay(which, id); + } } else { media_bays[which].last_value = id; media_bays[which].value_count = 0; @@ -319,27 +339,28 @@ switch (id) { case MB_CD: - feature_clear(bay->dev_node, FEATURE_Mediabay_floppy_enable); feature_set(bay->dev_node, FEATURE_Mediabay_enable); - feature_set(bay->dev_node, FEATURE_CD_power); feature_set(bay->dev_node, FEATURE_Mediabay_IDE_enable); + udelay(500); + feature_set(bay->dev_node, FEATURE_CD_power); printk(KERN_INFO "media bay %d contains a CD-ROM drive\n", which); break; case MB_FD: - feature_clear(bay->dev_node, FEATURE_CD_power); feature_set(bay->dev_node, FEATURE_Mediabay_enable); feature_set(bay->dev_node, FEATURE_Mediabay_floppy_enable); feature_set(bay->dev_node, FEATURE_SWIM3_enable); printk(KERN_INFO "media bay %d contains a floppy disk drive\n", which); break; case MB_NO: - feature_clear(bay->dev_node, FEATURE_Mediabay_floppy_enable); feature_clear(bay->dev_node, FEATURE_CD_power); + feature_clear(bay->dev_node, FEATURE_Mediabay_enable); + feature_clear(bay->dev_node, FEATURE_Mediabay_floppy_enable); + feature_clear(bay->dev_node, FEATURE_Mediabay_IDE_enable); + feature_clear(bay->dev_node, FEATURE_SWIM3_enable); + feature_set(bay->dev_node, FEATURE_Mediabay_reset); printk(KERN_INFO "media bay %d is empty\n", which); break; default: - feature_clear(bay->dev_node, FEATURE_Mediabay_floppy_enable); - feature_clear(bay->dev_node, FEATURE_CD_power); feature_set(bay->dev_node, FEATURE_Mediabay_enable); printk(KERN_INFO "media bay %d contains an unknown device (%d)\n", which, id); @@ -348,3 +369,62 @@ udelay(500); } + +#ifdef CONFIG_PMAC_PBOOK +/* + * notify clients before sleep and reset bus afterwards + */ +int __pmac +mb_notify_sleep(struct pmu_sleep_notifier *self, int when) +{ + volatile struct media_bay_info* bay; + int i; + + switch (when) { + case PBOOK_SLEEP_REQUEST: + case PBOOK_SLEEP_REJECT: + break; + + case PBOOK_SLEEP_NOW: + for (i=0; idev_node, FEATURE_Mediabay_enable); + feature_clear(bay->dev_node, FEATURE_Mediabay_IDE_enable); + feature_clear(bay->dev_node, FEATURE_SWIM3_enable); + feature_clear(bay->dev_node, FEATURE_Mediabay_floppy_enable); + feature_set(bay->dev_node, FEATURE_Mediabay_reset); + feature_clear(bay->dev_node, FEATURE_CD_power); + out_8(&media_bays[i].addr->contents, 0x70); + } + break; + case PBOOK_WAKE: + for (i=0; idev_node, FEATURE_Mediabay_enable); + /* I suppose this is enough delay to stabilize MB_CONTENT ... */ + mdelay(10); + /* We re-enable the bay using it's previous content only if + it did not change */ + if (MB_CONTENTS(i) == bay->content_id) { + set_media_bay(i, bay->content_id); + if (bay->content_id != MB_NO) { + mdelay(400); + /* Clear the bay reset */ + feature_clear(bay->dev_node, FEATURE_Mediabay_reset); + /* This small delay makes sure the device has time + to assert the BUSY bit (used by IDE sleep) */ + udelay(100); + /* We reset the state machine timers in case we were in the + middle of a wait loop */ + if (bay->reset_timer) + bay->reset_timer = MB_RESET_COUNT; + if (bay->cd_timer) + bay->cd_timer = MB_IDE_WAIT; + } + } + } + break; + } + return PBOOK_SLEEP_OK; +} +#endif /* CONFIG_PMAC_PBOOK */ diff -u --recursive --new-file v2.3.19/linux/drivers/macintosh/via-cuda.c linux/drivers/macintosh/via-cuda.c --- v2.3.19/linux/drivers/macintosh/via-cuda.c Tue Aug 31 17:29:14 1999 +++ linux/drivers/macintosh/via-cuda.c Thu Oct 7 10:17:09 1999 @@ -14,16 +14,31 @@ #include #include #include +#include +#include +#ifdef CONFIG_PPC #include -#include -#include +#include +#else +#include +#include +#include +#include +#endif #include -#include #include #include static volatile unsigned char *via; +#ifdef CONFIG_MAC +#define CUDA_IRQ IRQ_MAC_ADB +#define __openfirmware +#define eieio() +#else +#define CUDA_IRQ vias->intrs[0].line +#endif + /* VIA registers - spaced 0x200 bytes apart */ #define RS 0x200 /* skip between registers */ #define B 0 /* B-side data */ @@ -73,27 +88,38 @@ static unsigned char *reply_ptr; static int reading_reply; static int data_index; +#ifdef CONFIG_PPC static struct device_node *vias; +#endif static int cuda_fully_inited = 0; -static int init_via(void); +static int cuda_probe(void); +static int cuda_init(void); +static int cuda_init_via(void); static void cuda_start(void); -static void via_interrupt(int irq, void *arg, struct pt_regs *regs); +static void cuda_interrupt(int irq, void *arg, struct pt_regs *regs); static void cuda_input(unsigned char *buf, int nb, struct pt_regs *regs); -static int cuda_adb_send_request(struct adb_request *req, int sync); +static int cuda_send_request(struct adb_request *req, int sync); static int cuda_adb_autopoll(int devs); -static int cuda_adb_reset_bus(void); -static int cuda_send_request(struct adb_request *req); - - -static struct adb_controller cuda_controller = { - ADB_VIACUDA, - cuda_adb_send_request, +void cuda_poll(void); +static int cuda_reset_adb_bus(void); +static int cuda_write(struct adb_request *req); + +int cuda_request(struct adb_request *req, + void (*done)(struct adb_request *), int nbytes, ...); + +struct adb_driver via_cuda_driver = { + "CUDA", + cuda_probe, + cuda_init, + cuda_send_request, + /*cuda_write,*/ cuda_adb_autopoll, - cuda_adb_reset_bus, - cuda_poll + cuda_poll, + cuda_reset_adb_bus }; +#ifdef CONFIG_PPC void find_via_cuda() { @@ -106,7 +132,7 @@ #if 0 { int i; - printk("via_cuda_init: node = %p, addrs =", vias->node); + printk("find_via_cuda: node = %p, addrs =", vias->node); for (i = 0; i < vias->n_addrs; ++i) printk(" %x(%x)", vias->addrs[i].address, vias->addrs[i].size); printk(", intrs ="); @@ -124,31 +150,56 @@ via = (volatile unsigned char *) ioremap(vias->addrs->address, 0x2000); cuda_state = idle; + sys_ctrler = SYS_CTRLER_CUDA; +} +#endif /* CONFIG_PPC */ - if (!init_via()) { - printk(KERN_ERR "init_via failed\n"); - via = NULL; - } - - adb_controller = &cuda_controller; +static int +cuda_probe() +{ +#ifdef CONFIG_PPC + if (sys_ctrler != SYS_CTRLER_CUDA) + return -ENODEV; +#else + if (macintosh_config->adb_type != MAC_ADB_CUDA) + return -ENODEV; + via = via1; +#endif + return 0; } -void -via_cuda_init(void) +static int +cuda_init(void) { + int err; + if (via == NULL) - return; + return -ENODEV; - if (request_irq(vias->intrs[0].line, via_interrupt, 0, "VIA", (void *)0)) { - printk(KERN_ERR "VIA: can't get irq %d\n", vias->intrs[0].line); - return; + err = cuda_init_via(); + if (err) { + printk(KERN_ERR "cuda_probe: init_via() failed\n"); + via = NULL; + return err; } - /* Clear and enable interrupts */ + /* Clear and enable interrupts, but only on PPC. On 68K it's done */ + /* for us by the the main VIA driver in arch/m68k/mac/via.c */ + +#ifndef CONFIG_MAC via[IFR] = 0x7f; eieio(); /* clear interrupts by writing 1s */ via[IER] = IER_SET|SR_INT; eieio(); /* enable interrupt from SR */ +#endif + + if (request_irq(CUDA_IRQ, cuda_interrupt, 0, "ADB", cuda_interrupt)) { + printk(KERN_ERR "cuda_init: can't get irq %d\n", CUDA_IRQ); + return -EAGAIN; + } + + printk("adb: CUDA driver v0.5 for Unified ADB.\n"); cuda_fully_inited = 1; + return 0; } #define WAIT_FOR(cond, what) \ @@ -156,14 +207,14 @@ for (x = 1000; !(cond); --x) { \ if (x == 0) { \ printk("Timeout waiting for " what); \ - return 0; \ + return -ENXIO; \ } \ udelay(100); \ } \ } while (0) static int -init_via() +cuda_init_via() { int x; @@ -172,7 +223,9 @@ via[ACR] = (via[ACR] & ~SR_CTRL) | SR_EXT; /* SR data in */ eieio(); x = via[SR]; eieio(); /* clear any left-over data */ +#ifndef CONFIG_MAC via[IER] = 0x7f; eieio(); /* disable interrupts from VIA */ +#endif eieio(); /* delay 4ms and then clear any pending interrupt */ @@ -198,12 +251,12 @@ x = via[SR]; eieio(); via[B] |= TIP; eieio(); /* should be unnecessary */ - return 1; + return 0; } /* Send an ADB command */ static int -cuda_adb_send_request(struct adb_request *req, int sync) +cuda_send_request(struct adb_request *req, int sync) { int i; @@ -214,7 +267,7 @@ req->reply_expected = 1; - i = cuda_send_request(req); + i = cuda_write(req); if (i) return i; @@ -243,7 +296,7 @@ /* Reset adb bus - how do we do this?? */ static int -cuda_adb_reset_bus(void) +cuda_reset_adb_bus(void) { struct adb_request req; @@ -276,11 +329,11 @@ req->data[i] = va_arg(list, int); va_end(list); req->reply_expected = 1; - return cuda_send_request(req); + return cuda_write(req); } static int -cuda_send_request(struct adb_request *req) +cuda_write(struct adb_request *req) { unsigned long flags; @@ -336,17 +389,17 @@ void cuda_poll() { - int ie; + unsigned long flags; - __save_flags(ie); - __cli(); + save_flags(flags); + cli(); if (via[IFR] & SR_INT) - via_interrupt(0, 0, 0); - __restore_flags(ie); + cuda_interrupt(0, 0, 0); + restore_flags(flags); } static void -via_interrupt(int irq, void *arg, struct pt_regs *regs) +cuda_interrupt(int irq, void *arg, struct pt_regs *regs) { int x, status; struct adb_request *req; @@ -355,7 +408,7 @@ return; status = (~via[B] & (TIP|TREQ)) | (via[ACR] & SR_OUT); eieio(); - /* printk("via_interrupt: state=%d status=%x\n", cuda_state, status); */ + /* printk("cuda_interrupt: state=%d status=%x\n", cuda_state, status); */ switch (cuda_state) { case idle: /* CUDA has sent us the first byte of data - unsolicited */ @@ -469,7 +522,7 @@ break; default: - printk("via_interrupt: unknown cuda_state %d?\n", cuda_state); + printk("cuda_interrupt: unknown cuda_state %d?\n", cuda_state); } } @@ -489,10 +542,4 @@ printk(" %.2x", buf[i]); printk("\n"); } -} - -int -cuda_present(void) -{ - return (adb_controller && (adb_controller->kind == ADB_VIACUDA) && via); } diff -u --recursive --new-file v2.3.19/linux/drivers/macintosh/via-pmu.c linux/drivers/macintosh/via-pmu.c --- v2.3.19/linux/drivers/macintosh/via-pmu.c Tue Aug 31 17:29:14 1999 +++ linux/drivers/macintosh/via-pmu.c Thu Oct 7 10:17:09 1999 @@ -21,10 +21,12 @@ #include #include #include +#include +#include +#include +#include #include -#include -#include -#include +#include #include #include #include @@ -32,6 +34,7 @@ #include #include #include +#include /* Misc minor number allocated for /dev/pmu */ #define PMU_MINOR 154 @@ -70,6 +73,7 @@ #define IER_SET 0x80 /* set bits in IER */ #define IER_CLR 0 /* clear bits in IER */ #define SR_INT 0x04 /* Shift register full/empty */ +#define CB2_INT 0x08 #define CB1_INT 0x10 /* transition on CB1 input */ static enum pmu_state { @@ -98,11 +102,13 @@ int asleep; struct notifier_block *sleep_notifier_list; +static int pmu_probe(void); +static int pmu_init(void); static int init_pmu(void); static int pmu_queue_request(struct adb_request *req); static void pmu_start(void); static void via_pmu_interrupt(int irq, void *arg, struct pt_regs *regs); -static int pmu_adb_send_request(struct adb_request *req, int sync); +static int pmu_send_request(struct adb_request *req, int sync); static int pmu_adb_autopoll(int devs); static int pmu_adb_reset_bus(void); static void send_byte(int x); @@ -112,15 +118,31 @@ static void pmu_handle_data(unsigned char *data, int len, struct pt_regs *regs); static void set_volume(int level); +#ifdef CONFIG_PMAC_PBOOK +static void pmu_pass_intr(unsigned char *data, int len); +#endif -static struct adb_controller pmu_controller = { - ADB_VIAPMU, - pmu_adb_send_request, +struct adb_driver via_pmu_driver = { + "PMU", + pmu_probe, + pmu_init, + pmu_send_request, + /*pmu_queue_request,*/ pmu_adb_autopoll, - pmu_adb_reset_bus, - pmu_poll + pmu_poll, + pmu_adb_reset_bus }; +extern void low_sleep_handler(void); +extern void sleep_save_intrs(int); +extern void sleep_restore_intrs(void); + +extern int grackle_pcibios_read_config_word(unsigned char bus, + unsigned char dev_fn, unsigned char offset, unsigned short *val); + +extern int grackle_pcibios_write_config_word(unsigned char bus, + unsigned char dev_fn, unsigned char offset, unsigned short val); + /* * This table indicates for each PMU opcode: * - the number of data bytes to be sent with the command, or -1 @@ -164,13 +186,21 @@ /*f8*/ {-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1},{-1,-1}, }; +static char *pbook_type[] = { + "Unknown PowerBook", + "PowerBook 2400/3400/3500(G3)", + "PowerBook G3 Series", + "1999 PowerBook G3", +}; -void __openfirmware +int __openfirmware find_via_pmu() { + if (via != 0) + return 1; vias = find_devices("via-pmu"); if (vias == 0) - return; + return 0; if (vias->next != 0) printk(KERN_WARNING "Warning: only using 1st via-pmu\n"); @@ -179,7 +209,7 @@ #if 0 { int i; - printk("via_pmu_init: node = %p, addrs =", vias->node); + printk("find_via_pmu: node = %p, addrs =", vias->node); for (i = 0; i < vias->n_addrs; ++i) printk(" %x(%x)", vias->addrs[i].address, vias->addrs[i].size); printk(", intrs ="); @@ -192,12 +222,14 @@ printk(KERN_ERR "via-pmu: %d addresses, %d interrupts!\n", vias->n_addrs, vias->n_intrs); if (vias->n_addrs < 1 || vias->n_intrs < 1) - return; + return 0; } if (vias->parent->name && ((strcmp(vias->parent->name, "ohare") == 0) || device_is_compatible(vias->parent, "ohare"))) pmu_kind = PMU_OHARE_BASED; + else if (device_is_compatible(vias->parent, "paddington")) + pmu_kind = PMU_PADDINGTON_BASED; else if (device_is_compatible(vias->parent, "heathrow")) pmu_kind = PMU_HEATHROW_BASED; else @@ -209,23 +241,28 @@ pmu_state = idle; - if (!init_pmu()) + if (!init_pmu()) { via = NULL; + return 0; + } - adb_controller = &pmu_controller; + printk(KERN_INFO "PMU driver initialized for %s\n", + pbook_type[pmu_kind]); + sys_ctrler = SYS_CTRLER_PMU; + return 1; +} - if (via) - printk(KERN_INFO "PMU driver initialized for %s\n", - (pmu_kind == PMU_OHARE_BASED) ? "PowerBook 2400/3400/3500(G3)" : - ((pmu_kind == PMU_HEATHROW_BASED) ? "PowerBook G3 Series" : - "Unknown PowerBook")); +static int __openfirmware +pmu_probe() +{ + return vias == NULL? -ENODEV: 0; } -void __openfirmware -via_pmu_init(void) +static int __openfirmware +pmu_init(void) { if (vias == NULL) - return; + return -ENXIO; bright_req_1.complete = 1; bright_req_2.complete = 1; @@ -235,7 +272,7 @@ (void *)0)) { printk(KERN_ERR "VIA-PMU: can't get irq %d\n", vias->intrs[0].line); - return; + return -ENXIO; } /* Enable interrupts */ @@ -245,6 +282,8 @@ /* Enable backlight */ pmu_enable_backlight(1); + + return 0; } static int __openfirmware @@ -292,20 +331,19 @@ /* Send an ADB command */ static int __openfirmware -pmu_adb_send_request(struct adb_request *req, int sync) +pmu_send_request(struct adb_request *req, int sync) { - int i, ret; + int i, ret; - if ((vias == NULL) || (!pmu_fully_inited)) - { - req->complete = 1; - return -ENXIO; - } + if ((vias == NULL) || (!pmu_fully_inited)) { + req->complete = 1; + return -ENXIO; + } - ret = -EINVAL; - - switch (req->data[0]) { - case PMU_PACKET: + ret = -EINVAL; + + switch (req->data[0]) { + case PMU_PACKET: for (i = 0; i < req->nbytes - 1; ++i) req->data[i] = req->data[i+1]; --req->nbytes; @@ -316,7 +354,7 @@ req->reply_len = 0; ret = pmu_queue_request(req); break; - case CUDA_PACKET: + case CUDA_PACKET: switch (req->data[1]) { case CUDA_GET_TIME: if (req->nbytes != 2) @@ -344,7 +382,7 @@ break; } break; - case ADB_PACKET: + case ADB_PACKET: for (i = req->nbytes - 1; i > 1; --i) req->data[i+2] = req->data[i]; req->data[3] = req->nbytes - 2; @@ -356,19 +394,17 @@ req->reply_len = 0; ret = pmu_queue_request(req); break; - } - if (ret) - { - req->complete = 1; - return ret; - } - - if (sync) { - while (!req->complete) - pmu_poll(); - } + } + if (ret) { + req->complete = 1; + return ret; + } + + if (sync) + while (!req->complete) + pmu_poll(); - return 0; + return 0; } /* Enable/disable autopolling */ @@ -513,19 +549,25 @@ static void __openfirmware send_byte(int x) { - out_8(&via[ACR], 0x1c); - out_8(&via[SR], x); - out_8(&via[B], via[B] & ~0x10); /* assert TREQ */ + volatile unsigned char *v = via; + + out_8(&v[ACR], in_8(&v[ACR]) | SR_OUT | SR_EXT); + out_8(&v[SR], x); + out_8(&v[B], in_8(&v[B]) & ~TREQ); /* assert TREQ */ } static void __openfirmware recv_byte() { - out_8(&via[ACR], 0x0c); - in_8(&via[SR]); /* resets SR */ - out_8(&via[B], via[B] & ~0x10); + volatile unsigned char *v = via; + + out_8(&v[ACR], (in_8(&v[ACR]) & ~SR_OUT) | SR_EXT); + in_8(&v[SR]); /* resets SR */ + out_8(&v[B], in_8(&v[B]) & ~0x10); } +static int disable_poll; + static void __openfirmware pmu_start() { @@ -545,7 +587,9 @@ data_len = pmu_data_len[req->data[0]][0]; /* set the shift register to shift out and send a byte */ + ++disable_poll; send_byte(req->data[0]); + --disable_poll; out: restore_flags(flags); @@ -554,13 +598,15 @@ void __openfirmware pmu_poll() { - int ie; + unsigned long flags; - __save_flags(ie); - __cli(); + if (disable_poll) + return; + save_flags(flags); + cli(); if (via[IFR] & (SR_INT | CB1_INT)) via_pmu_interrupt(0, 0, 0); - __restore_flags(ie); + restore_flags(flags); } static void __openfirmware @@ -569,6 +615,7 @@ int intr; int nloop = 0; + ++disable_poll; while ((intr = in_8(&via[IFR])) != 0) { if (++nloop > 1000) { printk(KERN_DEBUG "PMU: stuck in intr loop, " @@ -580,11 +627,9 @@ else if (intr & CB1_INT) { adb_int_pending = 1; out_8(&via[IFR], CB1_INT); - } else - { - /* -- Disabled printk, will happen _really_ often on - PowerBooks ((CB2 interrupts) -- - printk(KERN_DEBUG "PMU: spurrious interrupt intr=%x\n", intr); */ + } + intr &= ~(SR_INT | CB1_INT); + if (intr != 0) { out_8(&via[IFR], intr); } } @@ -597,6 +642,7 @@ pmu_start(); } } + --disable_poll; } static void __openfirmware @@ -605,17 +651,17 @@ struct adb_request *req; int bite, timeout; + if (via[B] & TREQ) { + printk(KERN_ERR "PMU: spurious SR intr (%x)\n", via[B]); + out_8(&via[IFR], SR_INT); + return; + } if (via[B] & TACK) - printk(KERN_DEBUG "PMU: sr_intr but ack still high! (%x)\n", + printk(KERN_ERR "PMU: sr_intr but ack still high! (%x)\n", via[B]); - /* if reading grab the byte, and reset the interrupt */ - if ((via[ACR] & SR_OUT) == 0) - bite = in_8(&via[SR]); - out_8(&via[IFR], SR_INT); - /* reset TREQ and wait for TACK to go high */ - out_8(&via[B], via[B] | TREQ); + out_8(&via[B], in_8(&via[B]) | TREQ); timeout = 3200; while ((in_8(&via[B]) & TACK) == 0) { if (--timeout < 0) { @@ -625,6 +671,11 @@ udelay(10); } + /* if reading grab the byte, and reset the interrupt */ + if (pmu_state == reading || pmu_state == reading_intr) + bite = in_8(&via[SR]); + out_8(&via[IFR], SR_INT); + switch (pmu_state) { case sending: req = current_req; @@ -707,8 +758,6 @@ static void __openfirmware pmu_handle_data(unsigned char *data, int len, struct pt_regs *regs) { - static int show_pmu_ints = 1; - asleep = 0; if (len < 1) { adb_int_pending = 0; @@ -730,21 +779,34 @@ } pmu_done(req); } else { - adb_input(data+1, len-1, regs, 1); +#ifdef CONFIG_XMON + if (len == 4 && data[1] == 0x2c) { + extern int xmon_wants_key, xmon_pmu_keycode; + if (xmon_wants_key) { + xmon_pmu_keycode = data[2]; + return; + } + } +#endif /* CONFIG_XMON */ + /* + * XXX On the [23]400 the PMU gives us an up + * event for keycodes 0x74 or 0x75 when the PC + * card eject buttons are released, so we + * ignore those events. + */ + if (!(pmu_kind == PMU_OHARE_BASED && len == 4 + && data[1] == 0x2c && data[3] == 0xff + && (data[2] & ~1) == 0xf4)) + adb_input(data+1, len-1, regs, 1); } + } else if (data[0] == 0x08 && len == 3) { + /* sound/brightness buttons pressed */ + pmu_set_brightness(data[1] >> 3); + set_volume(data[2]); } else { - if (data[0] == 0x08 && len == 3) { - /* sound/brightness buttons pressed */ - pmu_set_brightness(data[1] >> 3); - set_volume(data[2]); - } else if (show_pmu_ints - && !(data[0] == PMU_INT_TICK && len == 1)) { - int i; - printk(KERN_DEBUG "pmu intr"); - for (i = 0; i < len; ++i) - printk(" %.2x", data[i]); - printk("\n"); - } +#ifdef CONFIG_PMAC_PBOOK + pmu_pass_intr(data, len); +#endif } } @@ -759,38 +821,46 @@ struct adb_request req; if (vias == NULL) - return ; + return; - if (on) { - /* first call: get current backlight value */ - if (backlight_level < 0) { - switch(pmu_kind) { - case PMU_OHARE_BASED: + /* first call: get current backlight value */ + if (on && backlight_level < 0) { + switch (pmu_kind) { + case PMU_OHARE_BASED: pmu_request(&req, NULL, 2, 0xd9, 0); while (!req.complete) pmu_poll(); backlight_level = req.reply[1] >> 3; - printk(KERN_DEBUG "pmu: controls returned bright: %d\n", (int)req.reply[1]); break; - case PMU_HEATHROW_BASED: + case PMU_HEATHROW_BASED: + /* We cannot use nvram_read_byte here (not yet initialized) */ pmu_request(&req, NULL, 3, PMU_READ_NVRAM, 0x14, 0xe); while (!req.complete) pmu_poll(); - printk(KERN_DEBUG "pmu: nvram returned bright: %d\n", (int)req.reply[1]); backlight_level = req.reply[1]; + printk(KERN_DEBUG "pmu: nvram returned bright: %d\n", backlight_level); break; - default: + case PMU_PADDINGTON_BASED: + /* the G3 PB 1999 has a backlight node + and chrp-structured nvram */ + /* XXX should read macos's "blkt" property in nvram + for this node. For now this ensures that the + backlight doesn't go off as soon as linux boots. */ + backlight_level = 20; + break; + default: backlight_enabled = 0; return; } - } - pmu_request(&req, NULL, 2, PMU_BACKLIGHT_BRIGHT, - LEVEL_TO_BRIGHT(backlight_level)); - while (!req.complete) - pmu_poll(); + } + if (on) { + pmu_request(&req, NULL, 2, PMU_BACKLIGHT_BRIGHT, + LEVEL_TO_BRIGHT(backlight_level)); + while (!req.complete) + pmu_poll(); } pmu_request(&req, NULL, 2, PMU_POWER_CTRL, - PMU_POW_BACKLIGHT | (on ? PMU_POW_ON : PMU_POW_OFF)); + PMU_POW_BACKLIGHT | (on ? PMU_POW_ON : PMU_POW_OFF)); while (!req.complete) pmu_poll(); backlight_enabled = on; @@ -847,7 +917,7 @@ { struct adb_request req; - __cli(); + cli(); pmu_request(&req, NULL, 2, PMU_SET_INTR_MASK, PMU_INT_ADB | PMU_INT_TICK ); @@ -866,7 +936,7 @@ { struct adb_request req; - __cli(); + cli(); pmu_request(&req, NULL, 2, PMU_SET_INTR_MASK, PMU_INT_ADB | PMU_INT_TICK ); @@ -881,13 +951,69 @@ ; } +#ifdef CONFIG_PMAC_PBOOK + +static LIST_HEAD(sleep_notifiers); + int -pmu_present(void) +pmu_register_sleep_notifier(struct pmu_sleep_notifier *n) { - return (adb_controller && (adb_controller->kind == ADB_VIAPMU) && vias); + struct list_head *list; + struct pmu_sleep_notifier *current; + + for (list = sleep_notifiers.next; list != &sleep_notifiers; + list = list->next) { + current = list_entry(list, struct pmu_sleep_notifier, list); + if (n->priority > current->priority) + break; + } + __list_add(&n->list, list->prev, list); + return 0; } -#ifdef CONFIG_PMAC_PBOOK +int +pmu_unregister_sleep_notifier(struct pmu_sleep_notifier* n) +{ + if (n->list.next == 0) + return -ENOENT; + list_del(&n->list); + n->list.next = 0; + return 0; +} + +/* Sleep is broadcast last-to-first */ +static int +broadcast_sleep(int when, int can_cancel) +{ + int ret = PBOOK_SLEEP_OK; + struct list_head *list; + struct pmu_sleep_notifier *current; + + for (list = sleep_notifiers.prev; list != &sleep_notifiers; + list = list->prev) { + current = list_entry(list, struct pmu_sleep_notifier, list); + ret = current->notifier_call(current, when); + if (can_cancel && (ret != PBOOK_SLEEP_OK)) + return ret; + } + return ret; +} + +/* Wake is broadcast first-to-last */ +static int +broadcast_wake(void) +{ + int ret = PBOOK_SLEEP_OK; + struct list_head *list; + struct pmu_sleep_notifier *current; + + for (list = sleep_notifiers.next; list != &sleep_notifiers; + list = list->next) { + current = list_entry(list, struct pmu_sleep_notifier, list); + current->notifier_call(current, PBOOK_WAKE); + } + return ret; +} /* * This struct is used to store config register values for @@ -897,10 +1023,11 @@ u16 command; u16 cache_lat; u16 intr; + u32 rom_address; } *pbook_pci_saves; static int n_pbook_pci_saves; -static inline void __openfirmware +static void __openfirmware pbook_pci_save(void) { int npci; @@ -922,12 +1049,13 @@ pci_read_config_word(pd, PCI_COMMAND, &ps->command); pci_read_config_word(pd, PCI_CACHE_LINE_SIZE, &ps->cache_lat); pci_read_config_word(pd, PCI_INTERRUPT_LINE, &ps->intr); + pci_read_config_dword(pd, PCI_ROM_ADDRESS, &ps->rom_address); ++ps; --npci; } } -static inline void __openfirmware +static void __openfirmware pbook_pci_restore(void) { u16 cmd; @@ -948,7 +1076,7 @@ PCI_BASE_ADDRESS_0 + j*4, pd->resource[j].start); pci_write_config_dword(pd, PCI_ROM_ADDRESS, - pd->resource[PCI_ROM_RESOURCE].start); + ps->rom_address); pci_write_config_word(pd, PCI_CACHE_LINE_SIZE, ps->cache_lat); pci_write_config_word(pd, PCI_INTERRUPT_LINE, @@ -963,43 +1091,147 @@ /* * Put the powerbook to sleep. */ -#define IRQ_ENABLE ((unsigned int *)0xf3000024) -#define MEM_CTRL ((unsigned int *)0xf8000070) + +#define FEATURE_CTRL(base) ((unsigned int *)(base + 0x38)) +#define GRACKLE_PM (1<<7) +#define GRACKLE_DOZE (1<<5) +#define GRACKLE_NAP (1<<4) +#define GRACKLE_SLEEP (1<<3) + +int __openfirmware powerbook_sleep_G3(void) +{ + int ret; + unsigned long save_l2cr; + unsigned long save_fcr; + unsigned long wait; + unsigned short pmcr1; + struct adb_request sleep_req; + struct device_node *macio; + unsigned long macio_base = 0; -int __openfirmware powerbook_sleep(void) + macio = find_devices("mac-io"); + if (macio != 0 && macio->n_addrs > 0) + macio_base = (unsigned long) + ioremap(macio->addrs[0].address, 0x40); + + /* Sync the disks. */ + /* XXX It would be nice to have some way to ensure that + * nobody is dirtying any new buffers while we wait. */ + fsync_dev(0); + + /* Notify device drivers */ + ret = broadcast_sleep(PBOOK_SLEEP_REQUEST, 1); + if (ret != PBOOK_SLEEP_OK) { + broadcast_sleep(PBOOK_SLEEP_REJECT, 0); + printk("pmu: sleep rejected\n"); + return -EBUSY; + } + broadcast_sleep(PBOOK_SLEEP_NOW, 0); + + /* Give the disks a little time to actually finish writing */ + for (wait = jiffies + (HZ/4); time_before(jiffies, wait); ) + mb(); + + /* Disable all interrupts except pmu */ + sleep_save_intrs(vias->intrs[0].line); + + /* Make sure the decrementer won't interrupt us */ + asm volatile("mtdec %0" : : "r" (0x7fffffff)); +#if 0 + /* Save the state of PCI config space for some slots */ + pbook_pci_save(); +#endif + /* For 750, save backside cache setting and disable it */ + save_l2cr = _get_L2CR(); /* (returns 0 if not 750) */ + if (save_l2cr) + _set_L2CR(0); + + if (macio_base != 0) { + save_fcr = in_le32(FEATURE_CTRL(macio_base)); + /* Check if this is still valid on older powerbooks */ + out_le32(FEATURE_CTRL(macio_base), save_fcr & ~(0x00000140UL)); + } + + if (current->thread.regs && (current->thread.regs->msr & MSR_FP) != 0) + giveup_fpu(current); + + grackle_pcibios_read_config_word(0,0,0x70,&pmcr1); + /* Apparently, MacOS uses NAP mode for Grackle ??? */ + pmcr1 &= ~(GRACKLE_DOZE|GRACKLE_SLEEP); + pmcr1 |= GRACKLE_PM|GRACKLE_NAP; + grackle_pcibios_write_config_word(0, 0, 0x70, pmcr1); + + /* Ask the PMU to put us to sleep */ + pmu_request(&sleep_req, NULL, 5, PMU_SLEEP, 'M', 'A', 'T', 'T'); + while (!sleep_req.complete) + mb(); + + cli(); + while (pmu_state != idle) + pmu_poll(); + + /* Call low-level ASM sleep handler */ + low_sleep_handler(); + + /* We're awake again, stop grackle PM */ + grackle_pcibios_read_config_word(0, 0, 0x70, &pmcr1); + pmcr1 &= ~(GRACKLE_PM|GRACKLE_DOZE|GRACKLE_SLEEP|GRACKLE_NAP); + grackle_pcibios_write_config_word(0, 0, 0x70, pmcr1); + + sti(); +#if 0 + /* According to someone from Apple, this should not be needed, + at least not for all devices. Let's keep it for now until we + have something that works. */ + pbook_pci_restore(); +#endif + set_context(current->mm->context); + + /* Restore L2 cache */ + if (save_l2cr) + _set_L2CR(save_l2cr | 0x200000); /* set invalidate bit */ + + /* reenable interrupts */ + sleep_restore_intrs(); + + /* Notify drivers */ + broadcast_wake(); + + return 0; +} + +#define PB3400_MEM_CTRL ((unsigned int *)0xf8000070) + +int __openfirmware powerbook_sleep_3400(void) { int ret, i, x; - static int save_backlight; - static unsigned int save_irqen; unsigned long msr; unsigned int hid0; unsigned long p, wait; struct adb_request sleep_req; - /* Notify device drivers */ - ret = notifier_call_chain(&sleep_notifier_list, PBOOK_SLEEP, NULL); - if (ret & NOTIFY_STOP_MASK) - return -EBUSY; - /* Sync the disks. */ /* XXX It would be nice to have some way to ensure that * nobody is dirtying any new buffers while we wait. */ fsync_dev(0); - /* Turn off the display backlight */ - save_backlight = backlight_enabled; - if (save_backlight) - pmu_enable_backlight(0); + /* Notify device drivers */ + ret = broadcast_sleep(PBOOK_SLEEP_REQUEST, 1); + if (ret != PBOOK_SLEEP_OK) { + broadcast_sleep(PBOOK_SLEEP_REJECT, 0); + printk("pmu: sleep rejected\n"); + return -EBUSY; + } + broadcast_sleep(PBOOK_SLEEP_NOW, 0); /* Give the disks a little time to actually finish writing */ for (wait = jiffies + (HZ/4); time_before(jiffies, wait); ) mb(); /* Disable all interrupts except pmu */ - save_irqen = in_le32(IRQ_ENABLE); - for (i = 0; i < 32; ++i) - if (i != vias->intrs[0].line && (save_irqen & (1 << i))) - disable_irq(i); + sleep_save_intrs(vias->intrs[0].line); + + /* Make sure the decrementer won't interrupt us */ asm volatile("mtdec %0" : : "r" (0x7fffffff)); /* Save the state of PCI config space for some slots */ @@ -1008,9 +1240,9 @@ /* Set the memory controller to keep the memory refreshed while we're asleep */ for (i = 0x403f; i >= 0x4000; --i) { - out_be32(MEM_CTRL, i); + out_be32(PB3400_MEM_CTRL, i); do { - x = (in_be32(MEM_CTRL) >> 16) & 0x3ff; + x = (in_be32(PB3400_MEM_CTRL) >> 16) & 0x3ff; } while (x == 0); if (x >= 0x100) break; @@ -1020,6 +1252,7 @@ pmu_request(&sleep_req, NULL, 5, PMU_SLEEP, 'M', 'A', 'T', 'T'); while (!sleep_req.complete) mb(); + /* displacement-flush the L2 cache - necessary? */ for (p = KERNELBASE; p < KERNELBASE + 0x100000; p += 0x1000) i = *(volatile int *)p; @@ -1035,7 +1268,7 @@ udelay(10); /* OK, we're awake again, start restoring things */ - out_be32(MEM_CTRL, 0x3f); + out_be32(PB3400_MEM_CTRL, 0x3f); pbook_pci_restore(); /* wait for the PMU interrupt sequence to complete */ @@ -1043,21 +1276,10 @@ mb(); /* reenable interrupts */ - for (i = 0; i < 32; ++i) - if (i != vias->intrs[0].line && (save_irqen & (1 << i))) - enable_irq(i); + sleep_restore_intrs(); /* Notify drivers */ - notifier_call_chain(&sleep_notifier_list, PBOOK_WAKE, NULL); - - /* reenable ADB autopoll */ - pmu_adb_autopoll(adb_dev_map); - - /* Turn on the screen backlight, if it was on before */ - if (save_backlight) - pmu_enable_backlight(1); - - /* Wait for the hard disk to spin up */ + broadcast_wake(); return 0; } @@ -1065,15 +1287,112 @@ /* * Support for /dev/pmu device */ +#define RB_SIZE 10 +struct pmu_private { + struct list_head list; + int rb_get; + int rb_put; + struct rb_entry { + unsigned short len; + unsigned char data[16]; + } rb_buf[RB_SIZE]; + wait_queue_head_t wait; + spinlock_t lock; +}; + +static LIST_HEAD(all_pmu_pvt); +static spinlock_t all_pvt_lock = SPIN_LOCK_UNLOCKED; + +static void pmu_pass_intr(unsigned char *data, int len) +{ + struct pmu_private *pp; + struct list_head *list; + int i; + unsigned long flags; + + if (len > sizeof(pp->rb_buf[0].data)) + len = sizeof(pp->rb_buf[0].data); + spin_lock_irqsave(&all_pvt_lock, flags); + for (list = &all_pmu_pvt; (list = list->next) != &all_pmu_pvt; ) { + pp = list_entry(list, struct pmu_private, list); + i = pp->rb_put + 1; + if (i >= RB_SIZE) + i = 0; + if (i != pp->rb_get) { + struct rb_entry *rp = &pp->rb_buf[pp->rb_put]; + rp->len = len; + memcpy(rp->data, data, len); + pp->rb_put = i; + wake_up_interruptible(&pp->wait); + } + } + spin_unlock_irqrestore(&all_pvt_lock, flags); +} + static int __openfirmware pmu_open(struct inode *inode, struct file *file) { + struct pmu_private *pp; + unsigned long flags; + + pp = kmalloc(sizeof(struct pmu_private), GFP_KERNEL); + if (pp == 0) + return -ENOMEM; + pp->rb_get = pp->rb_put = 0; + spin_lock_init(&pp->lock); + init_waitqueue_head(&pp->wait); + spin_lock_irqsave(&all_pvt_lock, flags); + list_add(&pp->list, &all_pmu_pvt); + spin_unlock_irqrestore(&all_pvt_lock, flags); + file->private_data = pp; return 0; } static ssize_t __openfirmware pmu_read(struct file *file, char *buf, size_t count, loff_t *ppos) { - return 0; + struct pmu_private *pp = file->private_data; + DECLARE_WAITQUEUE(wait, current); + int ret; + + if (count < 1 || pp == 0) + return -EINVAL; + ret = verify_area(VERIFY_WRITE, buf, count); + if (ret) + return ret; + + add_wait_queue(&pp->wait, &wait); + current->state = TASK_INTERRUPTIBLE; + + for (;;) { + ret = -EAGAIN; + spin_lock(&pp->lock); + if (pp->rb_get != pp->rb_put) { + int i = pp->rb_get; + struct rb_entry *rp = &pp->rb_buf[i]; + ret = rp->len; + if (ret > count) + ret = count; + if (ret > 0 && copy_to_user(buf, rp->data, ret)) + ret = -EFAULT; + if (++i >= RB_SIZE) + i = 0; + pp->rb_get = i; + } + spin_unlock(&pp->lock); + if (ret >= 0) + break; + + if (file->f_flags & O_NONBLOCK) + break; + ret = -ERESTARTSYS; + if (signal_pending(current)) + break; + schedule(); + } + current->state = TASK_RUNNING; + remove_wait_queue(&pp->wait, &wait); + + return ret; } static ssize_t __openfirmware pmu_write(struct file *file, const char *buf, @@ -1082,26 +1401,65 @@ return 0; } +static unsigned int pmu_fpoll(struct file *filp, poll_table *wait) +{ + struct pmu_private *pp = filp->private_data; + unsigned int mask = 0; + + if (pp == 0) + return 0; + poll_wait(filp, &pp->wait, wait); + spin_lock(&pp->lock); + if (pp->rb_get != pp->rb_put) + mask |= POLLIN; + spin_unlock(&pp->lock); + return mask; +} + +static int pmu_release(struct inode *inode, struct file *file) +{ + struct pmu_private *pp = file->private_data; + unsigned long flags; + + if (pp != 0) { + file->private_data = 0; + spin_lock_irqsave(&all_pvt_lock, flags); + list_del(&pp->list); + spin_unlock_irqrestore(&all_pvt_lock, flags); + kfree(pp); + } + return 0; +} + /* Note: removed __openfirmware here since it causes link errors */ -static int /*__openfirmware*/ pmu_ioctl(struct inode * inode, struct file *filp, +static int pmu_ioctl(struct inode * inode, struct file *filp, u_int cmd, u_long arg) { int error; __u32 value; switch (cmd) { - case PMU_IOC_SLEEP: - if (pmu_kind != PMU_OHARE_BASED) - return -ENOSYS; - return powerbook_sleep(); - case PMU_IOC_GET_BACKLIGHT: + case PMU_IOC_SLEEP: + switch (pmu_kind) { + case PMU_OHARE_BASED: + error = powerbook_sleep_3400(); + break; + case PMU_HEATHROW_BASED: + case PMU_PADDINGTON_BASED: + error = powerbook_sleep_G3(); + break; + default: + error = ENOSYS; + } + return error; + case PMU_IOC_GET_BACKLIGHT: return put_user(backlight_level, (__u32 *)arg); - case PMU_IOC_SET_BACKLIGHT: + case PMU_IOC_SET_BACKLIGHT: error = get_user(value, (__u32 *)arg); if (!error) pmu_set_brightness(value); return error; - case PMU_IOC_GET_MODEL: + case PMU_IOC_GET_MODEL: return put_user(pmu_kind, (__u32 *)arg); } return -EINVAL; @@ -1112,12 +1470,12 @@ pmu_read, pmu_write, NULL, /* no readdir */ - NULL, /* no poll yet */ + pmu_fpoll, pmu_ioctl, NULL, /* no mmap */ pmu_open, NULL, /* flush */ - NULL /* no release */ + pmu_release, }; static struct miscdevice pmu_device = { diff -u --recursive --new-file v2.3.19/linux/drivers/misc/Config.in linux/drivers/misc/Config.in --- v2.3.19/linux/drivers/misc/Config.in Mon Oct 4 15:49:29 1999 +++ linux/drivers/misc/Config.in Thu Oct 7 10:17:09 1999 @@ -4,13 +4,6 @@ mainmenu_option next_comment comment 'Misc devices' -if [ "$CONFIG_EXPERIMENTAL" = "y" ]; then - tristate 'Generic ACPI support' CONFIG_ACPI -fi - -# PIIX4 ACPI requires PCI for setup and a hardcoded TSC for timing -if [ "$CONFIG_PCI" = "y" -a "$CONFIG_X86_TSC" = "y" -a "$CONFIG_EXPERIMENTAL" = "y" ]; then - bool 'PIIX4 ACPI support' CONFIG_PIIX4_ACPI -fi +tristate 'Generic ACPI support' CONFIG_ACPI endmenu diff -u --recursive --new-file v2.3.19/linux/drivers/misc/Makefile linux/drivers/misc/Makefile --- v2.3.19/linux/drivers/misc/Makefile Mon Oct 4 15:49:29 1999 +++ linux/drivers/misc/Makefile Thu Oct 7 10:17:09 1999 @@ -26,10 +26,6 @@ endif endif -ifdef CONFIG_PIIX4_ACPI -O_OBJS += piix4_acpi.o -endif - include $(TOPDIR)/Rules.make fastdep: diff -u --recursive --new-file v2.3.19/linux/drivers/misc/acpi.c linux/drivers/misc/acpi.c --- v2.3.19/linux/drivers/misc/acpi.c Mon Oct 4 15:49:29 1999 +++ linux/drivers/misc/acpi.c Fri Oct 8 13:36:46 1999 @@ -18,6 +18,11 @@ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ +/* + * See http://www.geocities.com/SiliconValley/Hardware/3165/ + * for the user-level ACPI stuff + */ + #include #include #include @@ -46,6 +51,10 @@ static struct acpi_facp *acpi_facp = NULL; static unsigned long acpi_facp_addr = 0; static unsigned long acpi_dsdt_addr = 0; + +static volatile u32 acpi_pm1_status = 0; +static volatile u32 acpi_gpe_status = 0; +static volatile u32 acpi_gpe_level = 0; static DECLARE_WAIT_QUEUE_HEAD(acpi_wait_event); /* @@ -73,6 +82,19 @@ } /* + * Get the value of the fixed event enable register + */ +static u32 acpi_read_pm1_enable(struct acpi_facp *facp) +{ + int offset = facp->pm1_evt_len >> 1; + u32 value = inw(facp->pm1a_evt + offset); + if (facp->pm1b_evt) { + value |= inw(facp->pm1b_evt + offset); + } + return value; +} + +/* * Set the value of the fixed event enable register (enable events) */ static void acpi_write_pm1_enable(struct acpi_facp *facp, u32 value) @@ -128,6 +150,28 @@ } /* + * Get the value of the general-purpose event enable register + */ +static u32 acpi_read_gpe_enable(struct acpi_facp *facp) +{ + u32 value = 0; + int i, size, offset; + + offset = facp->gpe0_len >> 1; + if (facp->gpe1) { + size = facp->gpe1_len >> 1; + for (i = size - 1; i >= 0; i--) { + value = (value << 8) | inb(facp->gpe1 + offset + i); + } + } + size = facp->gpe0_len >> 1; + for (i = size - 1; i >= 0; i--) { + value = (value << 8) | inb(facp->gpe0 + offset + i); + } + return value; +} + +/* * Set the value of the general-purpose event enable register (enable events) */ static void acpi_write_gpe_enable(struct acpi_facp *facp, u32 value) @@ -157,7 +201,8 @@ if (addr) { // map table header to determine size table = (struct acpi_table *) - ioremap_nocache((unsigned long) addr, sizeof(struct acpi_table)); + ioremap_nocache((unsigned long) addr, + sizeof(struct acpi_table)); if (table) { unsigned long table_size = table->length; iounmap(table); @@ -201,10 +246,13 @@ // strip trailing space and print OEM identifier memcpy_fromio(oem, rsdp->oem, 6); oem[6] = '\0'; - for (j = 5; j > 0 && (oem[j] == '\0' || oem[j] == ' '); j--) { + for (j = 5; + j > 0 && (oem[j] == '\0' || oem[j] == ' '); + j--) { oem[j] = '\0'; } - printk(KERN_INFO "ACPI: \"%s\" found at 0x%p\n", oem, (void *) i); + printk(KERN_INFO "ACPI: \"%s\" found at 0x%p\n", + oem, (void *) i); break; } @@ -252,6 +300,7 @@ */ static void acpi_unmap_tables(void) { + acpi_idle = NULL; acpi_dsdt_addr = 0; acpi_facp_addr = 0; acpi_unmap_table((struct acpi_table *) acpi_facp); @@ -263,17 +312,32 @@ */ static void acpi_irq(int irq, void *dev_id, struct pt_regs *regs) { - u32 status; - - // detect and disable any fixed events - status = acpi_read_pm1_status(acpi_facp); - acpi_write_pm1_enable(acpi_facp, ~status); - - // detect and disable any general-purpose events - status = acpi_read_gpe_status(acpi_facp); - acpi_write_gpe_enable(acpi_facp, ~status); - + u32 pm1_status, gpe_status, gpe_level, gpe_edge; + // detect and clear fixed events + pm1_status = (acpi_read_pm1_status(acpi_facp) + & acpi_read_pm1_enable(acpi_facp)); + acpi_write_pm1_status(acpi_facp, pm1_status); + + // detect and handle general-purpose events + gpe_status = (acpi_read_gpe_status(acpi_facp) + & acpi_read_gpe_enable(acpi_facp)); + gpe_level = gpe_status & acpi_gpe_level; + if (gpe_level) { + // disable level-triggered events + acpi_write_gpe_enable( + acpi_facp, + acpi_read_gpe_enable(acpi_facp) & ~gpe_level); + } + gpe_edge = gpe_status & ~gpe_level; + if (gpe_edge) { + // clear edge-triggered events + while (acpi_read_gpe_status(acpi_facp) & gpe_edge) + acpi_write_gpe_status(acpi_facp, gpe_edge); + } + // notify process reading /dev/acpi + acpi_pm1_status |= pm1_status; + acpi_gpe_status |= gpe_status; wake_up_interruptible(&acpi_wait_event); } @@ -311,17 +375,79 @@ (void *) arg, sizeof(struct acpi_find_tables)); if (!status) { - struct acpi_find_tables *rqst = (struct acpi_find_tables *) arg; + struct acpi_find_tables *rqst + = (struct acpi_find_tables *) arg; put_user(acpi_facp_addr, &rqst->facp); put_user(acpi_dsdt_addr, &rqst->dsdt); status = 0; } break; + case ACPI_ENABLE_EVENT: + status = verify_area(VERIFY_READ, + (void *) arg, + sizeof(struct acpi_enable_event)); + if (!status) { + struct acpi_enable_event *rqst + = (struct acpi_enable_event *) arg; + u32 pm1_enable, gpe_enable, gpe_level; + u32 pm1_enabling, gpe_enabling; + + get_user(pm1_enable, &rqst->pm1_enable); + get_user(gpe_enable, &rqst->gpe_enable); + get_user(gpe_level, &rqst->gpe_level); + gpe_level &= gpe_enable; + + // clear previously disabled events before enabling + pm1_enabling = (pm1_enable + & ~acpi_read_pm1_enable(acpi_facp)); + acpi_write_pm1_status(acpi_facp, pm1_enabling); + gpe_enabling = (gpe_enable & + ~acpi_read_gpe_enable(acpi_facp)); + while (acpi_read_gpe_status(acpi_facp) & gpe_enabling) + acpi_write_gpe_status(acpi_facp, gpe_enabling); + + acpi_write_pm1_enable(acpi_facp, pm1_enable); + acpi_write_gpe_enable(acpi_facp, gpe_enable); + acpi_gpe_level = gpe_level; + + status = 0; + } + break; case ACPI_WAIT_EVENT: - interruptible_sleep_on(&acpi_wait_event); - if (signal_pending(current)) - return -ERESTARTSYS; - status = 0; + status = verify_area(VERIFY_WRITE, + (void *) arg, + sizeof(struct acpi_wait_event)); + if (!status) { + struct acpi_wait_event *rqst + = (struct acpi_wait_event *) arg; + u32 pm1_status = 0; + u32 gpe_status = 0; + + for (;;) { + unsigned long flags; + + // we need an atomic exchange here + save_flags(flags); + cli(); + pm1_status = acpi_pm1_status; + acpi_pm1_status = 0; + gpe_status = acpi_gpe_status; + acpi_gpe_status = 0; + restore_flags(flags); + + if (pm1_status || gpe_status) + break; + + // wait for an event to arrive + interruptible_sleep_on(&acpi_wait_event); + if (signal_pending(current)) + return -ERESTARTSYS; + } + + put_user(pm1_status, &rqst->pm1_status); + put_user(gpe_status, &rqst->gpe_status); + status = 0; + } break; } return status; @@ -355,6 +481,48 @@ NULL }; +/* Make it impossible to enter L2/L3 until after we've initialized */ +static unsigned long acpi_p_lvl2_lat = ~0UL; +static unsigned long acpi_p_lvl3_lat = ~0UL; + +/* Initialize to guaranteed harmless port read */ +static u16 acpi_p_lvl2 = 0x80; +static u16 acpi_p_lvl3 = 0x80; + +static void acpi_idle_handler(void) +{ + unsigned long time; + static int sleep_level = 1; + + time = inl(acpi_facp->pm_tmr); + switch (sleep_level) { + case 1: + __asm__ __volatile__("sti ; hlt": : :"memory"); + break; + case 2: + inb(acpi_p_lvl2); + break; + case 3: + /* Disable PCI arbitration while sleeping, to avoid DMA corruption? */ + if (acpi_facp->pm2_cnt) { + unsigned int port = acpi_facp->pm2_cnt; + outb(inb(port) | ACPI_ARB_DIS, port); + inb(acpi_p_lvl3); + outb(inb(port) & ~ACPI_ARB_DIS, port); + break; + } + inb(acpi_p_lvl3); + } + time = (inl(acpi_facp->pm_tmr) - time) & ACPI_TMR_MASK; + + if (time > acpi_p_lvl3_lat) + sleep_level = 3; + else if (time > acpi_p_lvl2_lat) + sleep_level = 2; + else + sleep_level = 1; +} + /* * Initialize and enable ACPI */ @@ -376,6 +544,17 @@ if (misc_register(&acpi_device)) { printk(KERN_ERR "ACPI: misc. register failed\n"); } + + /* + * Set up the ACPI idle function. Note that we can't really + * do this with multiple CPU's, we'd need a per-CPU ACPI + * device.. + */ +#ifdef __SMP__ + if (smp_num_cpus > 1) + return 0; +#endif + acpi_idle = acpi_idle_handler; return 0; } @@ -389,7 +568,8 @@ // disable and clear any pending events acpi_write_gpe_enable(acpi_facp, 0); while (acpi_read_gpe_status(acpi_facp)) { - acpi_write_gpe_status(acpi_facp, acpi_read_gpe_status(acpi_facp)); + acpi_write_gpe_status(acpi_facp, + acpi_read_gpe_status(acpi_facp)); } acpi_write_pm1_enable(acpi_facp, 0); acpi_write_pm1_status(acpi_facp, acpi_read_pm1_status(acpi_facp)); @@ -405,6 +585,7 @@ module_init(acpi_init) module_exit(acpi_exit) + #else __initcall(acpi_init); diff -u --recursive --new-file v2.3.19/linux/drivers/misc/piix4_acpi.c linux/drivers/misc/piix4_acpi.c --- v2.3.19/linux/drivers/misc/piix4_acpi.c Fri Aug 13 13:50:58 1999 +++ linux/drivers/misc/piix4_acpi.c Wed Dec 31 16:00:00 1969 @@ -1,214 +0,0 @@ -/* - * linux/drivers/misc/piix4_acpi.c - * - * (C) Copyright 1999 Linus Torvalds - * - * A PM driver for the ACPI portion of the Intel PIIX4 - * chip. - * - * This has been known to occasionally work on some laptops. - * - * It probably only works on Intel PII machines that support - * the STPCLK protocol. - */ - -#include -#include -#include - -#include - -extern void (*acpi_idle)(void); - -/* - * This first part should be common to all ACPI - * CPU sleep functionality. Assuming we get the - * timing heuristics in a better shape than "none" ;) - */ - -typedef void (*sleep_fn_t)(void); - -/* - * Our "sleep mode" is a fixed point number - * with two binary places, ranging between - * [0 .. 3[ - */ -#define Cx_SHIFT 2 -#define MAXMODE ((3 << Cx_SHIFT)-1) - -/* - * NOTE! - * - * Right now this always defaults to C3, which is just broken. - * The exit latency is usually too high for much busy IO activity, - * and generally it's not always the best thing to do. - * - * We should just read the cycle counter around all the cases, - * and if we pause for a long time we go to a deeper sleep, while - * a short wait makes us go into a lighter sleep. - */ -static void common_acpi_idle(sleep_fn_t *sleep) -{ - int mode = MAXMODE; - - while (1) { - while (!current->need_resched) { - unsigned int time; - - time = get_cycles(); - sleep[(mode) >> Cx_SHIFT](); - time = get_cycles() - time; - - /* - * Yeah, yeah, yeah. - * if (time > Large && mode < MAXMODE) mode++; - * if (time < Small && mode > 0) mode--; - * Yadda-yadda-yadda. - * - * "Large" is on the order of half a timer tick. - * "Small" is on the order of Large >> 2 or so. - * - * Somebody should _really_ look at the exact - * details. The ACPI bios would give some made-up - * numbers, they might be useful (or maybe not: - * they are probably tuned for whatever Windows - * does, so don't take them for granted). - */ - } - schedule(); - check_pgt_cache(); - } -} - -/* Ok, here starts the magic PIIX4 knowledge */ - -/* - * Ehh.. We "know" about the northbridge - * bus arbitration stuff. Maybe somebody - * should actually verify this some day? - */ -#define NORTHBRIDGE_CONTROL 0x22 -#define NB_ARBITRATE 0x01 - -/* - * PIIX4 ACPI IO offsets and defines - */ -#define PMEN 0x02 -#define PMCNTRL 0x04 -#define PMTMR 0x08 -#define GPSTS 0x0c -#define GPEN 0x0E - -#define PCNTRL 0x10 -#define CC_EN 0x0200 -#define BST_EN 0x0400 -#define SLEEP_EN 0x0800 -#define STPCLK_EN 0x1000 -#define CLKRUN_EN 0x2000 - -#define PLVL2 0x14 -#define PLVL3 0x15 - -/* - * PIIX4 ACPI PCI configurations offsets and defines - */ -#define DEVACTB 0x58 -#define BRLD_EN_IRQ0 0x01 -#define BRLD_EN_IRQ 0x02 - -#define PMREGMISC 0x80 -#define PMIOSE 0x01 - -static unsigned int piix4_base_address = 0; - -static void piix4_c1_sleep(void) -{ - asm volatile("sti ; hlt" : : : "memory"); -} - -static void piix4_c2_sleep(void) -{ - outl(CLKRUN_EN | CC_EN, piix4_base_address + PCNTRL); - inb(piix4_base_address + PLVL2); -} - -static void piix4_c3_sleep(void) -{ - __cli(); - outl(CLKRUN_EN | CC_EN | STPCLK_EN | SLEEP_EN, piix4_base_address + PCNTRL); - outb(NB_ARBITRATE, NORTHBRIDGE_CONTROL); - inb(piix4_base_address + PLVL3); - outb(0, NORTHBRIDGE_CONTROL); - __sti(); -} - -static sleep_fn_t piix4_sleep[] = { - piix4_c1_sleep, /* low-latency C1 (ie "sti ; hlt") */ - piix4_c2_sleep, /* medium latency C2 (ie LVL2 stopckl) */ - piix4_c3_sleep /* high-latency C3 (ie LVL3 sleep) */ -}; - -static void piix4_acpi_idle(void) -{ - common_acpi_idle(piix4_sleep); -} - -static int __init piix4_acpi_init(void) -{ - /* This is the PIIX4 ACPI device */ - struct pci_dev *dev; - u32 base, val; - u16 cmd; - u8 pmregmisc; - -#ifdef __SMP__ - /* - * We can't really do idle things with multiple CPU's, I'm - * afraid. We'd need a per-CPU ACPI device. - */ - if (smp_num_cpus > 1) - return -1; -#endif - dev = pci_find_device(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_82371AB_3, NULL); - - if (!dev) - return -1; - - /* - * Read the IO base value, and verify that it makes sense - * - * We could enable this if it wasn't enabled before, but - * let's walk before we run.. - */ - pci_read_config_word(dev, PCI_COMMAND, &cmd); - if (!(cmd & PCI_COMMAND_IO)) - return -1; - - pci_read_config_byte(dev, PMREGMISC, &pmregmisc); - if (!(pmregmisc & PMIOSE)) - return -1; - - pci_read_config_dword(dev, 0x40, &base); - if (!(base & PCI_BASE_ADDRESS_SPACE_IO)) - return -1; - - base &= PCI_BASE_ADDRESS_IO_MASK; - if (!base) - return -1; - - printk("Found PIIX4 ACPI device at %04x\n", base); - piix4_base_address = base; - - /* Enable stopcklock, sleep and bursts, along with clock control */ - outl(CLKRUN_EN | CC_EN | STPCLK_EN | SLEEP_EN, piix4_base_address + PCNTRL); - - /* Make all unmasked interrupts be BREAK events */ - pci_read_config_dword(dev, DEVACTB, &val); - pci_write_config_dword(dev, DEVACTB, val | BRLD_EN_IRQ0 | BRLD_EN_IRQ); - - /* Set up the new idle handler.. */ - acpi_idle = piix4_acpi_idle; - return 0; -} - -__initcall(piix4_acpi_init); diff -u --recursive --new-file v2.3.19/linux/drivers/net/pcmcia/ray_cs.c linux/drivers/net/pcmcia/ray_cs.c --- v2.3.19/linux/drivers/net/pcmcia/ray_cs.c Mon Oct 4 15:49:29 1999 +++ linux/drivers/net/pcmcia/ray_cs.c Thu Oct 7 11:50:26 1999 @@ -57,21 +57,17 @@ left out. If you compile with PCMCIA_DEBUG=0, the debug code will be present but disabled -- but it can then be enabled for specific modules at load time with a 'pc_debug=#' option to insmod. - - I found that adding -DPCMCIA_DEBUG to the compile options during - the 'make config' resulted in cardmgr not finding any sockets. - Therefore, this module uses RAYLINK_DEBUG instead. - The module option to use is ray_debug=# - where # is 1 for modest output - 2 for more output - ... */ #ifdef RAYLINK_DEBUG -static int ray_debug = RAYLINK_DEBUG; -MODULE_PARM(ray_debug, "i"); -/* #define DEBUG(n, args...) if (ray_debug>(n)) printk(KERN_DEBUG args); */ -#define DEBUG(n, args...) if (ray_debug>(n)) printk(args); +#define PCMCIA_DEBUG RAYLINK_DEBUG +#endif +#ifdef PCMCIA_DEBUG +static int ray_debug = 0; +static int pc_debug = PCMCIA_DEBUG; +MODULE_PARM(pc_debug, "i"); +/* #define DEBUG(n, args...) if (pc_debug>(n)) printk(KERN_DEBUG args); */ +#define DEBUG(n, args...) if (pc_debug>(n)) printk(args); #else #define DEBUG(n, args...) #endif @@ -137,7 +133,6 @@ /* void start_net(ray_dev_t *local); */ int ray_cs_proc_read(char *buf, char **start, off_t off, int len, int spare); - /* Create symbol table for registering with kernel in init_module */ EXPORT_SYMBOL(ray_dev_ioctl); EXPORT_SYMBOL(ray_rx); @@ -147,40 +142,30 @@ /* Bit map of interrupts to choose from */ /* This means pick from 15, 14, 12, 11, 10, 9, 7, 5, 4, and 3 */ static u_long irq_mask = 0xdeb8; -MODULE_PARM(irq_mask,"i"); /* ADHOC=0, Infrastructure=1 */ static int net_type = ADHOC; -MODULE_PARM(net_type,"i"); /* Hop dwell time in Kus (1024 us units defined by 802.11) */ static int hop_dwell = 128; -MODULE_PARM(hop_dwell,"i"); /* Beacon period in Kus */ static int beacon_period = 256; -MODULE_PARM(beacon_period,"i"); /* power save mode (0 = off, 1 = save power) */ static int psm = 0; -MODULE_PARM(psm,"i"); /* String for network's Extended Service Set ID. 32 Characters max */ static char *essid = NULL; -MODULE_PARM(essid,"s"); /* Default to encapsulation unless translation requested */ static int translate = 1; -MODULE_PARM(translate,"i"); static int country = USA; -MODULE_PARM(country,"i"); static int sniffer = 0; -MODULE_PARM(sniffer,"i"); static int bc = 0; -MODULE_PARM(bc,"i"); /* 48 bit physical card address if overriding card's real physical * address is required. Since IEEE 802.11 addresses are 48 bits @@ -193,7 +178,6 @@ * things will happen if it is not 0 in a card address. */ static char *phy_addr = NULL; -MODULE_PARM(phy_addr,"s"); /* The dev_info variable is the "key" that is used to match up this @@ -214,7 +198,22 @@ 'priv' pointer in a dev_link_t structure can be used to point to a device-specific private data structure, like this. */ -static const unsigned int ray_mem_speed = 0x2A; +static unsigned int ray_mem_speed = 0x2A; + +MODULE_AUTHOR("Corey Thomas "); +MODULE_DESCRIPTION("Raylink/WebGear wireless LAN driver"); +MODULE_PARM(irq_mask,"i"); +MODULE_PARM(net_type,"i"); +MODULE_PARM(hop_dwell,"i"); +MODULE_PARM(beacon_period,"i"); +MODULE_PARM(psm,"i"); +MODULE_PARM(essid,"s"); +MODULE_PARM(translate,"i"); +MODULE_PARM(country,"i"); +MODULE_PARM(sniffer,"i"); +MODULE_PARM(bc,"i"); +MODULE_PARM(phy_addr,"s"); +MODULE_PARM(ray_mem_speed, "i"); static UCHAR b5_default_startup_parms[] = { 0, 0, /* Adhoc station */ @@ -284,7 +283,7 @@ /*===========================================================================*/ static unsigned char eth2_llc[] = {0xaa, 0xaa, 3, 0, 0, 0}; -static char rcsid[] = " $Id: ray_cs.c,v 1.60 1999/09/01 20:58:45 corey Exp $ - Corey Thomas corey@world.std.com"; +static char rcsid[] = "Raylink/WebGear wireless LAN - Corey "; #ifdef CONFIG_PROC_FS struct proc_dir_entry ray_cs_proc_entry = { @@ -358,7 +357,7 @@ local->finder = link; link->dev = &local->node; local->card_status = CARD_INSERTED; - local->authentication_state = UNAUTHENTICATED; + local->authentication_state = UNAUTHENTICATED; local->num_multi = 0; DEBUG(2,"ray_attach link = %p, dev = %p, local = %p, intr = %p\n", link,dev,local,&ray_interrupt); @@ -442,8 +441,6 @@ if (link->state & DEV_CONFIG) { ray_release((u_long)link); if(link->state & DEV_STALE_CONFIG) { - DEBUG(0,"ray_cs: detach postponed, '%s' " - "still locked\n", link->dev->dev_name); link->state |= DEV_STALE_LINK; return; } @@ -472,7 +469,7 @@ =============================================================================*/ #define CS_CHECK(fn, args...) \ while ((last_ret=CardServices(last_fn=(fn),args))!=0) goto cs_failed -#define MAX_TUPLE_SIZE 80 +#define MAX_TUPLE_SIZE 128 void ray_config(dev_link_t *link) { client_handle_t handle = link->handle; @@ -480,7 +477,7 @@ cisparse_t parse; int last_fn, last_ret; int i; - u_char buf[80]; + u_char buf[MAX_TUPLE_SIZE]; win_req_t req; memreq_t mem; struct net_device *dev = (struct net_device *)link->priv; @@ -499,6 +496,19 @@ link->conf.ConfigBase = parse.config.base; link->conf.Present = parse.config.rmask[0]; + /* Determine card type and firmware version */ + buf[0] = buf[MAX_TUPLE_SIZE - 1] = 0; + tuple.DesiredTuple = CISTPL_VERS_1; + CS_CHECK(GetFirstTuple, handle, &tuple); + tuple.TupleData = buf; + tuple.TupleDataMax = MAX_TUPLE_SIZE; + tuple.TupleOffset = 2; + CS_CHECK(GetTupleData, handle, &tuple); + + for (i=0; istate |= DEV_CONFIG; @@ -562,7 +572,10 @@ } link->state &= ~DEV_CONFIG_PENDING; - DEBUG(0, "ray_cs device loaded\n"); + printk(KERN_INFO "%s: RayLink, irq %d, hw_addr ", + dev->name, dev->irq); + for (i = 0; i < 6; i++) + printk("%02X%s", dev->dev_addr[i], ((i<5) ? ":" : "\n")); return; @@ -594,7 +607,8 @@ /* Check Power up test status and get mac address from card */ if (local->startup_res.startup_word != 0x80) { -DEBUG(0,"ray_init ERROR card status = %2x\n", local->startup_res.startup_word); + printk(KERN_INFO "ray_init ERROR card status = %2x\n", + local->startup_res.startup_word); local->card_status = CARD_INIT_ERROR; return -1; } @@ -619,16 +633,12 @@ if (parse_addr(phy_addr, local->sparm.b4.a_mac_addr)) { p = local->sparm.b4.a_mac_addr; - DEBUG(1,"ray_cs phy address overridden = %2x %2x %2x %2x %2x %2x\n",\ - p[0],p[1],p[2],p[3],p[4],p[5]); } else { memcpy(&local->sparm.b4.a_mac_addr, &local->startup_res.station_addr, ADDRLEN); p = local->sparm.b4.a_mac_addr; - DEBUG(1,"ray_cs phy addr= %2x %2x %2x %2x %2x %2x\n",\ - p[0],p[1],p[2],p[3],p[4],p[5]); } clear_interrupt(local); /* Clear any interrupt from the card */ @@ -647,7 +657,7 @@ DEBUG(1,"dl_startup_params entered\n"); if (!(link->state & DEV_PRESENT)) { - DEBUG(0,"ray_cs dl_startup_params - device not present\n"); + DEBUG(2,"ray_cs dl_startup_params - device not present\n"); return -1; } @@ -661,14 +671,15 @@ /* Fill in the CCS fields for the ECF */ - if ((ccsindex = get_free_ccs(local)) == -1) return -1; + if ((ccsindex = get_free_ccs(local)) < 0) return -1; local->dl_param_ccs = ccsindex; pccs = ((struct ccs *)(local->sram + CCS_BASE)) + ccsindex; writeb(CCS_DOWNLOAD_STARTUP_PARAMS, &pccs->cmd); DEBUG(2,"dl_startup_params start ccsindex = %d\n", local->dl_param_ccs); /* Interrupt the firmware to process the command */ if (interrupt_ecf(local, ccsindex)) { - DEBUG(0,"ray dl_startup_params failed - ECF not ready for intr\n"); + printk(KERN_INFO "ray dl_startup_params failed - " + "ECF not ready for intr\n"); local->card_status = CARD_DL_PARAM_ERROR; writeb(CCS_BUFFER_FREE, &(pccs++)->buffer_status); return -2; @@ -723,11 +734,11 @@ local->sparm.b4.a_curr_country_code = country; local->sparm.b4.a_hop_pattern_length = hop_pattern_length[(int)country] - 1; - if (bc) - { - local->sparm.b4.a_ack_timeout = 0x50; - local->sparm.b4.a_sifs = 0x3f; - } + if (bc) + { + local->sparm.b4.a_ack_timeout = 0x50; + local->sparm.b4.a_sifs = 0x3f; + } } else { /* Version 5 uses real kus values */ memcpy((UCHAR *)&local->sparm.b5, b5_default_startup_parms, @@ -756,30 +767,29 @@ ray_dev_t *local = (ray_dev_t *)data; struct ccs *pccs = ((struct ccs *)(local->sram + CCS_BASE)) + local->dl_param_ccs; UCHAR status; -/* UCHAR *p = local->sram + HOST_TO_ECF_BASE; */ dev_link_t *link = local->finder; if (!(link->state & DEV_PRESENT)) { - DEBUG(0,"ray_cs verify_dl_startup - device not present\n"); + DEBUG(2,"ray_cs verify_dl_startup - device not present\n"); return; } -#ifdef RAYLINK_DEBUG - { - int i; - DEBUG(2,"verify_dl_startup parameters sent via ccs %d:\n",\ - local->dl_param_ccs); - for (i=0; isram + HOST_TO_ECF_BASE + i)); +#ifdef PCMCIA_DEBUG + if (pc_debug > 2) { + int i; + printk(KERN_DEBUG "verify_dl_startup parameters sent via ccs %d:\n", + local->dl_param_ccs); + for (i=0; isram + HOST_TO_ECF_BASE + i)); } - DEBUG(1,"\n"); + printk("\n"); } #endif status = readb(&pccs->buffer_status); if (status!= CCS_BUFFER_FREE) { - DEBUG(0,"Download startup params failed. Status = %d\n",status); + printk(KERN_INFO "Download startup params failed. Status = %d\n", + status); local->card_status = CARD_DL_PARAM_ERROR; return; } @@ -799,11 +809,11 @@ int ccsindex; dev_link_t *link = local->finder; if (!(link->state & DEV_PRESENT)) { - DEBUG(0,"ray_cs start_net - device not present\n"); + DEBUG(2,"ray_cs start_net - device not present\n"); return; } /* Fill in the CCS fields for the ECF */ - if ((ccsindex = get_free_ccs(local)) == -1) return; + if ((ccsindex = get_free_ccs(local)) < 0) return; pccs = ((struct ccs *)(local->sram + CCS_BASE)) + ccsindex; writeb(CCS_START_NETWORK, &pccs->cmd); writeb(0, &pccs->var.start_network.update_param); @@ -827,11 +837,11 @@ dev_link_t *link = local->finder; if (!(link->state & DEV_PRESENT)) { - DEBUG(0,"ray_cs join_net - device not present\n"); + DEBUG(2,"ray_cs join_net - device not present\n"); return; } /* Fill in the CCS fields for the ECF */ - if ((ccsindex = get_free_ccs(local)) == -1) return; + if ((ccsindex = get_free_ccs(local)) < 0) return; pccs = ((struct ccs *)(local->sram + CCS_BASE)) + ccsindex; writeb(CCS_JOIN_NETWORK, &pccs->cmd); writeb(0, &pccs->var.join_network.update_param); @@ -867,7 +877,7 @@ link->state |= DEV_STALE_CONFIG; return; } - del_timer(&local->timer); + del_timer(&local->timer); if (link->dev != '\0') unregister_netdev(dev); /* Unlink the device chain */ link->dev = NULL; @@ -962,13 +972,14 @@ DEBUG(1,"ray_dev_init(dev=%p)\n",dev); if (!(link->state & DEV_PRESENT)) { - DEBUG(0,"ray_dev_init - device not present\n"); + DEBUG(2,"ray_dev_init - device not present\n"); return -1; } /* Download startup parameters */ if ( (i = dl_startup_params(dev)) < 0) { - DEBUG(0,"ray_dev_init dl_startup_params failed - returns 0x%x/n",i); + printk(KERN_INFO "ray_dev_init dl_startup_params failed - " + "returns 0x%x/n",i); return -1; } @@ -976,15 +987,6 @@ memcpy(&dev->dev_addr, &local->sparm.b4.a_mac_addr, ADDRLEN); memset(dev->broadcast, 0xff, ETH_ALEN); -#ifdef RAYLINK_DEBUG - { - UCHAR *p; - p = (UCHAR *)(local->startup_res.station_addr); - DEBUG(1,"ray_dev_init card hardware mac addr = %2x %2x %2x %2x %2x %2x\n",\ - p[0],p[1],p[2],p[3],p[4],p[5]); - } -#endif - DEBUG(2,"ray_dev_init ending\n"); return 0; } @@ -996,7 +998,7 @@ /* Dummy routine to satisfy device structure */ DEBUG(1,"ray_dev_config(dev=%p,ifmap=%p)\n",dev,map); if (!(link->state & DEV_PRESENT)) { - DEBUG(0,"ray_dev_config - device not present\n"); + DEBUG(2,"ray_dev_config - device not present\n"); return -1; } @@ -1010,13 +1012,13 @@ short length; if (!(link->state & DEV_PRESENT)) { - DEBUG(0,"ray_dev_start_xmit - device not present\n"); + DEBUG(2,"ray_dev_start_xmit - device not present\n"); return -1; } DEBUG(3,"ray_dev_start_xmit(skb=%p, dev=%p)\n",skb,dev); if (dev->tbusy) { - DEBUG(2,"ray_dev_start_xmit busy\n"); + printk(KERN_NOTICE "ray_dev_start_xmit busy\n"); return 1; } if (local->authentication_state == NEED_TO_AUTH) { @@ -1031,7 +1033,7 @@ length = ETH_ZLEN < skb->len ? skb->len : ETH_ZLEN; switch (ray_hw_xmit( skb->data, length, dev, DATA_TYPE)) { case XMIT_NO_CCS: - case XMIT_NEED_AUTH: + case XMIT_NEED_AUTH: dev->tbusy = 1; return 1; case XMIT_NO_INTR: @@ -1058,15 +1060,20 @@ DEBUG(3,"ray_hw_xmit(data=%p, len=%d, dev=%p)\n",data,len,dev); if (len + TX_HEADER_LENGTH > TX_BUF_SIZE) { - DEBUG(0,"ray_hw_xmit packet to large %d bytes\n",len); + printk(KERN_INFO "ray_hw_xmit packet too large: %d bytes\n",len); return XMIT_MSG_BAD; } - if ((ccsindex = get_free_tx_ccs(local)) == -1) - { - DEBUG(2,"ray_hw_xmit - No free tx ccs\n"); + switch (ccsindex = get_free_tx_ccs(local)) { + case ECCSBUSY: + DEBUG(2,"ray_hw_xmit tx_ccs table busy\n"); + case ECCSFULL: + DEBUG(2,"ray_hw_xmit No free tx ccs\n"); + case ECARDGONE: dev->tbusy = 1; return XMIT_NO_CCS; - } + default: + break; + } addr = TX_BUF_BASE + (ccsindex << 11); if (msg_type == DATA_TYPE) { @@ -1186,7 +1193,7 @@ int err = 0; if (!(link->state & DEV_PRESENT)) { - DEBUG(0,"ray_dev_ioctl - device not present\n"); + DEBUG(2,"ray_dev_ioctl - device not present\n"); return -1; } DEBUG(2,"ray_cs IOCTL dev=%p, ifr=%p, cmd = 0x%x\n",dev,ifr,cmd); @@ -1258,16 +1265,14 @@ int interrupt_ecf(ray_dev_t *local, int ccs) { int i = 50; -/* UCHAR *p = (local->amem + CIS_OFFSET + ECF_INTR_OFFSET); */ dev_link_t *link = local->finder; if (!(link->state & DEV_PRESENT)) { - DEBUG(0,"ray_cs interrupt_ecf - device not present\n"); + DEBUG(2,"ray_cs interrupt_ecf - device not present\n"); return -1; } DEBUG(2,"interrupt_ecf(local=%p, ccs = 0x%x\n",local,ccs); -/* while ( i && (*p & ECF_INTR_SET)) i--; */ while ( i && (readb(local->amem + CIS_OFFSET + ECF_INTR_OFFSET) & ECF_INTR_SET)) i--; @@ -1275,8 +1280,8 @@ DEBUG(2,"ray_cs interrupt_ecf card not ready for interrupt\n"); return -1; } - - *(local->sram + SCB_BASE) = ccs; + /* Fill the mailbox, then kick the card */ + writeb(ccs, local->sram + SCB_BASE); writeb(ECF_INTR_SET, local->amem + CIS_OFFSET + ECF_INTR_OFFSET); return 0; } /* interrupt_ecf */ @@ -1290,19 +1295,26 @@ dev_link_t *link = local->finder; if (!(link->state & DEV_PRESENT)) { - DEBUG(0,"ray_cs get_free_tx_ccs - device not present\n"); - return -1; + DEBUG(2,"ray_cs get_free_tx_ccs - device not present\n"); + return ECARDGONE; } + if (test_and_set_bit(0,&local->tx_ccs_lock)) { + DEBUG(1,"ray_cs tx_ccs_lock busy\n"); + return ECCSBUSY; + } + for (i=0; i < NUMBER_OF_TX_CCS; i++) { if (readb(&(pccs+i)->buffer_status) == CCS_BUFFER_FREE) { writeb(CCS_BUFFER_BUSY, &(pccs+i)->buffer_status); writeb(CCS_END_LIST, &(pccs+i)->link); + local->tx_ccs_lock = 0; return i; } } - DEBUG(1,"ray_cs ERROR no free tx CCS for raylink card\n"); - return -1; + local->tx_ccs_lock = 0; + DEBUG(2,"ray_cs ERROR no free tx CCS for raylink card\n"); + return ECCSFULL; } /* get_free_tx_ccs */ /*===========================================================================*/ /* Get next free CCS */ @@ -1314,25 +1326,33 @@ dev_link_t *link = local->finder; if (!(link->state & DEV_PRESENT)) { - DEBUG(0,"ray_cs get_free_ccs - device not present\n"); - return -1; + DEBUG(2,"ray_cs get_free_ccs - device not present\n"); + return ECARDGONE; } + if (test_and_set_bit(0,&local->ccs_lock)) { + DEBUG(1,"ray_cs ccs_lock busy\n"); + return ECCSBUSY; + } + for (i = NUMBER_OF_TX_CCS; i < NUMBER_OF_CCS; i++) { if (readb(&(pccs+i)->buffer_status) == CCS_BUFFER_FREE) { writeb(CCS_BUFFER_BUSY, &(pccs+i)->buffer_status); writeb(CCS_END_LIST, &(pccs+i)->link); + local->ccs_lock = 0; return i; } } + local->ccs_lock = 0; DEBUG(1,"ray_cs ERROR no free CCS for raylink card\n"); - return -1; + return ECCSFULL; } /* get_free_ccs */ /*===========================================================================*/ void authenticate_timeout(u_long data) { ray_dev_t *local = (ray_dev_t *)data; del_timer(&local->timer); - DEBUG(0,"ray_cs Authentication with access point failed - timeout\n"); + printk(KERN_INFO "ray_cs Authentication with access point failed" + " - timeout\n"); join_net((u_long)local); } /*===========================================================================*/ @@ -1381,26 +1401,26 @@ dev_link_t *link = local->finder; struct status *p = (struct status *)(local->sram + STATUS_BASE); if (!(link->state & DEV_PRESENT)) { - DEBUG(0,"ray_cs enet_statistics - device not present\n"); + DEBUG(2,"ray_cs enet_statistics - device not present\n"); return &local->stats; } - if (p->mrx_overflow_for_host) + if (readb(&p->mrx_overflow_for_host)) { - local->stats.rx_over_errors += ntohs(p->mrx_overflow); - p->mrx_overflow = 0; - p->mrx_overflow_for_host = 0; + local->stats.rx_over_errors += ntohs(readb(&p->mrx_overflow)); + writeb(0,&p->mrx_overflow); + writeb(0,&p->mrx_overflow_for_host); } - if (p->mrx_checksum_error_for_host) + if (readb(&p->mrx_checksum_error_for_host)) { - local->stats.rx_crc_errors += ntohs(p->mrx_checksum_error); - p->mrx_checksum_error = 0; - p->mrx_checksum_error_for_host = 0; + local->stats.rx_crc_errors += ntohs(readb(&p->mrx_checksum_error)); + writeb(0,&p->mrx_checksum_error); + writeb(0,&p->mrx_checksum_error_for_host); } - if (p->rx_hec_error_for_host) + if (readb(&p->rx_hec_error_for_host)) { - local->stats.rx_frame_errors += ntohs(p->rx_hec_error); - p->rx_hec_error = 0; - p->rx_hec_error_for_host = 0; + local->stats.rx_frame_errors += ntohs(readb(&p->rx_hec_error)); + writeb(0,&p->rx_hec_error); + writeb(0,&p->rx_hec_error_for_host); } return &local->stats; } @@ -1414,11 +1434,11 @@ struct ccs *pccs; if (!(link->state & DEV_PRESENT)) { - DEBUG(0,"ray_update_parm - device not present\n"); + DEBUG(2,"ray_update_parm - device not present\n"); return; } - if ((ccsindex = get_free_ccs(local)) == -1) + if ((ccsindex = get_free_ccs(local)) < 0) { DEBUG(0,"ray_update_parm - No free ccs\n"); return; @@ -1449,12 +1469,12 @@ UCHAR *p = local->sram + HOST_TO_ECF_BASE; if (!(link->state & DEV_PRESENT)) { - DEBUG(1,"ray_update_multi_list - device not present\n"); + DEBUG(2,"ray_update_multi_list - device not present\n"); return; } else - DEBUG(1,"ray_update_multi_list(%p)\n",dev); - if ((ccsindex = get_free_ccs(local)) == -1) + DEBUG(2,"ray_update_multi_list(%p)\n",dev); + if ((ccsindex = get_free_ccs(local)) < 0) { DEBUG(1,"ray_update_multi - No free ccs\n"); return; @@ -1491,7 +1511,7 @@ ray_dev_t *local = (ray_dev_t *)dev->priv; UCHAR promisc; - DEBUG(1,"ray_cs set_multicast_list(%p)\n",dev); + DEBUG(2,"ray_cs set_multicast_list(%p)\n",dev); if (dev->flags & IFF_PROMISC) { @@ -1534,30 +1554,23 @@ UCHAR cmd; UCHAR status; - if (dev == NULL) { - link = dev_list; - dev = (struct net_device *)link->priv; - DEBUG(4,"ray_cs interrupt dev = %p, link = %p\n",dev,link); - if (dev->irq != irq) - { - DEBUG(0,"ray_cs interrupt irq %d for unknown device.\n", irq); - return; - } - } + if ((dev == NULL) || !dev->start) + return; + DEBUG(4,"ray_cs: interrupt for *dev=%p\n",dev); - if (dev->interrupt) { + if (test_and_set_bit(0,&dev->interrupt)) { printk("ray_cs Reentering interrupt handler not allowed\n"); return; } - dev->interrupt = 1; + local = (ray_dev_t *)dev->priv; link = (dev_link_t *)local->finder; if ( ! (link->state & DEV_PRESENT) || link->state & DEV_SUSPEND ) { - DEBUG(1,"ray_cs interrupt from device not present or suspended.\n"); + DEBUG(2,"ray_cs interrupt from device not present or suspended.\n"); return; } - rcsindex = ((struct scb *)(local->sram))->rcs_index; + rcsindex = readb(&((struct scb *)(local->sram))->rcs_index); if (rcsindex >= (NUMBER_OF_CCS + NUMBER_OF_RCS)) { @@ -1602,7 +1615,7 @@ case CCS_JOIN_NETWORK: if (status == CCS_COMMAND_COMPLETE) { if (readb(&pccs->var.start_network.net_initiated) == 1) { - DEBUG(0,"ray_cs interrupt network \"%s\"started\n",\ + DEBUG(0,"ray_cs interrupt network \"%s\" started\n",\ local->sparm.b4.a_current_ess_id); } else { @@ -1741,16 +1754,16 @@ switch(readb(pmsg)) { case DATA_TYPE: - DEBUG(4,"ray_rx data type\n"); + DEBUG(4,"ray_rx data type\n"); rx_data(dev, prcs, pkt_addr, rx_len); break; case AUTHENTIC_TYPE: - DEBUG(4,"ray_rx authentic type\n"); + DEBUG(4,"ray_rx authentic type\n"); if (sniffer) rx_data(dev, prcs, pkt_addr, rx_len); else rx_authenticate(local, prcs, pkt_addr, rx_len); break; case DEAUTHENTIC_TYPE: - DEBUG(4,"ray_rx deauth type\n"); + DEBUG(4,"ray_rx deauth type\n"); if (sniffer) rx_data(dev, prcs, pkt_addr, rx_len); else rx_deauthenticate(local, prcs, pkt_addr, rx_len); break; @@ -1758,7 +1771,7 @@ DEBUG(3,"ray_cs rx NULL msg\n"); break; case BEACON_TYPE: - DEBUG(4,"ray_rx beacon type\n"); + DEBUG(4,"ray_rx beacon type\n"); if (sniffer) rx_data(dev, prcs, pkt_addr, rx_len); copy_from_rx_buff(local, (UCHAR *)&local->last_bcn, pkt_addr, @@ -1909,19 +1922,24 @@ struct ethhdr *peth; UCHAR srcaddr[ADDRLEN]; UCHAR destaddr[ADDRLEN]; - int i; - if (local->sparm.b5.a_acting_as_ap_status != TYPE_STA) + if (local->sparm.b5.a_acting_as_ap_status != TYPE_STA) memcpy(destaddr, pmac->addr_3, ADDRLEN); else memcpy(destaddr, pmac->addr_1, ADDRLEN); memcpy(srcaddr, pmac->addr_2, ADDRLEN); - DEBUG(3,"skb->data before untranslate"); +#ifdef PCMCIA_DEBUG + if (pc_debug > 3) { + int i; + printk(KERN_DEBUG "skb->data before untranslate"); for (i=0;i<64;i++) - DEBUG(3,"%02x ",skb->data[i]); - DEBUG(3,"\ntype = %08x, xsap = %08x, org = %08x\n",type,xsap,org); - DEBUG(3,"untranslate skb->data = %p\n",skb->data); + printk("%02x ",skb->data[i]); + printk("\n" KERN_DEBUG "type = %08x, xsap = %08x, org = %08x\n", + type,xsap,org); + printk(KERN_DEBUG "untranslate skb->data = %p\n",skb->data); + } +#endif if ( xsap != SNAP_ID) { /* not a snap type so leave it alone */ @@ -1971,10 +1989,15 @@ DEBUG(3,"untranslate after skb_pull(%d), skb->data = %p\n",delta,skb->data); memcpy(peth->h_dest, destaddr, ADDRLEN); memcpy(peth->h_source, srcaddr, ADDRLEN); - DEBUG(3,"skb->data after untranslate:"); - for (i=0;i<64;i++) - DEBUG(3,"%02x ",skb->data[i]); - DEBUG(3,"\n"); +#ifdef PCMCIA_DEBUG + if (pc_debug > 3) { + int i; + printk(KERN_DEBUG "skb->data after untranslate:"); + for (i=0;i<64;i++) + printk("%02x ",skb->data[i]); + printk("\n"); + } +#endif } /* end untranslate */ /*===========================================================================*/ /* Copy data from circular receive buffer to PC memory. @@ -2020,7 +2043,7 @@ dev_link_t *link = local->finder; DEBUG(0,"ray_cs Starting authentication.\n"); if (!(link->state & DEV_PRESENT)) { - DEBUG(1,"ray_cs authenticate - device not present\n"); + DEBUG(2,"ray_cs authenticate - device not present\n"); return; } @@ -2046,37 +2069,37 @@ del_timer(&local->timer); copy_from_rx_buff(local, buff, pkt_addr, rx_len & 0xff); - /* if we are trying to get authenticated */ + /* if we are trying to get authenticated */ if (local->sparm.b4.a_network_type == ADHOC) { - DEBUG(1,"ray_cs rx_auth var= %02x %02x %02x %02x %02x %02x\n", msg->var[0],msg->var[1],msg->var[2],msg->var[3],msg->var[4],msg->var[5]); - if (msg->var[2] == 1) { + DEBUG(1,"ray_cs rx_auth var= %02x %02x %02x %02x %02x %02x\n", msg->var[0],msg->var[1],msg->var[2],msg->var[3],msg->var[4],msg->var[5]); + if (msg->var[2] == 1) { DEBUG(0,"ray_cs Sending authentication response.\n"); if (!build_auth_frame (local, msg->mac.addr_2, OPEN_AUTH_RESPONSE)) { local->authentication_state = NEED_TO_AUTH; memcpy(local->auth_id, msg->mac.addr_2, ADDRLEN); } - } - } - else /* Infrastructure network */ - { - if (local->authentication_state == AWAITING_RESPONSE) { - /* Verify authentication sequence #2 and success */ - if (msg->var[2] == 2) { - if ((msg->var[3] | msg->var[4]) == 0) { - DEBUG(1,"Authentication successful\n"); - local->card_status = CARD_AUTH_COMPLETE; - associate(local); - local->authentication_state = AUTHENTICATED; - } - else { - DEBUG(0,"Authentication refused\n"); - local->card_status = CARD_AUTH_REFUSED; - join_net((u_long)local); - local->authentication_state = UNAUTHENTICATED; - } - } - } - } + } + } + else /* Infrastructure network */ + { + if (local->authentication_state == AWAITING_RESPONSE) { + /* Verify authentication sequence #2 and success */ + if (msg->var[2] == 2) { + if ((msg->var[3] | msg->var[4]) == 0) { + DEBUG(1,"Authentication successful\n"); + local->card_status = CARD_AUTH_COMPLETE; + associate(local); + local->authentication_state = AUTHENTICATED; + } + else { + DEBUG(0,"Authentication refused\n"); + local->card_status = CARD_AUTH_REFUSED; + join_net((u_long)local); + local->authentication_state = UNAUTHENTICATED; + } + } + } + } } /* end rx_authenticate */ /*===========================================================================*/ @@ -2087,11 +2110,11 @@ struct net_device *dev = link->priv; int ccsindex; if (!(link->state & DEV_PRESENT)) { - DEBUG(1,"ray_cs associate - device not present\n"); + DEBUG(2,"ray_cs associate - device not present\n"); return; } /* If no tx buffers available, return*/ - if ((ccsindex = get_free_ccs(local)) == -1) + if ((ccsindex = get_free_ccs(local)) < 0) { /* TBD should never be here but... what if we are? */ DEBUG(1,"ray_cs associate - No free ccs\n"); @@ -2125,7 +2148,7 @@ struct rx_msg *msg = (struct rx_msg *)buff; */ DEBUG(0,"Deauthentication frame received\n"); - local->authentication_state = UNAUTHENTICATED; + local->authentication_state = UNAUTHENTICATED; /* Need to reauthenticate or rejoin depending on reason code */ /* copy_from_rx_buff(local, buff, pkt_addr, rx_len & 0xff); */ @@ -2256,9 +2279,8 @@ int ccsindex; /* If no tx buffers available, return */ - if ((ccsindex = get_free_tx_ccs(local)) == -1) + if ((ccsindex = get_free_tx_ccs(local)) < 0) { -/* TBD should never be here but... what if we are? */ DEBUG(1,"ray_cs send authenticate - No free tx ccs\n"); return -1; } diff -u --recursive --new-file v2.3.19/linux/drivers/net/pcmcia/ray_cs.h linux/drivers/net/pcmcia/ray_cs.h --- v2.3.19/linux/drivers/net/pcmcia/ray_cs.h Fri Sep 10 23:57:30 1999 +++ linux/drivers/net/pcmcia/ray_cs.h Thu Oct 7 11:50:26 1999 @@ -17,9 +17,14 @@ + sizeof(struct tim_element)]; }; +/* Return values for get_free{,_tx}_ccs */ +#define ECCSFULL (-1) +#define ECCSBUSY (-2) +#define ECARDGONE (-3) + typedef struct ray_dev_t { int card_status; - int authentication_state; + int authentication_state; dev_node_t node; window_handle_t amem_handle; /* handle to window for attribute memory */ window_handle_t rmem_handle; /* handle to window for rx buffer on card */ @@ -28,6 +33,8 @@ UCHAR *rmem; /* pointer to receive buffer window */ dev_link_t *finder; /* pointer back to dev_link_t for card */ struct timer_list timer; + int tx_ccs_lock; + int ccs_lock; int dl_param_ccs; union { struct b4_startup_params b4; diff -u --recursive --new-file v2.3.19/linux/drivers/net/pcmcia/rayctl.h linux/drivers/net/pcmcia/rayctl.h --- v2.3.19/linux/drivers/net/pcmcia/rayctl.h Fri Sep 10 23:57:30 1999 +++ linux/drivers/net/pcmcia/rayctl.h Thu Oct 7 11:50:26 1999 @@ -142,8 +142,6 @@ }; /*****************************************************************************/ /*****************************************************************************/ - - /* #define C_MAC_HDR_2_WEP 0x40 */ /* TX/RX CCS constants */ #define TX_HEADER_LENGTH 0x1C @@ -151,6 +149,9 @@ #define TX_AUTHENTICATE_LENGTH (TX_HEADER_LENGTH + 6) #define TX_AUTHENTICATE_LENGTH_MSB (TX_AUTHENTICATE_LENGTH >> 8) #define TX_AUTHENTICATE_LENGTH_LSB (TX_AUTHENTICATE_LENGTH & 0xff) +#define TX_DEAUTHENTICATE_LENGTH (TX_HEADER_LENGTH + 2) +#define TX_DEAUTHENTICATE_LENGTH_MSB (TX_AUTHENTICATE_LENGTH >> 8) +#define TX_DEAUTHENTICATE_LENGTH_LSB (TX_AUTHENTICATE_LENGTH & 0xff) #define FCS_LEN 4 #define ADHOC 0 @@ -324,17 +325,23 @@ #define CARD_ASSOC_COMPLETE (6) #define CARD_ASSOC_FAILED (16) -/*** Values for authentication_state */ +/*** Values for authentication_state ***********************************/ #define UNAUTHENTICATED (0) #define AWAITING_RESPONSE (1) #define AUTHENTICATED (2) #define NEED_TO_AUTH (3) -/*** Values for authentication type */ +/*** Values for authentication type ************************************/ #define OPEN_AUTH_REQUEST (1) #define OPEN_AUTH_RESPONSE (2) - - +#define BROADCAST_DEAUTH (0xc0) +/*** Values for timer functions ****************************************/ +#define TODO_NOTHING (0) +#define TODO_VERIFY_DL_START (-1) +#define TODO_START_NET (-2) +#define TODO_JOIN_NET (-3) +#define TODO_AUTHENTICATE_TIMEOUT (-4) +#define TODO_SEND_CCS (-5) /***********************************************************************/ /* Parameter passing structure for update/report parameter CCS's */ struct object_id { diff -u --recursive --new-file v2.3.19/linux/drivers/parport/ieee1284.c linux/drivers/parport/ieee1284.c --- v2.3.19/linux/drivers/parport/ieee1284.c Fri Aug 6 15:25:47 1999 +++ linux/drivers/parport/ieee1284.c Fri Oct 8 15:46:35 1999 @@ -151,8 +151,6 @@ { port = port->physport; - port->ieee1284.phase = IEEE1284_PH_TERMINATE; - /* EPP terminates differently. */ switch (port->ieee1284.mode) { case IEEE1284_MODE_EPP: @@ -161,17 +159,42 @@ /* Terminate from EPP mode. */ /* Event 68: Set nInit low */ - parport_frob_control (port, - PARPORT_CONTROL_INIT, - PARPORT_CONTROL_INIT); + parport_frob_control (port, PARPORT_CONTROL_INIT, 0); udelay (50); /* Event 69: Set nInit high, nSelectIn low */ parport_frob_control (port, - PARPORT_CONTROL_SELECT, - PARPORT_CONTROL_SELECT); + PARPORT_CONTROL_SELECT + | PARPORT_CONTROL_INIT, + PARPORT_CONTROL_SELECT + | PARPORT_CONTROL_INIT); break; - + + case IEEE1284_MODE_ECP: + case IEEE1284_MODE_ECPRLE: + case IEEE1284_MODE_ECPSWE: + /* In ECP we can only terminate from fwd idle phase. */ + if (port->ieee1284.phase != IEEE1284_PH_FWD_IDLE) { + /* Event 47: Set nInit high */ + parport_frob_control (port, + PARPORT_CONTROL_INIT + | PARPORT_CONTROL_AUTOFD, + PARPORT_CONTROL_INIT + | PARPORT_CONTROL_AUTOFD); + + /* Event 49: PError goes high */ + parport_wait_peripheral (port, + PARPORT_STATUS_PAPEROUT, + PARPORT_STATUS_PAPEROUT); + + parport_data_forward (port); + DPRINTK (KERN_DEBUG "%s: ECP direction: forward\n", + port->name); + port->ieee1284.phase = IEEE1284_PH_FWD_IDLE; + } + + /* fall-though.. */ + default: /* Terminate from all other modes. */ diff -u --recursive --new-file v2.3.19/linux/drivers/parport/ieee1284_ops.c linux/drivers/parport/ieee1284_ops.c --- v2.3.19/linux/drivers/parport/ieee1284_ops.c Thu Aug 12 11:53:18 1999 +++ linux/drivers/parport/ieee1284_ops.c Thu Oct 7 10:17:09 1999 @@ -9,8 +9,10 @@ * Note: Make no assumptions about hardware or architecture in this file! * * Author: Tim Waugh + * Fixed AUTOFD polarity in ecp_forward_to_reverse(). Fred Barnes, 1999 */ + #include #include #include @@ -336,7 +338,7 @@ /* Event 38: Set nAutoFd low */ parport_frob_control (port, PARPORT_CONTROL_AUTOFD, - 0); + PARPORT_CONTROL_AUTOFD); parport_data_reverse (port); udelay (5); @@ -524,12 +526,12 @@ if (count && dev->port->irq != PARPORT_IRQ_NONE) { parport_release (dev); current->state = TASK_INTERRUPTIBLE; - schedule_timeout ((HZ + 99) / 25); + schedule_timeout ((HZ + 24) / 25); parport_claim_or_block (dev); } else /* We must have the device claimed here. */ - parport_wait_event (port, (HZ + 99) / 25); + parport_wait_event (port, (HZ + 24) / 25); /* Is there a signal pending? */ if (signal_pending (current)) @@ -610,10 +612,11 @@ count += rle_count; DPRINTK (KERN_DEBUG "%s: decompressed to %d bytes\n", port->name, rle_count); - } - else + } else { /* Normal data byte. */ - *buf++ = byte, count++; + *buf = byte; + buf++, count++; + } } out: diff -u --recursive --new-file v2.3.19/linux/drivers/parport/init.c linux/drivers/parport/init.c --- v2.3.19/linux/drivers/parport/init.c Fri Sep 10 23:57:30 1999 +++ linux/drivers/parport/init.c Thu Oct 7 14:10:06 1999 @@ -91,6 +91,8 @@ if (sep++) { if (!strncmp (sep, "auto", 4)) dma[parport_setup_ptr] = PARPORT_DMA_AUTO; + else if (!strncmp (sep, "nofifo", 6)) + dma[parport_setup_ptr] = PARPORT_DMA_NOFIFO; else if (strncmp (sep, "none", 4)) { val = simple_strtoul (sep, &endptr, 0); if (endptr == sep) { @@ -209,6 +211,8 @@ EXPORT_SYMBOL(parport_daisy_deselect_all); EXPORT_SYMBOL(parport_daisy_select); EXPORT_SYMBOL(parport_daisy_init); +EXPORT_SYMBOL(parport_find_device); +EXPORT_SYMBOL(parport_find_class); #endif void inc_parport_count(void) diff -u --recursive --new-file v2.3.19/linux/drivers/parport/parport_pc.c linux/drivers/parport/parport_pc.c --- v2.3.19/linux/drivers/parport/parport_pc.c Thu Aug 12 11:53:22 1999 +++ linux/drivers/parport/parport_pc.c Fri Oct 8 10:06:21 1999 @@ -10,6 +10,7 @@ * * Cleaned up include files - Russell King * DMA support - Bert De Jonghe + * Many ECP bugs fixed. Fred Barnes & Jamie Lokier, 1999 */ /* This driver should work with any hardware that is broadly compatible @@ -73,7 +74,12 @@ static void frob_econtrol (struct parport *pb, unsigned char m, unsigned char v) { - outb ((inb (ECONTROL (pb)) & ~m) ^ v, ECONTROL (pb)); + unsigned char ectr = inb (ECONTROL (pb)); +#ifdef DEBUG_PARPORT + printk (KERN_DEBUG "frob_econtrol(%02x,%02x): %02x -> %02x\n", + m, v, ectr, (ectr & ~m) ^ v); +#endif + outb ((ectr & ~m) ^ v, ECONTROL (pb)); } #ifdef CONFIG_PARPORT_PC_FIFO @@ -94,11 +100,8 @@ oecr = inb (ecr); mode = (oecr >> 5) & 0x7; if (mode == m) return 0; - if (mode && m) - /* We have to go through mode 000 */ - change_mode (p, ECR_SPP); - if (m < 2 && !(parport_read_control (p) & 0x20)) { + if (mode >= 2 && !(priv->ctr & 0x20)) { /* This mode resets the FIFO, so we may * have to wait for it to drain first. */ long expire = jiffies + p->physport->cad->timeout; @@ -127,6 +130,13 @@ } } + if (mode >= 2 && m >= 2) { + /* We have to go through mode 001 */ + oecr &= ~(7 << 5); + oecr |= ECR_PS2 << 5; + outb (oecr, ecr); + } + /* Set the mode. */ oecr &= ~(7 << 5); oecr |= m << 5; @@ -160,11 +170,11 @@ residue); /* Reset the FIFO. */ - frob_econtrol (p, 0xe0, 0x20); + frob_econtrol (p, 0xe0, ECR_PS2 << 5); parport_frob_control (p, PARPORT_CONTROL_STROBE, 0); /* Now change to config mode and clean up. FIXME */ - frob_econtrol (p, 0xe0, 0xe0); + frob_econtrol (p, 0xe0, ECR_CNF << 5); cnfga = inb (CONFIGA (p)); printk (KERN_DEBUG "%s: cnfgA contains 0x%02x\n", p->name, cnfga); @@ -177,7 +187,7 @@ * PWord != 1 byte. */ /* Back to PS2 mode. */ - frob_econtrol (p, 0xe0, 0x20); + frob_econtrol (p, 0xe0, ECR_PS2 << 5); return residue; } @@ -209,9 +219,9 @@ /* * Access functions. * - * These aren't static because they may be used by the parport_xxx_yyy - * macros. extern __inline__ versions of several of these are in - * parport_pc.h. + * Most of these aren't static because they may be used by the + * parport_xxx_yyy macros. extern __inline__ versions of several + * of these are in parport_pc.h. */ static void parport_pc_interrupt(int irq, void *dev_id, struct pt_regs *regs) @@ -229,21 +239,6 @@ return inb (DATA (p)); } -unsigned char __frob_control (struct parport *p, unsigned char mask, - unsigned char val) -{ - const unsigned char wm = (PARPORT_CONTROL_STROBE | - PARPORT_CONTROL_AUTOFD | - PARPORT_CONTROL_INIT | - PARPORT_CONTROL_SELECT); - struct parport_pc_private *priv = p->physport->private_data; - unsigned char ctr = priv->ctr; - ctr = (ctr & ~mask) ^ val; - ctr &= priv->ctr_writable; /* only write writable bits. */ - outb (ctr, CONTROL (p)); - return priv->ctr = ctr & wm; /* update soft copy */ -} - void parport_pc_write_control(struct parport *p, unsigned char d) { const unsigned char wm = (PARPORT_CONTROL_STROBE | @@ -253,18 +248,22 @@ /* Take this out when drivers have adapted to the newer interface. */ if (d & 0x20) { - printk (KERN_DEBUG "%s (%s): use data_reverse for this!\n", - p->name, p->cad->name); - parport_pc_data_reverse (p); + printk (KERN_DEBUG "%s (%s): use data_reverse for this!\n", + p->name, p->cad->name); + parport_pc_data_reverse (p); } - __frob_control (p, wm, d & wm); + __parport_pc_frob_control (p, wm, d & wm); } unsigned char parport_pc_read_control(struct parport *p) { + const unsigned char wm = (PARPORT_CONTROL_STROBE | + PARPORT_CONTROL_AUTOFD | + PARPORT_CONTROL_INIT | + PARPORT_CONTROL_SELECT); const struct parport_pc_private *priv = p->physport->private_data; - return priv->ctr; /* Use soft copy */ + return priv->ctr & wm; /* Use soft copy */ } unsigned char parport_pc_frob_control (struct parport *p, unsigned char mask, @@ -277,16 +276,20 @@ /* Take this out when drivers have adapted to the newer interface. */ if (mask & 0x20) { - printk (KERN_DEBUG "%s (%s): use data_reverse for this!\n", - p->name, p->cad->name); + printk (KERN_DEBUG "%s (%s): use data_%s for this!\n", + p->name, p->cad->name, + (val & 0x20) ? "reverse" : "forward"); + if (val & 0x20) parport_pc_data_reverse (p); + else + parport_pc_data_forward (p); } /* Restrict mask and val to control lines. */ mask &= wm; val &= wm; - return __frob_control (p, mask, val); + return __parport_pc_frob_control (p, mask, val); } unsigned char parport_pc_read_status(struct parport *p) @@ -296,22 +299,22 @@ void parport_pc_disable_irq(struct parport *p) { - __frob_control (p, 0x10, 0); + __parport_pc_frob_control (p, 0x10, 0); } void parport_pc_enable_irq(struct parport *p) { - __frob_control (p, 0x10, 0x10); + __parport_pc_frob_control (p, 0x10, 0x10); } void parport_pc_data_forward (struct parport *p) { - __frob_control (p, 0x20, 0); + __parport_pc_frob_control (p, 0x20, 0); } void parport_pc_data_reverse (struct parport *p) { - __frob_control (p, 0x20, 0x20); + __parport_pc_frob_control (p, 0x20, 0x20); } void parport_pc_init_state(struct pardevice *dev, struct parport_state *s) @@ -469,7 +472,7 @@ frob_econtrol (port, (1<<4), (1<<4)); /* nErrIntrEn */ /* Forward mode. */ - parport_pc_data_forward (port); + parport_pc_data_forward (port); /* Must be in PS2 mode */ while (left) { unsigned char byte; @@ -559,7 +562,7 @@ frob_econtrol (port, (1<<4), (1<<4)); /* nErrIntrEn */ /* Forward mode. */ - parport_pc_data_forward (port); + parport_pc_data_forward (port); /* Must be in PS2 mode */ while (left) { long expire = jiffies + port->physport->cad->timeout; @@ -656,8 +659,8 @@ length, flags); /* Set up parallel port FIFO mode.*/ + parport_pc_data_forward (port); /* Must be in PS2 mode */ change_mode (port, ECR_PPF); /* Parallel port FIFO */ - parport_pc_data_forward (port); port->physport->ieee1284.phase = IEEE1284_PH_FWD_DATA; /* Write the data to the FIFO. */ @@ -687,8 +690,8 @@ outb (0, FIFO (port)); } - /* Reset the FIFO. */ - frob_econtrol (port, 0xe0, 0); + /* Reset the FIFO and return to PS2 mode. */ + frob_econtrol (port, 0xe0, ECR_PS2 << 5); /* De-assert strobe. */ parport_frob_control (port, PARPORT_CONTROL_STROBE, 0); @@ -727,8 +730,8 @@ } /* Set up ECP parallel port mode.*/ + parport_pc_data_forward (port); /* Must be in PS2 mode */ change_mode (port, ECR_ECP); /* ECP FIFO */ - parport_pc_data_forward (port); port->physport->ieee1284.phase = IEEE1284_PH_FWD_DATA; /* Write the data to the FIFO. */ @@ -758,17 +761,20 @@ outb (0, FIFO (port)); } - /* Reset the FIFO. */ - frob_econtrol (port, 0xe0, 0); + /* Reset the FIFO and return to PS2 mode. */ + frob_econtrol (port, 0xe0, ECR_PS2 << 5); + + /* De-assert strobe. */ parport_frob_control (port, PARPORT_CONTROL_STROBE, 0); /* Host transfer recovery. */ + parport_pc_data_reverse (port); /* Must be in PS2 mode */ + udelay (5); + parport_frob_control (port, PARPORT_CONTROL_INIT, 0); + parport_wait_peripheral (port, PARPORT_STATUS_PAPEROUT, 0); parport_frob_control (port, PARPORT_CONTROL_INIT, PARPORT_CONTROL_INIT); - parport_pc_data_reverse (port); - parport_wait_peripheral (port, PARPORT_STATUS_PAPEROUT, 0); - parport_frob_control (port, PARPORT_CONTROL_INIT, 0); parport_wait_peripheral (port, PARPORT_STATUS_PAPEROUT, PARPORT_STATUS_PAPEROUT); @@ -819,21 +825,21 @@ parport_frob_control (port, PARPORT_CONTROL_AUTOFD, PARPORT_CONTROL_AUTOFD); - parport_pc_data_reverse (port); + parport_pc_data_reverse (port); /* Must be in PS2 mode */ udelay (5); /* Event 39: Set nInit low to initiate bus reversal */ parport_frob_control (port, PARPORT_CONTROL_INIT, - PARPORT_CONTROL_INIT); + 0); /* Event 40: PError goes low */ parport_wait_peripheral (port, PARPORT_STATUS_PAPEROUT, 0); } /* Set up ECP parallel port mode.*/ + parport_pc_data_reverse (port); /* Must be in PS2 mode */ change_mode (port, ECR_ECP); /* ECP FIFO */ - parport_pc_data_reverse (port); port->ieee1284.phase = IEEE1284_PH_REV_DATA; /* Do the transfer. */ @@ -1054,7 +1060,6 @@ struct parport_pc_private *priv = pb->private_data; unsigned char r = 0xc; - priv->ecr = 0; outb (r, CONTROL (pb)); if ((inb (ECONTROL (pb)) & 0x3) == (r & 0x3)) { outb (r ^ 0x2, CONTROL (pb)); /* Toggle bit 1 */ @@ -1120,9 +1125,9 @@ /* cancel input mode */ parport_pc_data_forward (pb); - if (ok) + if (ok) { pb->modes |= PARPORT_MODE_TRISTATE; - else { + } else { struct parport_pc_private *priv = pb->private_data; priv->ctr_writable &= ~0x20; } @@ -1180,8 +1185,8 @@ priv->writeIntrThreshold = i; /* Find out readIntrThreshold */ - frob_econtrol (pb, 0xe0, ECR_PS2 << 5); /* Reset FIFO */ - parport_pc_data_reverse (pb); + frob_econtrol (pb, 0xe0, ECR_PS2 << 5); /* Reset FIFO and enable PS2 */ + parport_pc_data_reverse (pb); /* Must be in PS2 mode */ frob_econtrol (pb, 0xe0, ECR_TST << 5); /* Test FIFO */ frob_econtrol (pb, 1<<2, 1<<2); frob_econtrol (pb, 1<<2, 0); @@ -1544,12 +1549,10 @@ if (base_hi && !check_region(base_hi,3)) { parport_ECR_present(p); parport_ECP_supported(p); - parport_ECPPS2_supported(p); } if (base != 0x3bc) { if (!check_region(base+0x3, 5)) { - parport_EPP_supported(p); - if (!(p->modes & PARPORT_MODE_EPP)) + if (!parport_EPP_supported(p)) parport_ECPEPP_supported(p); } } @@ -1558,8 +1561,10 @@ kfree (priv); return NULL; } - - parport_PS2_supported (p); + if (priv->ecr) + parport_ECPPS2_supported(p); + else + parport_PS2_supported (p); if (!(p = parport_register_port(base, PARPORT_IRQ_NONE, PARPORT_DMA_NONE, ops))) { @@ -1599,7 +1604,8 @@ p->dma = PARPORT_DMA_NONE; #ifdef CONFIG_PARPORT_PC_FIFO - if (priv->fifo_depth > 0 && p->irq != PARPORT_IRQ_NONE) { + if (p->dma != PARPORT_DMA_NOFIFO && + priv->fifo_depth > 0 && p->irq != PARPORT_IRQ_NONE) { p->ops->compat_write_data = parport_pc_compat_write_block_pio; #ifdef CONFIG_PARPORT_1284 p->ops->ecp_write_data = parport_pc_ecp_write_block_pio; @@ -1672,9 +1678,10 @@ /* Done probing. Now put the port into a sensible start-up state. * SELECT | INIT also puts IEEE1284-compliant devices into * compatibility mode. */ - if (p->modes & PARPORT_MODE_ECP) + if (priv->ecr) /* * Put the ECP detected port in PS2 mode. + * Do this also for ports that have ECR but don't do ECP. */ outb (0x34, ECONTROL (p)); @@ -1751,6 +1758,8 @@ { { 0, -1 }, } }, { PCI_VENDOR_ID_LAVA, PCI_DEVICE_ID_LAVA_DUAL_PAR_B, 1, { { 0, -1 }, } }, + { PCI_VENDOR_ID_EXSYS, PCI_DEVICE_ID_EXSYS_4014, 2, + { { 2, -1 }, { 3, -1 }, } }, { 0, } }; diff -u --recursive --new-file v2.3.19/linux/drivers/parport/share.c linux/drivers/parport/share.c --- v2.3.19/linux/drivers/parport/share.c Fri Sep 10 23:57:30 1999 +++ linux/drivers/parport/share.c Thu Oct 7 14:10:06 1999 @@ -633,7 +633,7 @@ } static int parport_parse_params (int nports, const char *str[], int val[], - int automatic, int none) + int automatic, int none, int nofifo) { unsigned int i; for (i = 0; i < nports && str[i]; i++) { @@ -641,6 +641,8 @@ val[i] = automatic; else if (!strncmp(str[i], "none", 4)) val[i] = none; + else if (nofifo && !strncmp(str[i], "nofifo", 4)) + val[i] = nofifo; else { char *ep; unsigned long r = simple_strtoul(str[i], &ep, 0); @@ -659,11 +661,11 @@ int parport_parse_irqs(int nports, const char *irqstr[], int irqval[]) { return parport_parse_params (nports, irqstr, irqval, PARPORT_IRQ_AUTO, - PARPORT_IRQ_NONE); + PARPORT_IRQ_NONE, 0); } int parport_parse_dmas(int nports, const char *dmastr[], int dmaval[]) { return parport_parse_params (nports, dmastr, dmaval, PARPORT_DMA_AUTO, - PARPORT_DMA_NONE); + PARPORT_DMA_NONE, PARPORT_DMA_NOFIFO); } diff -u --recursive --new-file v2.3.19/linux/drivers/pci/Makefile linux/drivers/pci/Makefile --- v2.3.19/linux/drivers/pci/Makefile Tue Sep 7 12:14:06 1999 +++ linux/drivers/pci/Makefile Thu Oct 7 18:07:25 1999 @@ -25,6 +25,10 @@ L_OBJS += proc.o endif -L_OBJS += compat.o quirks.o names.o syscall.o setup.o +L_OBJS += compat.o quirks.o names.o helper.o + +ifndef CONFIG_X86 +L_OBJS += syscall.o setup.o +endif include $(TOPDIR)/Rules.make diff -u --recursive --new-file v2.3.19/linux/drivers/pci/devlist.h linux/drivers/pci/devlist.h --- v2.3.19/linux/drivers/pci/devlist.h Fri Sep 10 23:57:30 1999 +++ linux/drivers/pci/devlist.h Fri Oct 8 10:06:21 1999 @@ -989,6 +989,10 @@ DEVICE( ATRONICS, ATRONICS_2015, "IDE-2015PL") ENDVENDOR() +VENDOR( EXSYS, "Exsys" ) + DEVICE( EXSYS, EXSYS_4014, "EX-4014") +ENDVENDOR() + VENDOR( TIGERJET, "TigerJet" ) DEVICE( TIGERJET, TIGERJET_300, "Tiger300 ISDN") ENDVENDOR() diff -u --recursive --new-file v2.3.19/linux/drivers/pci/helper.c linux/drivers/pci/helper.c --- v2.3.19/linux/drivers/pci/helper.c Wed Dec 31 16:00:00 1969 +++ linux/drivers/pci/helper.c Thu Oct 7 18:07:25 1999 @@ -0,0 +1,69 @@ +/* + * $Id$ + * + * drivers/pci/helper.c + * + * Copyright 1999 Jeff Garzik + * This software is free. See the file COPYING for licensing details. + * + */ + +#include +#include +#include + + +int pci_simple_probe (struct pci_simple_probe_entry *list, size_t match_limit, + pci_simple_probe_callback cb, void *drvr_data) +{ + struct pci_dev *dev; + struct pci_simple_probe_entry *ent; + size_t matches = 0; + unsigned short vendor, device; + int rc; + + if (!list || !cb) + return -1; + + dev = pci_find_device (PCI_ANY_ID, PCI_ANY_ID, NULL); + while (dev) { + ent = list; + while (ent->vendor && ent->device) { + vendor = ent->vendor; + device = ent->device; + + if (((vendor != 0xFFFF) && + (vendor != dev->vendor)) || + ((device != 0xFFFF) && + (device != dev->device))) { + ent++; + continue; + } + + if (((ent->subsys_vendor) && + (ent->subsys_vendor != dev->subsystem_vendor)) || + ((ent->subsys_device) && + (ent->subsys_device != dev->subsystem_device))) { + ent++; + continue; + } + + rc = (* cb) (dev, matches, ent, drvr_data); + if (rc < 0) + return rc; + + matches++; + + if (match_limit && match_limit == matches) + return matches; + + ent++; + } + + dev = pci_find_device (PCI_ANY_ID, PCI_ANY_ID, dev); + } + + return matches; +} + + diff -u --recursive --new-file v2.3.19/linux/drivers/pci/pci.c linux/drivers/pci/pci.c --- v2.3.19/linux/drivers/pci/pci.c Fri Sep 10 23:57:30 1999 +++ linux/drivers/pci/pci.c Thu Oct 7 12:23:21 1999 @@ -17,7 +17,6 @@ #include #include -#include #include #undef DEBUG @@ -125,26 +124,20 @@ int i; struct resource *best = NULL; - while (bus) { - for(i=0; i<4; i++) { - struct resource *r = bus->resource[i]; - if (!r) - continue; - if (res->start && !(res->start >= r->start && res->end <= r->end)) - continue; /* Not contained */ - if ((res->flags ^ r->flags) & (IORESOURCE_IO | IORESOURCE_MEM)) - continue; /* Wrong type */ - if (!((res->flags ^ r->flags) & IORESOURCE_PREFETCH)) - return r; /* Exact match */ - if ((res->flags & IORESOURCE_PREFETCH) && !(r->flags & IORESOURCE_PREFETCH)) - best = r; /* Approximating prefetchable by non-prefetchable */ - } - if (best) - return best; - bus = bus->parent; + for(i=0; i<4; i++) { + struct resource *r = bus->resource[i]; + if (!r) + continue; + if (res->start && !(res->start >= r->start && res->end <= r->end)) + continue; /* Not contained */ + if ((res->flags ^ r->flags) & (IORESOURCE_IO | IORESOURCE_MEM)) + continue; /* Wrong type */ + if (!((res->flags ^ r->flags) & IORESOURCE_PREFETCH)) + return r; /* Exact match */ + if ((res->flags & IORESOURCE_PREFETCH) && !(r->flags & IORESOURCE_PREFETCH)) + best = r; /* Approximating prefetchable by non-prefetchable */ } - printk(KERN_ERR "PCI: Bug: Parent resource not found!\n"); - return NULL; + return best; } @@ -193,47 +186,18 @@ pci_read_config_word(dev, PCI_COMMAND, &cmd); if (! (cmd & PCI_COMMAND_MASTER)) { - printk("PCI: Enabling bus mastering for device %s\n", dev->name); + printk("PCI: Enabling bus mastering for device %s\n", dev->slot_name); cmd |= PCI_COMMAND_MASTER; pci_write_config_word(dev, PCI_COMMAND, cmd); } pci_read_config_byte(dev, PCI_LATENCY_TIMER, &lat); if (lat < 16) { - printk("PCI: Increasing latency timer of device %s to 64\n", dev->name); + printk("PCI: Increasing latency timer of device %s to 64\n", dev->slot_name); pci_write_config_byte(dev, PCI_LATENCY_TIMER, 64); } } /* - * Assign new address to PCI resource. We hope our resource information - * is complete. On the PC, we don't re-assign resources unless we are - * forced to do so or the driver asks us to. - * - * Expects start=0, end=size-1, flags=resource type. - */ -int __init pci_assign_resource(struct pci_dev *dev, int i) -{ - struct resource *r = &dev->resource[i]; - struct resource *pr = pci_find_parent_resource(dev, r); - unsigned long size = r->end + 1; - - if (!pr) - return -EINVAL; - if (r->flags & IORESOURCE_IO) { - if (size > 0x100) - return -EFBIG; - if (allocate_resource(pr, r, size, 0x1000, ~0, 1024)) - return -EBUSY; - } else { - if (allocate_resource(pr, r, size, 0x10000000, ~0, size)) - return -EBUSY; - } - if (i < 6) - pci_write_config_dword(dev, PCI_BASE_ADDRESS_0 + 4*i, r->start); - return 0; -} - -/* * Translate the low bits of the PCI base * to the resource type */ @@ -296,7 +260,7 @@ res->end = res->start + (((unsigned long) ~l) << 32); #else if (l) { - printk(KERN_ERR "PCI: Unable to handle 64-bit address for device %s\n", dev->name); + printk(KERN_ERR "PCI: Unable to handle 64-bit address for device %s\n", dev->slot_name); res->start = 0; res->flags = 0; continue; @@ -305,6 +269,7 @@ } } if (rom) { + dev->rom_base_reg = rom; res = &dev->resource[PCI_ROM_RESOURCE]; pci_read_config_dword(dev, rom, &l); pci_write_config_dword(dev, rom, ~PCI_ROM_ADDRESS_ENABLE); @@ -324,8 +289,9 @@ pci_write_config_word(dev, PCI_COMMAND, cmd); } -void __init pci_read_bridge_bases(struct pci_dev *dev, struct pci_bus *child) +void __init pci_read_bridge_bases(struct pci_bus *child) { + struct pci_dev *dev = child->self; u8 io_base_lo, io_limit_lo; u16 mem_base_lo, mem_limit_lo, io_base_hi, io_limit_hi; u32 mem_base_hi, mem_limit_hi; @@ -333,6 +299,9 @@ struct resource *res; int i; + if (!dev) /* It's a host bus, nothing to read */ + return; + for(i=0; i<3; i++) child->resource[i] = &dev->resource[PCI_BRIDGE_RESOURCES+i]; @@ -425,31 +394,27 @@ dev_cache = NULL; dev->vendor = l & 0xffff; dev->device = (l >> 16) & 0xffff; - sprintf(dev->name, "%02x:%02x.%d", bus->number, PCI_SLOT(devfn), PCI_FUNC(devfn)); + sprintf(dev->slot_name, "%02x:%02x.%d", bus->number, PCI_SLOT(devfn), PCI_FUNC(devfn)); pci_name_device(dev); pci_read_config_dword(dev, PCI_CLASS_REVISION, &class); class >>= 8; /* upper 3 bytes */ dev->class = class; class >>= 8; - dev->hdr_type = hdr_type; + dev->hdr_type = hdr_type & 0x7f; - switch (hdr_type & 0x7f) { /* header type */ + switch (dev->hdr_type) { /* header type */ case PCI_HEADER_TYPE_NORMAL: /* standard header */ if (class == PCI_CLASS_BRIDGE_PCI) goto bad; /* - * If the card generates interrupts, read IRQ number - * (some architectures change it during pcibios_fixup()) + * Read interrupt line and base address registers. + * The architecture-dependent code can tweak these, of course. */ pci_read_config_byte(dev, PCI_INTERRUPT_PIN, &irq); if (irq) pci_read_config_byte(dev, PCI_INTERRUPT_LINE, &irq); dev->irq = irq; - /* - * read base address registers, again pcibios_fixup() can - * tweak these - */ pci_read_bases(dev, 6, PCI_ROM_ADDRESS); pci_read_config_word(dev, PCI_SUBSYSTEM_VENDOR_ID, &dev->subsystem_vendor); pci_read_config_word(dev, PCI_SUBSYSTEM_ID, &dev->subsystem_device); @@ -468,8 +433,8 @@ break; default: /* unknown header */ bad: - printk(KERN_ERR "PCI: %02x:%02x [%04x/%04x/%06x] has unknown header type %02x, ignoring.\n", - bus->number, dev->devfn, dev->vendor, dev->device, class, hdr_type); + printk(KERN_ERR "PCI: device %s has unknown header type %02x, ignoring.\n", + dev->slot_name, hdr_type); continue; } diff -u --recursive --new-file v2.3.19/linux/drivers/pci/quirks.c linux/drivers/pci/quirks.c --- v2.3.19/linux/drivers/pci/quirks.c Mon Oct 4 15:49:29 1999 +++ linux/drivers/pci/quirks.c Thu Oct 7 12:23:21 1999 @@ -31,7 +31,7 @@ while ((d = pci_find_device(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_82371SB_0, d))) { pci_read_config_byte(d, 0x82, &dlc); if (!(dlc & 1<<1)) { - printk("PCI: PIIX3: Enabling Passive Release on %s\n", d->name); + printk("PCI: PIIX3: Enabling Passive Release on %s\n", d->slot_name); dlc |= 1<<1; pci_write_config_byte(d, 0x82, dlc); } @@ -99,7 +99,7 @@ (f->vendor == dev->vendor || f->vendor == (u16) PCI_ANY_ID) && (f->device == dev->device || f->device == (u16) PCI_ANY_ID)) { #ifdef DEBUG - printk("PCI: Calling quirk %p for %s\n", f->hook, dev->name); + printk("PCI: Calling quirk %p for %s\n", f->hook, dev->slot_name); #endif f->hook(dev); } diff -u --recursive --new-file v2.3.19/linux/drivers/pci/setup.c linux/drivers/pci/setup.c --- v2.3.19/linux/drivers/pci/setup.c Fri Sep 10 23:57:30 1999 +++ linux/drivers/pci/setup.c Thu Oct 7 12:23:21 1999 @@ -16,7 +16,6 @@ #include #include -#include #define DEBUG_CONFIG 0 @@ -108,9 +107,12 @@ (ie. do not respond to memory space writes) when it is left enabled. A good example are QlogicISP adapters. */ - pci_read_config_dword(dev, PCI_ROM_ADDRESS, ®); - reg &= ~PCI_ROM_ADDRESS_ENABLE; - pci_write_config_dword(dev, PCI_ROM_ADDRESS, reg); + if (dev->rom_base_reg) { + pci_read_config_dword(dev, dev->rom_base_reg, ®); + reg &= ~PCI_ROM_ADDRESS_ENABLE; + pci_write_config_dword(dev, dev->rom_base_reg, reg); + dev->resource[PCI_ROM_RESOURCE].flags &= ~PCI_ROM_ADDRESS_ENABLE; + } /* All of these (may) have I/O scattered all around and may not use I/O base address registers at all. So we just have to diff -u --recursive --new-file v2.3.19/linux/drivers/scsi/ChangeLog.ncr53c8xx linux/drivers/scsi/ChangeLog.ncr53c8xx --- v2.3.19/linux/drivers/scsi/ChangeLog.ncr53c8xx Mon Apr 12 09:51:04 1999 +++ linux/drivers/scsi/ChangeLog.ncr53c8xx Thu Oct 7 10:17:09 1999 @@ -1,3 +1,33 @@ +Sat Sep 11 18:00 1999 Gerard Roudier (groudier@club-internet.fr) + * revision 3.2c + - Handle correctly (hopefully) jiffies wrap-around. + - Restore the entry used to detect 875 until revision 0xff. + (I removed it inadvertently, it seems :) ) + - Replace __initfunc() which is deprecated stuff by __init which + is not yet so. ;-) + - Add support of some 'resource handling' for linux-2.3.13. + Basically the BARs have been changed to something more complex + in the pci_dev structure. + - Remove some deprecated code. + +Sat May 10 11:00 1999 Gerard Roudier (groudier@club-internet.fr) + * revision pre-3.2b-1 + - Support for the 53C895A by Pamela Delaney + The 53C895A contains all of the features of the 896 but has only + one channel and has a 32 bit PCI bus. It does 64 bit PCI addressing + using dual cycle PCI data transfers. + - Miscellaneous minor fixes. + - Some additions to the README.ncr53c8xx file. + +Sun Apr 11 10:00 1999 Gerard Roudier (groudier@club-internet.fr) + * revision 3.2a + - Add 'hostid:#id' boot option. This option allows to change the + default SCSI id the driver uses for controllers. + - Remove nvram layouts and driver set-up structures from the C source, + and use the one defined in sym53c8xx_defs.h file. + (shared by both drivers). + - Set for now MAX LUNS to 16 (instead of 8). + Thu Mar 11 23:00 1999 Gerard Roudier (groudier@club-internet.fr) * revision 3.2 (8xx-896 driver bundle) - Only define the host template in ncr53c8xx.h and include the diff -u --recursive --new-file v2.3.19/linux/drivers/scsi/ChangeLog.sym53c8xx linux/drivers/scsi/ChangeLog.sym53c8xx --- v2.3.19/linux/drivers/scsi/ChangeLog.sym53c8xx Mon Apr 12 09:51:04 1999 +++ linux/drivers/scsi/ChangeLog.sym53c8xx Thu Oct 7 10:17:09 1999 @@ -1,3 +1,132 @@ +Sat Sep 11 11:00 1999 Gerard Roudier (groudier@club-internet.fr) + * version sym53c8xx-1.5e + - New linux-2.3.13 __setup scheme support added. + - Cleanup of the extended error status handling: + Use 1 bit per error type. + - Also save the extended error status prior to auto-sense. + - Add the FE_DIFF chip feature bit to indicate support of + diff probing from GPIO3 (825/825A/876/875). + - Remove the quirk handling that has been useless since day one. + - Work-around PCI chips being reported twice on some platforms. + - Add some redundant PCI reads in order to deal with common + bridge misbehaviour regarding posted write flushing. + - Add some other conditionnal code for people who have to deal + with really broken bridges (they will have to edit a source + file to try these options). + - Handle correctly (hopefully) jiffies wrap-around. + - Restore the entry used to detect 875 until revision 0xff. + (I removed it inadvertently, it seems :) ) + - Replace __initfunc() which is deprecated stuff by __init which + is not yet so. ;-) + - Rewrite the MESSAGE IN scripts more generic by using a MOVE + table indirect. Extended messages of any size are accepted now. + (Size is limited to 8 for now, but a constant is just to be + increased if necessary) + - Fix some bug in the fully untested MDP handling:) and share + some code between MDP handling and residual calculation. + - Calculate the data transfer residual as the 2's complement + integer (A positive value in returned on data overrun, and + a negative one on underrun). + - Add support of some 'resource handling' for linux-2.3.13. + Basically the BARs have been changed to something more complex + in the pci_dev structure. + - Remove some deprecated code. + +Sat Jun 5 11:00 1999 Gerard Roudier (groudier@club-internet.fr) + * version sym53c8xx-1.5c + - Donnot negotiate on auto-sense if we are currently using 8 bit + async transfer for the target. + - Only check for SISL/RAID on i386 platforms. + (A problem has been reported on PPC with that code). + - On MSG REJECT for a negotiation, the driver attempted to restart + the SCRIPT processor when this one was already running. + +Sat May 29 12:00 1999 Gerard Roudier (groudier@club-internet.fr) + * version sym53c8xx-1.5b + - Force negotiation prior auto-sense. + This ensures that the driver will be able to grab the sense data + from a device that has received a BUS DEVICE RESET message from + another initiator. + - Complete all disconnected CCBs for a logical UNIT if we are told + about a UNIT ATTENTION for a RESET condition by this target. + - Add the control command 'cleardev' that allows to send a ABORT + message to a logical UNIT (for test purpose). + +Tue May 25 23:00 1999 Gerard Roudier (groudier@club-internet.fr) + * version sym53c8xx-1.5a + - Add support for task abort and bus device reset SCSI message + and implement proper synchonisation with SCRIPTS to handle + correctly task abortion without races. + - Send an ABORT message (if untagged) or ABORT TAG message (if tagged) + when the driver is told to abort a command that is disconnected and + complete the command with appropriate error. + If the aborted command is not yet started, remove it from the start + queue and complete it with error. + - Add the control command 'resetdev' that allows to send a BUS + DEVICE RESET message to a target (for test purpose). + - Clean-up some unused or useless code. + +Fri May 21 23:00 1999 Gerard Roudier (groudier@club-internet.fr) + * version sym53c8xx-1.5 + - Add support for CHMOV with Wide controllers. + - Handling of the SWIDE (low byte residue at the end of a CHMOV + in DATA IN phase with WIDE transfer when the byte count gets odd). + - Handling of the IGNORE WIDE RESIDUE message. + Handled from SCRIPTS as possible with some optimizations when both + a wide device and the controller are odd at the same time (SWIDE + present and IGNORE WIDE RESIDUE message on the BUS at the same time). + - Check against data OVERRUN/UNDERRUN condition at the end of a data + transfer, whatever a SWIDE is present (OVERRUN in DATA IN phase) + or the SODL is full (UNDERRUN in DATA out phase). + - Handling of the MODIFY DATA POINTER message. + This one cannot be handled from SCRIPTS, but hopefully it will not + happen very often. :) + - Large rewrite of the SCSI MESSAGE handling. + +Sun May 9 11:00 1999 Gerard Roudier (groudier@club-internet.fr) + * version sym53c8xx-1.4 + - Support for IMMEDIATE ARBITRATION. + See the README file for detailed information about this feature. + Requires both a compile option and a boot option. + - Minor SCRIPTS optimization in reselection pattern for LUN 0. + - Simpler algorithm to deal with SCSI command starvation. + Just use 2 tag counters in flip/flop and switch to the other + one every 3 seconds. + - Do some work in SCRIPTS after the SELECT instruction and prior + to testing for a PHASE. SYMBIOS say this feature is working fine. + (Btw, only problems with Toshiba 3401B had been reported). + - Measure the PCI clock speed and donnot attach controllers if + result is greater than 37 MHz. Since the precision of the + algorithm (from Stefan Esser) is better than 2%, this should + be fine. + - Fix the misdetection of SYM53C875E (was detected as a 876). + - Fix the misdetection of SYM53C810 not A (was detected as a 810A). + - Support for up to 256 TAGS per LUN (CMD_PER_LUN). + Currently limited to 255 due to Linux limitation. :) + - Support for up to 508 active commands (CAN_QUEUE). + - Support for the 53C895A by Pamela Delaney + The 53C895A contains all of the features of the 896 but has only + one channel and has a 32 bit PCI bus. It does 64 bit PCI addressing + using dual cycle PCI data transfers. + - Miscellaneous minor fixes. + - Some additions to the README.ncr53c8xx file. + +Tue Apr 15 10:00 1999 Gerard Roudier (groudier@club-internet.fr) + * version sym53c8xx-1.3e + - Support for any number of LUNs (64) (SPI2-compliant). + (Btw, this may only be ever usefull under linux-2.2 ;-)) + +Sun Apr 11 10:00 1999 Gerard Roudier (groudier@club-internet.fr) + * version sym53c8xx-1.3d + - Add 'hostid:#id' boot option. This option allows to change the + default SCSI id the driver uses for controllers. + - Make SCRIPTS not use self-mastering for PCI. + There were still 2 places the driver used this feature of the + 53C8XX family. + - Move some data structures (nvram layouts and driver set-up) to + the sym53c8xx_defs.h file. So, the both drivers will share them. + - Set MAX LUNS to 16 (instead of 8). + Sat Mar 20 21:00 1999 Gerard Roudier (groudier@club-internet.fr) * version sym53c8xx-1.3b - Add support for NCR PQS PDS. diff -u --recursive --new-file v2.3.19/linux/drivers/scsi/Makefile linux/drivers/scsi/Makefile --- v2.3.19/linux/drivers/scsi/Makefile Tue Aug 31 17:29:14 1999 +++ linux/drivers/scsi/Makefile Thu Oct 7 10:17:09 1999 @@ -129,6 +129,14 @@ endif endif +ifeq ($(CONFIG_SCSI_SIM710),y) +L_OBJS += sim710.o +else + ifeq ($(CONFIG_SCSI_SIM710),m) + M_OBJS += sim710.o + endif +endif + ifeq ($(CONFIG_A4000T_SCSI),y) L_OBJS += amiga7xx.o 53c7xx.o else @@ -681,6 +689,17 @@ 53c7xx.o : 53c7xx_d.h +sim710_d.h: sim710.scr script_asm.pl + ln -sf sim710.scr fake7.c + $(CPP) -traditional -DCHIP=710 fake7.c | grep -v '^#' | perl -s script_asm.pl -ncr7x0_family + mv script.h sim710_d.h + mv scriptu.h sim710_u.h + rm fake7.c + +sim710_u.h: sim710_d.h + +sim710.o : sim710_d.h + initio.o: ini9100u.c i91uscsi.c $(CC) $(CFLAGS) -c ini9100u.c -o ini9100u.o $(CC) $(CFLAGS) -c i91uscsi.c -o i91uscsi.o diff -u --recursive --new-file v2.3.19/linux/drivers/scsi/README.aic7xxx linux/drivers/scsi/README.aic7xxx --- v2.3.19/linux/drivers/scsi/README.aic7xxx Wed Jun 9 16:59:15 1999 +++ linux/drivers/scsi/README.aic7xxx Thu Oct 7 12:50:23 1999 @@ -20,11 +20,13 @@ AHA-2920C AHA-2930 AHA-2930U + AHA-2930CU AHA-2930U2 AHA-2940 AHA-2940W AHA-2940U AHA-2940UW + AHA-2940UW-PRO AHA-2940AU AHA-2940U2W AHA-2940U2 @@ -37,6 +39,7 @@ AHA-2950U2 AHA-2950U2W AHA-2950U2B + AHA-29160M AHA-3940 AHA-3940U AHA-3940W @@ -45,6 +48,8 @@ AHA-3940U2W AHA-3950U2B AHA-3950U2D + AHA-3960D + AHA-39160M AHA-3985 AHA-3985U AHA-3985W @@ -159,6 +164,12 @@ on your controller. This helps those people who have cards without a SEEPROM make sure that linux and all other operating systems think the same way about your hard drives. + + "aic7xxx=scbram" - Some cards have external SCB RAM that can be used to + give the card more hardware SCB slots. This allows the driver to use + that SCB RAM. Without this option, the driver won't touch the SCB + RAM because it is known to cause problems on a few cards out there + (such as 3985 class cards). "aic7xxx=irq_trigger:x" - Replace x with either 0 or 1 to force the kernel to use the correct IRQ type for your card. This only applies to EISA @@ -464,10 +475,9 @@ FTP sites ------------------------------ ftp://ftp.redhat.com/pub/aic/ - - Primary site for Doug Ledford developed driver releases - ftp://ftp.dialnet.net/pub/linux/aic7xxx - - Temporary mirror of the redhat.com ftp site while people - get used to the new address + - Out of date. I used to keep stuff here, but too many people + complained about having a hard time getting into Red Hat's ftp + server. So use the web site below instead. ftp://ftp.pcnet.com/users/eischen/Linux/ - Dan Eischen's driver distribution area ftp://ekf2.vsb.cz/pub/linux/kernel/aic7xxx/ftp.teleport.com/ @@ -475,10 +485,8 @@ Web sites ------------------------------ - http://developer.redhat.com/aic7xxx/ - - Primary web site maintained by Doug Ledford. I haven't actually - put anything up yet....but I'm planning on it. This information - is put here as an add for the vapor page :) + http://people.redhat.com/dledford/aic7xxx.html + - Primary web site maintained by Doug Ledford. Dean W. Gehnert deang@teleport.com diff -u --recursive --new-file v2.3.19/linux/drivers/scsi/README.ncr53c8xx linux/drivers/scsi/README.ncr53c8xx --- v2.3.19/linux/drivers/scsi/README.ncr53c8xx Mon Apr 12 09:51:04 1999 +++ linux/drivers/scsi/README.ncr53c8xx Thu Oct 7 10:17:09 1999 @@ -1,10 +1,10 @@ -The Linux NCR53C8XX driver README file +The Linux NCR53C8XX/SYM53C8XX drivers README file Written by Gerard Roudier 21 Rue Carnot 95170 DEUIL LA BARRE - FRANCE -10 March 1999 +29 May 1999 =============================================================================== 1. Introduction @@ -25,14 +25,39 @@ 8.6 Clear profile counters 8.7 Set flag (no_disc) 8.8 Set verbose level + 8.9 Reset all logical units of a target + 8.10 Abort all tasks of all logical units of a target 9. Configuration parameters 10. Boot setup commands 10.1 Syntax 10.2 Available arguments + 10.2.1 Master parity checking + 10.2.2 Scsi parity checking + 10.2.3 Scsi disconnections + 10.2.4 Special features + 10.2.5 Ultra SCSI support + 10.2.6 Default number of tagged commands + 10.2.7 Default synchronous period factor + 10.2.8 Negotiate synchronous with all devices + 10.2.9 Verbosity level + 10.2.10 Debug mode + 10.2.11 Burst max + 10.2.12 LED support + 10.2.13 Max wide + 10.2.14 Differential mode + 10.2.15 IRQ mode + 10.2.16 Reverse probe + 10.2.17 Fix up PCI configuration space + 10.2.18 Serial NVRAM + 10.2.19 Check SCSI BUS + 10.2.20 Exclude a host from being attached + 10.2.21 Suggest a default SCSI id for hosts + 10.2.22 Enable use of IMMEDIATE ARBITRATION 10.3 Advised boot setup commands 10.4 PCI configuration fix-up boot option 10.5 Serial NVRAM support boot option 10.6 SCSI BUS checking boot option + 10.7 IMMEDIATE ARBITRATION boot option 11. Some constants and flags of the ncr53c8xx.h header file 12. Installation 13. Architecture dependent features @@ -43,6 +68,8 @@ 14.4 Possible data corruption during a Memory Write and Invalidate 14.5 IRQ sharing problems 15. SCSI problem troubleshooting + 15.1 Problem tracking + 15.2 Understanding hardware error reports 16. Synchonous transfer negotiation tables 16.1 Synchronous timings for 53C875 and 53C860 Ultra-SCSI controllers 16.2 Synchronous timings for fast SCSI-2 53C8XX controllers @@ -69,11 +96,12 @@ It is now available as a bundle of 2 drivers: - ncr53c8xx generic driver that supports all the SYM53C8XX family including - the ealiest 810 rev. 1 and the latest 896 2 channels LVD SCSI controller. + the ealiest 810 rev. 1, the latest 896 (2 channel LVD SCSI controller) and + the new 895A (1 channel LVD SCSI controller). - sym53c8xx enhanced driver (a.k.a. 896 drivers) that drops support of oldest chips in order to gain advantage of new features, as LOAD/STORE intructions available since the 810A and hardware phase mismatch available with the - latest 896. + 896 and the 895A. You can find technical information about the NCR 8xx family in the PCI-HOWTO written by Michael Will and in the SCSI-HOWTO written by @@ -95,15 +123,17 @@ These tools are not ALPHA but quite clean and work quite well. It is essential you have the 'scsiinfo' package. -This short documentation only describes the features of the NCR53C8XX -driver, configuration parameters and control commands available -through the proc SCSI file system read / write operations. +This short documentation describes the features of the generic and enhanced +drivers, configuration parameters and control commands available through +the proc SCSI file system read / write operations. This driver has been tested OK with linux/i386, Linux/Alpha and Linux/PPC. Latest driver version and patches are available at: ftp://ftp.tux.org/pub/people/gerard-roudier +or + ftp://ftp.symbios.com/mirror/ftp.tux.org/pub/tux/roudier/drivers I am not a native speaker of English and there are probably lots of mistakes in this README file. Any help will be welcome. @@ -136,6 +166,7 @@ 875 Y Y FAST20 40 MB/s Y Y 876 Y Y FAST20 40 MB/s Y Y 895 Y Y FAST40 80 MB/s Y Y +895A Y Y FAST40 80 MB/s Y Y 896 Y Y FAST40 80 MB/s Y Y @@ -156,21 +187,25 @@ 3.1 Optimized SCSI SCRIPTS. -The 810A, 825A, 875, 895 and newest 896 support new SCSI SCRIPTS instructions -named LOAD and STORE that allow to move 1 DWORD from/to an IO register to/from -memory much faster that the MOVE MEMORY instruction that is supported by the -53c7xx and 53c8xx family. The LOAD/STORE instructions support absolute and -DSA relative addressing modes. The SCSI SCRIPTS had been entirely rewritten -using LOAD/STORE instead of MOVE MEMORY instructions. +The 810A, 825A, 875, 895, 896 and 895A support new SCSI SCRIPTS instructions +named LOAD and STORE that allow to move up to 1 DWORD from/to an IO register +to/from memory much faster that the MOVE MEMORY instruction that is supported +by the 53c7xx and 53c8xx family. +The LOAD/STORE instructions support absolute and DSA relative addressing +modes. The SCSI SCRIPTS had been entirely rewritten using LOAD/STORE instead +of MOVE MEMORY instructions. 3.2 New features of the SYM53C896 (64 bit PCI dual LVD SCSI controller) -The 896 allows to handle the phase mismatch context saving from SCRIPTS -(avoids the phase mismatch interrupt that stops the SCSI processor +The 896 and the 895A allows handling of the phase mismatch context from +SCRIPTS (avoids the phase mismatch interrupt that stops the SCSI processor until the C code has saved the context of the transfer). Implementing this without using LOAD/STORE instructions would be painfull -and I did'nt even try it. This chip also supports 64 bit PCI transactions -and addressing. The SCRIPTS processor is not true 64 bit, but uses segment +and I did'nt even want to try it. + +The 896 chip supports 64 bit PCI transactions and addressing, while the +895A supports 32 bit PCI transactions and 64 bit addressing. +The SCRIPTS processor of these chips is not true 64 bit, but uses segment registers for bit 32-63. Another interesting feature is that LOAD/STORE instructions that address the on-chip RAM (8k) remain internal to the chip. @@ -219,9 +254,13 @@ is currently set to 8 by default. This value is suitable for most SCSI disks. With large SCSI disks (>= 2GB, cache >= 512KB, average seek time <= 10 ms), using a larger value may give better performances. -The driver supports up to 64 commands per device, but using more than -32 is generally not worth it, unless you are using a very large disk -or disk array. + +The sym53c8xx driver supports up to 255 commands per device, and the +generic ncr53c8xx driver supports up to 64, but using more than 32 is +generally not worth-while, unless you are using a very large disk or disk +array. It is noticeable that most of recent hard disks seem not to accept +more than 64 simultaneous commands. So, using more than 64 queued commands +is probably just resource wasting. If your controller does not have NVRAM or if it is managed by the SDMS BIOS/SETUP, you can configure tagged queueing feature and device queue @@ -491,6 +530,24 @@ The driver default verbose level is 1. This command allows to change th driver verbose level after boot-up. +8.9 Reset all logical units of a target + + resetdev + + target: target number + The driver will try to send a BUS DEVICE RESET message to the target. + (Only supported by the SYM53C8XX driver and provided for test purpose) + +8.10 Abort all tasks of all logical units of a target + + cleardev + + target: target number + The driver will try to send a ABORT message to all the logical units + of the target. + (Only supported by the SYM53C8XX driver and provided for test purpose) + + 9. Configuration parameters If the firmware of all your devices is perfect enough, all the @@ -566,10 +623,11 @@ Setup commands can be passed to the driver either at boot time or as a string variable using 'insmod'. -A boot setup command for the ncr53c8xx driver begins with the driver name -"ncr53c8xx=". The kernel syntax parser then expects an optionnal list of -integers separated with comma followed by an optionnal list of comma- -separated strings. Example of boot setup command under lilo prompt: +A boot setup command for the ncr53c8xx (sym53c8xx) driver begins with the +driver name "ncr53c8xx="(sym53c8xx). The kernel syntax parser then expects +an optionnal list of integers separated with comma followed by an optional +list of comma-separated strings. Example of boot setup command under lilo +prompt: lilo: linux root=/dev/hda2 ncr53c8xx=tags:4,sync:10,debug:0x200 @@ -582,7 +640,7 @@ The following command will install driver module with the same options as above. -insmod ncr53c8xx.o ncr53c8xx="tags:4 sync:10 debug:0x200" + insmod ncr53c8xx.o ncr53c8xx="tags:4 sync:10 debug:0x200" For the moment, the integer list of arguments is discarded by the driver. It will be used in the future in order to allow a per controller setup. @@ -590,40 +648,53 @@ Each string argument must be specified as "keyword:value". Only lower-case characters and digits are allowed. +In a system that contains multiple 53C8xx adapters insmod will install the +specified driver on each adapter. To exclude a chip use the 'excl' keyword. + +The sequence of commands, + + insmod sym53c8xx sym53c8xx=excl:0x1400 + insmod ncr53c8xx + +installs the sym53c8xx driver on all adapters except the one at IO port +address 0x1400 and then installs the ncr53c8xx driver to the adapter at IO +port address 0x1400. + + 10.2 Available arguments -Master parity checking - mpar:y enabled - mpar:n disabled - -Scsi parity checking - spar:y enabled - spar:n disabled - -Scsi disconnections - disc:y enabled - disc:n disabled +10.2.1 Master parity checking + mpar:y enabled + mpar:n disabled + +10.2.2 Scsi parity checking + spar:y enabled + spar:n disabled + +10.2.3 Scsi disconnections + disc:y enabled + disc:n disabled -Special features +10.2.4 Special features Only apply to 810A, 825A, 860, 875 and 895 controllers. Have no effect with other ones. - specf:y (or 1) enabled - specf:n (or 0) disabled - specf:3 enabled except Memory Write And Invalidate + specf:y (or 1) enabled + specf:n (or 0) disabled + specf:3 enabled except Memory Write And Invalidate The default driver setup is 'specf:3'. As a consequence, option 'specf:y' must be specified in the boot setup command to enable Memory Write And Invalidate. -Ultra SCSI support +10.2.5 Ultra SCSI support Only apply to 860, 875 and 895 controllers. Have no effect with other ones. - ultra:2 Ultra2 enabled - ultra:1 Ultra enabled - ultra:n disabled - -Default number of tagged commands - tags:0 (or tags:1 ) tagged command queuing disabled - tags:#tags (#tags > 1) tagged command queuing enabled + ultra:2 Ultra2 enabled + ultra:1 Ultra enabled + ultra:n disabled + +10.2.6 Default number of tagged commands + tags:0 (or tags:1 ) tagged command queuing disabled + tags:#tags (#tags > 1) tagged command queuing enabled #tags will be truncated to the max queued commands configuration parameter. This option also allows to specify a command queue depth for each device that support tagged command queueing. @@ -635,9 +706,9 @@ - controller #1 target #1 logical unit #2 -> 32 commands, - all other logical units (all targets, all controllers) -> 10 commands. -Default synchronous period factor - sync:255 disabled (asynchronous transfer mode) - sync:#factor +10.2.7 Default synchronous period factor + sync:255 disabled (asynchronous transfer mode) + sync:#factor #factor = 10 Ultra-2 SCSI 40 Mega-transfers / second #factor = 11 Ultra-2 SCSI 33 Mega-transfers / second #factor < 25 Ultra SCSI 20 Mega-transfers / second @@ -646,19 +717,19 @@ In all cases, the driver will use the minimum transfer period supported by controllers according to NCR53C8XX chip type. -Negotiate synchronous with all devices - (force sync nego) - fsn:y enabled - fsn:n disabled - -Verbosity level - verb:0 minimal - verb:1 normal - verb:2 too much - -Debug mode - debug:0 clear debug flags - debug:#x set debug flags +10.2.8 Negotiate synchronous with all devices + (force sync nego) + fsn:y enabled + fsn:n disabled + +10.2.9 Verbosity level + verb:0 minimal + verb:1 normal + verb:2 too much + +10.2.10 Debug mode + debug:0 clear debug flags + debug:#x set debug flags #x is an integer value combining the following power-of-2 values: DEBUG_ALLOC 0x1 DEBUG_PHASE 0x2 @@ -677,10 +748,10 @@ You can play safely with DEBUG_NEGO. However, some of these flags may generate bunches of syslog messages. -Burst max - burst:0 burst disabled - burst:255 get burst length from initial IO register settings. - burst:#x burst enabled (1<<#x burst transfers max) +10.2.11 Burst max + burst:0 burst disabled + burst:255 get burst length from initial IO register settings. + burst:#x burst enabled (1<<#x burst transfers max) #x is an integer value which is log base 2 of the burst transfers max. The NCR53C875 and NCR53C825A support up to 128 burst transfers (#x = 7). Other chips only support up to 16 (#x = 4). @@ -688,42 +759,42 @@ and revision ids. By default the driver uses the maximum value supported by the chip. -LED support - led:1 enable LED support - led:0 disable LED support +10.2.12 LED support + led:1 enable LED support + led:0 disable LED support Donnot enable LED support if your scsi board does not use SDMS BIOS. (See 'Configuration parameters') -Max wide - wide:1 wide scsi enabled - wide:0 wide scsi disabled +10.2.13 Max wide + wide:1 wide scsi enabled + wide:0 wide scsi disabled Some scsi boards use a 875 (ultra wide) and only supply narrow connectors. If you have connected a wide device with a 50 pins to 68 pins cable converter, any accepted wide negotiation will break further data transfers. In such a case, using "wide:0" in the bootup command will be helpfull. -Differential mode - diff:0 never set up diff mode - diff:1 set up diff mode if BIOS set it - diff:2 always set up diff mode - diff:3 set diff mode if GPIO3 is not set - -IRQ mode - irqm:0 always open drain - irqm:1 same as initial settings (assumed BIOS settings) - irqm:2 always totem pole - irqm:0x10 driver will not use SA_SHIRQ flag when requesting irq - irqm:0x20 driver will not use SA_INTERRUPT flag when requesting irq +10.2.14 Differential mode + diff:0 never set up diff mode + diff:1 set up diff mode if BIOS set it + diff:2 always set up diff mode + diff:3 set diff mode if GPIO3 is not set + +10.2.15 IRQ mode + irqm:0 always open drain + irqm:1 same as initial settings (assumed BIOS settings) + irqm:2 always totem pole + irqm:0x10 driver will not use SA_SHIRQ flag when requesting irq + irqm:0x20 driver will not use SA_INTERRUPT flag when requesting irq (Bits 0x10 and 0x20 can be combined with hardware irq mode option) -Reverse probe - revprob:n probe chip ids from the PCI configuration in this order: - 810, 815, 820, 860, 875, 885, 895, 896 - revprob:y probe chip ids in the reverse order. +10.2.16 Reverse probe + revprob:n probe chip ids from the PCI configuration in this order: + 810, 815, 820, 860, 875, 885, 895, 896 + revprob:y probe chip ids in the reverse order. -Fix up PCI configuration space - pcifix: