LDP/LDP/howto/linuxdoc/Plug-and-Play-HOWTO.sgml

1949 lines
104 KiB
Plaintext

<!doctype linuxdoc system>
<article>
<title> Plug-and-Play-HOWTO </title>
<author>David S.Lawyer
<tt><url url="mailto:dave@lafn.org"></tt>
<date> v1.07, August 2003
<!--
Revision history:
v1.07 August 2003: New M$ url, reserve resources for isa-pnp, lspci+,
scanport may not find hdw, finding dev. and config.
v1.06 September 2002: Revised about telling the BIOS if the OS is PnP
v1.05 July 2002: typos: or => of, and => an, A Allocate => Allocate,
programs => program; Dell PCs: "Plug and Play Configuration Error",
clarity on telling BIOS if your OS is PnP, "Intro to PnP" had truncated
sentence, routing IRQs on PCI clarified, Change of emphasis in entire
doc: Linux is now a PnP OS (sort of), PCI has almost replaced ISA
v1.04 March 2002 finding a device driver, PCI serial ports,
alias example in modules.conf, PnP needed for linmodems
v1.03 August 2001: error messages, boot-prompt parameters
v1.02 July 2001: PCI config regs.
v1.01 April 2001: less shortage today of bus-resources, clarity in sect. 2,
Windows 2000 OK (even if "not a PnP OS" in CMOS)
v1.00 November 2000: "skip file" workaround for reconfiguring under Windows.
PCI interrupt details: X, W were transposed, rewrote, mentioned MSI,
etc. General Introduction added. Revised "How Linux Does PnP",
etc.. Patching kernel to make it PnP no longer feasible. Drivers do
more now due to kernel-provided functions.
v0.12 June 2000 scanpci, workaround for Dos zeroing PCI IRQs.
v0.11 May 2000 scanport utility, many typos fixed, setpci hard to use
v0.10 2 March 2000 typo: /bus/pnp/devices, lspci+, book "Programming
..."
v0.09 /proc/bus/pci/devices too cryptic,
v0.08 my new email
v0.07 in Windows: remove devices
v0.06 Oct. 1999 in Windows: forced+, legacy into ESCD, pause key (bios)
v0.05 Aug. 1999 lspci, url for isapnp, tell the dev. driver, PCI still
needs PnP
v0.04 June 1999 alternatives to reinstall Windows?, add D.D. url
v0.03 May 1999 typos, reinstall Windows, clarity, removed D.D. url
v0.02 Apr. 1999 /proc/... doesn't show hdw config (except pci)
v0.01 Mar. 1999 serial PnP spec, PCI interrupts, no DMA on PCI,
dumpregs for pnpdump , Bus Mastering DMA, clarity rewrites, pciutils
kernel 2.2 /proc tree, IO range check, Windows may not update ESCD
v0.00 Nov. 1998
-->
<abstract>
Help with understanding and dealing with the complex Plug-and-Play
(PnP) issue. How to get PnP to work on your PC (if it doesn't already).
It doesn't cover what's called "Universal Plug and Play"
(UPnP). See <ref id="UPnP_" name="Universal Plug and Play (UPnP)"
</abstract>
<toc>
<sect> Introduction
<sect1>1. Copyright, Trademarks, Disclaimer, & Credits
<sect2> Copyright
<p> Copyright (c) 1998-2003 by David S. Lawyer <url url="mailto:dave@lafn.org">
<!-- license.D begin -->
Please freely copy and distribute (sell or give away) this document
in any format. Send any corrections and comments to the document
maintainer. You may create a derivative work and distribute it
provided that you:
<enum>
<item> If it's not a translation: Email a copy of your derivative work
(in a format LDP accepts) to the author(s) and maintainer (could be
the same person). If you don't get a response then email the LDP
(Linux Documentation Project): submit@en.tldp.org.
<item>License the derivative work in the spirit of this license or use
GPL. Include a copyright notice and at least a pointer to the
license used.
<item>Give due credit to previous authors and major contributors.
</enum>
If you're considering making a derived work other than a
translation, it's requested that you discuss your plans with the
current maintainer.
<sect2>Disclaimer
<p> While I haven't intentionally tried to mislead you, there are
likely a number of errors in this document. Please let me know about
them. Since this is free documentation, it should be obvious that I
cannot be held legally responsible for any errors.
<sect2>Trademarks.
<p> Any brand names (starts with a capital letter such as MS Windows)
should be assumed to be a trademark). Such trademarks belong to their
respective owners. <!-- license.D end -->
<sect2> Credits
<p>
<itemize>
<item> Daniel Scott proofread this in March 2000 and found many
typos, etc.
<item> Pete Barrett gave a workaround to prevent Windows from zeroing
PCI IRQs.
</itemize>
<sect1> Future Plans; You Can Help
<p> Please let me know of any errors in facts, opinions, logic,
spelling, grammar, clarity, links, etc. But first, if the date is
over a couple of months old, check to see that you have the latest
version. Please send me any info that you think belongs in this
document.
I haven't studied the code used by various Linux drivers to implement
Plug-and-Play. Nor have I looked into the details of how the kernel
deals with it. Thus this HOWTO is still incomplete. It needs to
explain more about the PCI bus and about "hot swapping". It likely
has some inaccuracies (let me know where I'm wrong). In this HOWTO
I've sometimes used ?? to indicate that I don't really know the
answer.
<sect1> New Versions of this HOWTO
<p> New versions of the Plug-and-Play-HOWTO should appear every few
months or so and will be available to browse and/or download at LDP
mirror sites. For a list of mirror sites see: <url
url="http://tldp.org/mirrors.html">. Various formats are
available. If you only want to quickly check the date of the latest
version look at: <url
url="http://tldp.org/HOWTO/Plug-and-Play-HOWTO.html">. The
version you are now reading is: v1.07, August 2003 .
<sect1> New in Recent Versions
<p> For a full revision history going back to the first version see
the source file (in linuxdoc format) at <url
url="http://www.ibiblio.org/pub/linux/docs/HOWTO/other-formats/sgml/Plug-and-Play-HOWTO.sgml.gz">.
v1.07 August 2003: New M$ url, reserve resources for isa-pnp, lspci+,
scanport may not find hdw, finding dev. and config.
v1.06 September 2002: Revised about telling the BIOS if the OS is
PnP<newline>
v1.05 July 2002 typos: or => of, and => an, A Allocate => Allocate,
programs => program; Dell PCs: "Plug and Play Configuration Error",
clarity on telling BIOS if your OS is PnP, "Intro to PnP" had truncated
sentence, routing IRQs on PCI clarified, Change of emphasis in entire
doc: Linux is now a PnP OS (sort of), PCI has almost replaced
ISA<newline>
The version 1.0 (Nov. 2000) was long overdue and recognized that the
kernel is doing more in helping device drivers set up PnP. Kernel 2.4
is significantly improved in this respect. There's still a lot of
improvement needed in both this HOWTO and the way that Linux does
PnP.
<sect1> General Introduction. Do you need this HOWTO?
<p> Plug-and-play (PnP) is a system which automatically detects
devices such as disks, sound cards, ethernet cards, modems, etc. It
also does some low-level configuring of them. To be detected by PnP, the
device must be designed for PnP. Non-PnP devices (or PnP devices which
have been correctly PnP-configured), can often be detected by
non-PnP methods. The modern PCI bus is inherently PnP while the old
ISA bus originally wasn't PnP but had PnP support added to it later.
So often PnP is used to only mean PnP for the old ISA bus. In this
HOWTO, PnP means PnP for both the ISA and the PCI bus.
As time goes by the Linux kernel is becoming better at supporting PnP.
In the 20th century, one could say that Linux was not really a PnP OS.
But it's becoming a PnP OS even thought it still doesn't have a fully
centralized plug-and-play system. It does provide programs that
device drivers can call on to do their own plug-and-play. The kernel
also reads all configuration registers of all devices and maintains a
table of them that device drivers can consult. Many drivers take
advantage of this and find your PnP devices OK. The BIOS hardware of
your PC likely may also do some plug-and-play work. Thus if
everything works OK PnP-wise, you can use your computer without
needing to know anything about plug-and-play. But if some devices
which are supported by Linux don't work (because they're not discovered
or configured correctly by PnP) then you may need to read some of this
HOWTO. You'll learn not only about PnP but also learn about how
communication takes place inside the computer.
If you're having problems with a device, watch the messages displayed
at boot-time (go back thru them using Shift-PageUp). Check to see that you
have the right driver for a device, and that the driver is being found
and used. If the driver is a module, type "lsmod" (as the root user)
to see it it's loaded (in use). If it's not a module then it should
be built into the kernel. There should be a file somewhere that tells
what drivers are built into the kernel: (such as: /boot/config-2.4-20
in Debian). Sometimes a device name (such as /dev/eth0) doesn't get a
driver assigned to it unless the assignment is found in the file:
/etc/modules.conf: For example, to assign the "tulip" driver to eth0
you add a line to this file: "alias eth0 tulip".
This HOWTO doesn't cover the problem of finding and installing device
drivers. Perhaps it should. One problem is that a certain brand of a
card (or other physical device) may not say what kind of chips are
used in it. The driver name is often the same as the chip name and
not the brand name. One way to start to check on a driver is to see
if it is discussed in the kernel documentation, in another HOWTO, or
on the Internet. Warning: Such documentation may be out of date.
In this document I mention so many things that can go wrong that one
who believes in Murphy's Law (If something can go wrong it will) may
become quite alarmed. But for PnP for most people: If something can
go wrong it usually doesn't. Remember that sometimes problems which
seem to be PnP related are actually due to defective hardware or to
hardware that doesn't fully conform to PnP specs.
<sect> What PnP Should Do: Allocate "Bus-Resources"
<sect1> What is Plug-and-Play (PnP)?
<p> If you don't understand this section, read the next section
<ref id="find_dev" name="How a Computer Finds Devices (and
conversely)">
<p> Oversimplified, Plug-and-Play automatically tells the software
(device drivers) where to find various pieces of hardware (devices)
such as modems, network cards, sound cards, etc. Plug-and-Play's task
is to match up physical devices with the software (device drivers)
that operates them and to establish channels of communication between
each physical device and its driver. In order to achieve this, PnP
allocates the following "bus-resources" to both drivers and hardware:
I/O addresses, memory regions, IRQs, DMA channels (ISA bus only).
These 4 things are sometimes called "1st order resources" or just
"resources". If you don't understand what these 4 bus-resources are,
read the following subsections of this HOWTO: I/O Addresses, IRQs, DMA
Channels, Memory Regions. An article in Linux Gazette regarding 3 of
these bus-resources is <htmlurl
url="http://www.linuxgazette.com/issue38/blanchard.html"
name="Introduction to IRQs, DMAs and Base Addresses">. Once these
bus-resources have been assigned (and if the correct driver is
installed), the "files" for such devices in the /dev directory are
ready to use.
This PnP assignment of bus-resources is sometimes called "configuring"
but it is only a low level type of configuring. The /etc directory
has many configuration files but most of them are not for PnP
configuring. So most of the configuring of hardware devices has
nothing to do with PnP or bus-resources. For, example the
initializing of a modem by an "init string" or setting it's speed is
not PnP. Thus when talking about PnP, "configuring" means only a
certain type of configuring. While other documentation (such a for MS
Windows) simply calls bus-resources "resources", I have used the term
"bus-resources" so as to distinguish it from the multitude of other
kinds of resources.
<sect1> How a Computer Finds Devices (and conversely) <label
id="find_dev">
<p> A computer consists of a CPU/processor to do the computing and RAM
memory to store programs and data (for fast access). In addition,
there are a number of devices such as various kinds of disk-drives, a
video card, a keyboard, network cards, modem cards, sound cards, the
USB bus, serial and parallel ports, etc. There is also a power supply
to provide electric energy, various buses on a motherboard to connect
the devices to the CPU, and a case to put all this into.
In olden days most all devices had their own plug-in cards (printed
circuit boards). Today, in addition to plug-in cards, many "devices"
are small chips permanently mounted on the "motherboard".
Furthermore, cards which plug into the motherboard may contain more
than one device. Memory chips are also sometimes considered to be
devices but are not plug-and-play in the sense used in this HOWTO.
For the computer system to work right, each device must be under the
control of its "device driver". This is software which is a part of
the operating system (perhaps loaded as a module) and runs on the CPU.
Device drivers are associated with "special files" in the /dev
directory although they are not really files. They have names such as
hda3 (third partition on hard drive a), ttyS1 (the second serial port),
eth0 (the first ethernet card), etc.
To make matters more complicated, the particular device driver
selected, say for example eth0, may depend on the type of ethernet
card you have. Thus eth0 can't just be assigned to any ethernet
driver. It must be assigned to a certain driver that will work for
the type of ethernet card you have installed. If the driver is a
module, some of these assignments might be found in /etc/modules.conf
(called "alias") while others may reside in an internal kernel table.
For example, if you have an ethernet card that uses the "tulip" chip
put "alias eth0 tulip" into /etc/modules.conf so that when your
computer asks for eth0 it finds the tulip driver. Other device names
may have a standard driver associated with them so the above isn't
always required.
To control a device, the CPU (under the control of the device driver)
sends commands and data to, and reads status and data from the
various devices. In order to do this each device driver must know the
address of the device it controls. Knowing such an address is
equivalent to setting up a communication channel, even though the
physical "channel" is actually the data bus inside the PC which is
shared with almost everything else.
This communication channel is actually a little more complex than
described above. An "address" is actually a range of addresses so
that sometimes the word "range" is used instead of "address". There
could even be more that one range (with no overlapping) for a single
device. Also, there is a reverse part of the channel (known as
interrupts) which allows devices to send an urgent "help" request to
their device driver.
<sect1> Addresses
<p> PCs have 3 address spaces: I/O, main memory (IO memory), and
configuration (except that the old ISA bus lacks a genuine
"configuration" address space). All of these 3 types of addresses
share the same bus inside the PC. But the presence or absence of
voltage on certain dedicated wires on the PC's bus tells which "space"
an address is in: I/O, main memory, (see <ref id="mem_" name="Memory
Ranges">), or configuration. See <ref id="address_details"
name="Address Details"> for more details. Only two of these 3 address
spaces are used for device I/O: I/0 and main memory. I/O stands for
Input-Output.
<sect1> I/O Addresses and Allocating Them
<p> Devices were originally located in I/O address space but today
they may use space in main memory. An I/0 address is sometimes just
called "I/O", "IO", "i/o" or "io". The terms "I/O port" or "I/O
range" are also used. Don't confuse these IO ports with "IO memory"
located in main memory. There are two main steps to allocate the I/O
addresses (or some other bus-resources such as interrupts on the ISA
bus):
<enum>
<item> Set the I/O address, etc. on the card (in one of its registers)
<item> Let its device driver know what this I/O address, etc. is
</enum>
Often, the device driver does both of these.
The two step process above is something like the two part problem of
finding someone's house number on a street. Someone must install a
number on the front of the house so that it may be found and then you
must obtain (and write down) this house number so that you can find
the house. In computers the device hardware must first get the
address it will use set a special register and then the device driver
must obtain this address. Both of these must be done, either
automatically by software or by entering the data manually into files.
Problems may occur when only one of them gets done (or is attempted).
For manual PnP configuration some people make the mistake of doing
only one of these and then wonder why the computer can't find the
device. For example, they may use "setserial" to assign an address
to a serial port without realizing that this only tells the driver an
address. It doesn't set the address in the serial port hardware
itself. If the serial port hardware doesn't have the address you told
setserial (or doesn't have any address set in it) then you're in
trouble.
An obvious requirement is that before the device driver can use an
address it must be first set in the physical device (such as a card).
Since device drivers often start up soon after you start the computer,
they sometimes try to access a card (to see if it's there, etc.)
before the address has been set in the card by a PnP configuration
program. Then you see an error message that they can't find the card
even though it's there (but doesn't yet have an address).
What was said in the last few paragraphs regarding I/O addresses applies
with equal force to most other bus-resources: <ref id="mem_" name="Memory
Ranges">, <ref id="interrupt_over" name="IRQs --Overview"> and <ref
id="dma_" name="DMA Channels">. What these are will be explained in
the next 3 sections. The exception is that IRQs on the PCI bus are
not set by a card register but are set by a special routing chip on
the motherboard.
<sect1> Memory Ranges <label id="mem_">
<p> Many devices are assigned address space in main memory. It's
sometimes called "shared memory" or "memory-mapped IO" or "IO memory".
This memory is physically located in the device. When discussing
bus-resources it's often just called "memory", "mem", or "iomem". In
addition to using such "memory", such a device might also use
conventional IO address space. To see what mem is in use on your
computer, look at /proc/iomem. This "file" includes the memory range
used by your ordinary RAM memory chips but this really not strictly a
part of iomem.
When you insert a card that uses iomem, you are in effect also
inserting a memory module for main memory. A high address is selected
for it by PnP so that it doesn't conflict with main memory chips.
This memory can either be ROM (Read Only Memory) or shared memory.
Shared memory is shared between the device and the CPU (running the
device driver) just as IO address space is shared between the device
and the CPU. This shared memory serves as a means of data "transfer"
between the device and main memory. It's IO but it's not done in IO
space. Both the card and the device driver need to know where it is.
ROM is different. It is likely a program (perhaps a device driver)
which will be used with the device. It could be initialization code
so that a device driver is still required. Hopefully, it will work
with Linux and not just MS Windows. It may need to be shadowed
which means that it is copied to your main memory chips in order to
run faster. Once it's shadowed it's no longer "read only".
<sect1> IRQs --Overview <label id="interrupt_over">
<p> After reading this you may read <ref id="interrupt_detail" name=
"Interrupts --Details"> for many more details. The following is
intentionally oversimplified: Besides the address, there is also an
interrupt number to deal with (such as IRQ 5). It's called an IRQ
(Interrupt ReQuest) number or just an "irq" for short. We already
mentioned above that the device driver must know the address of a card
in order to be able to communicate with it.
But what about communication in the opposite direction? Suppose the
device needs to tell its device driver something immediately? For
example, the device may have just received a lot of bytes destined for
main memory and the device needs to tell its driver to fetch these
bytes at once and transfer them from the device's nearly full buffer
into main memory. Another example is to signal the driver that the
device has finished sending out a bunch of bytes and is now waiting
for some more bytes from the driver so it can send them too.
How should the device rapidly signal its driver? It may not be able
to use the main data bus since it's likely already in use. Instead it
puts a voltage on a dedicated interrupt wire (part of the bus) which
is often reserved for that device alone. This voltage signal is
called an Interrupt ReQuest (IRQ) or just an "interrupt" for short.
There are the equivalent of 16 such wires in a PC and each wire leads
(indirectly) to a certain device driver. Each wire has a unique IRQ
(Interrupt ReQuest) number. The device must put its interrupt on the
correct wire and the device driver must listen for the interrupt on
the correct wire. Which wire the device sends help requests on is
determined by the IRQ number stored in the device. This same IRQ
number must be known to the device driver so that the device driver
knows which IRQ line to listen on.
Once the device driver gets the interrupt from the device it must find
out why the interrupt was issued and take appropriate action to
service the interrupt. On the ISA bus each device usually needs its
own unique IRQ number. For the PCI bus and other special cases the
sharing of IRQs is allowed and the IRQ assignment is determined by a
programmable routing chip. See <ref id="interrupt_detail" name=
"Interrupts --Details"> for how this works.
<sect1> DMA Channels <label id="dma_"> (ISA bus only)
<p> DMA channels are only for the ISA bus. DMA stands for "Direct Memory
Access". This is where a device is allowed to take over the main
computer bus from the CPU and transfer bytes directly to main memory.
Normally the CPU would make such a transfer in a two step process:
<enum>
<item>reading from the I/O memory space of the device and putting these
bytes into the CPU itself
<item> writing these bytes from the CPU to main memory
</enum>
<enum>
<item> With DMA it's usually a one step process of sending the bytes
directly from the device to memory
</enum>
The device must have such capabilities built into its hardware and
thus not all devices can do DMA. While DMA is going on the CPU can't
do too much since the main bus is being used by the DMA transfer.
The PCI bus doesn't really have any DMA but instead it has something
even better: bus mastering. It works something like DMA and is
sometimes called DMA (for example, hard disk drives that call
themselves "UltraDMA"). It allows devices to temporarily become bus
masters and to transfer bytes almost like the bus master was the CPU.
It doesn't use any channel numbers since the organization of the PCI
bus is such that the PCI hardware knows which device is currently the
bus master and which device is requesting to become a bus master.
Thus there is no resource allocation of DMA channels for the PCI bus.
When a device on the ISA bus wants to do DMA it issues a DMA-request
using dedicated DMA request wires much like an interrupt request. DMA
actually could have been handled by using interrupts but this would
introduce some delays so it's faster to do it by having a special type
of interrupt known as a DMA-request. Like interrupts, DMA-requests
are numbered so as to identify which device is making the request.
This number is called a DMA-channel. Since DMA transfers all use the
main bus (and only one can run at a time) they all actually use the
same channel but the "DMA channel" number serves to identify who is
using the "channel". Hardware registers exist on the motherboard
which store the current status of each "channel". Thus in order to
issue a DMA-request, the device must know its DMA-channel number which
must be stored in a special register on the physical device.
<sect1> "Resources" for both Device and Driver
<p> Thus device drivers must be "attached" in some way to the hardware
they control. This is done by allocating bus-resources (I/O, Memory,
IRQ's, DMA's) to both the physical device and the device driver
software. For example, a serial port uses only 2 (out of 4 possible)
resources: an IRQ and an I/O address. Both of these values must be
supplied to the device driver and the physical device. The driver
(and its device) is also given a name in the /dev directory (such as
ttyS1). The address and IRQ number is stored by the physical device
in configuration registers on its card (or in a chip on the
motherboard). For the case of jumpers, it's the location of the
jumpers themselves that store the bus-resource configuration in the
device hardware (on the card, etc.). For the case of PnP, the
configuration register data is usually lost when the PC is powered
down (turned off) so that the bus-resource data must be supplied to
each device anew each time the PC is powered on.
<sect1> The Problem
<p> The architecture of the PC provides only a limited number of
IRQ's, DMA channels, I/O address, and memory regions. If there were
only several devices and they all had standardized bus-resource data
(such as unique I/O addresses and IRQ numbers) there would be no
problem of attaching device drivers to devices. Each device would
have a fixed resources which would not conflict with any other device
on your computer. No two devices would have the same addresses, there
would be no IRQ conflicts, etc. Each driver would be programmed with
the unique addresses, IRQ, etc. hard-coded into the program. Life
would be simple.
But it's not. Not only are there so many different devices today that
conflicts are frequent, but one sometimes needs to have more than one of
the same type of device. For example, one may want to have a few
different disk-drives, a few network cards, etc. For these reasons
devices need to have some flexibility so that they can be set to
whatever address, IRQ, etc. is needed to avoid conflicts. But some
IRQ's and addresses are pretty standard such as the ones for the clock
and keyboard. These don't need such flexibility.
Besides the problem of conflicting allocation of bus-resources, there
is a problem of making a mistake in telling the device driver what the
bus-resources are for the case of manual configuration. For example,
suppose that you enter IRQ 4 in a configuration file when the device
is actually set at IRQ 5. This is another type of bus-resource
allocation error.
The allocation of bus-resources, if done correctly, establishes
channels of communication between physical hardware and their device
drivers. For example, if a certain I/O address range (resource) is
allocated to both a device driver and a piece of hardware, then this
has established a one-way communication channel between them. The
driver may send commands and other info to the device. It's actually a
little more than one-way since the driver may get information from the
device by reading its registers. But the device can't initiate any
communication this way. To initiate communication the device needs an
IRQ so it can send interrupts to its driver. This creates a two-way
communication channel where both the driver and the physical device
can initiate communication.
<sect1> PnP Finds Devices Plugged Into Serial Ports
<p> External devices that connect to the serial port via a cable (such
as external modems) can also be called Plug-and-Play. Since only the
serial port itself needs bus-resources (an IRQ and I/O address) there are
no bus-resources to allocate to such plug-in devices. In this case,
PnP is used only to identify the modem (read it's model code number).
This could be important if the modem is a software modem (linmodem)
and requires a special driver. There is a special PnP specification
for such external serial devices (something connected to the serial
port).
Linux doesn't support this yet ?? For a hardware modem, the ordinary
serial driver will work OK so there's little need for using the
special serial PnP to find a driver. You still need to tell the
communications program what port (such as /dev/ttyS1) the modem is on.
With PnP you wouldn't need to even do this. With the advent of
software modems that have Linux drivers (linmodems), it would be nice
to have the appropriate driver install itself automatically via PnP.
<sect> The Plug-and-Play (PnP) Solution
<sect1> Introduction to PnP
<p> The term Plug-and-Play (PnP) has various meanings. In the broad
sense it is just auto-configuration where one just plugs in a device
and it configures itself. In the sense used in this HOWTO, the
configuration is only that of configuring PnP bus-resources and letting
the device drivers know about it. In a narrower sense it is just
setting bus-resources in the hardware devices. For the case of Linux,
it is often just a driver giving a command to set the bus-resources in
it's device or determining how the BIOS has set them. "PnP" often
means just PnP on the ISA bus so the message from isapnp: "No Plug and
Play device found" just means that no ISA PnP devices were found. The
standard PCI specifications (which are not called "PnP") provide the
equivalent of PnP for the PCI bus.
PnP matches up devices with their device drivers and specifies their
communication channels. On the ISA bus before Plug-and-Play, the
bus-resources were formerly set in hardware devices by jumpers or
switches. Software drivers were assigned bus-resources by
configuration files (or the like) or by probing the for the device at
addresses where it's expected to reside. The PCI bus was PnP-like
from the beginning but at first it wasn't called PnP (and often still
isn't called PnP). While the PCI bus specifications don't use the
term PnP, it supports in hardware what today is called PnP.
<sect1> How It Works (simplified)
<p> Here's how PnP should work in theory. The PnP
configuration program finds all PnP devices and asks each what
bus-resources it needs. Then it checks what bus-resources (IRQs,
etc.) it has to give away. Of course, if it has reserved
bus-resources used by non-PnP (legacy) devices (if it knows about
them) it doesn't give these away. Then it uses some criteria (not
specified by PnP specifications) to give out the bus-resources so that
there are no conflicts and so that all devices get what they need (if
possible). It then tells each physical device what bus-resources are
assigned to it and the devices set themselves up to use only the
assigned bus-resources. Then the device drivers somehow find out what
bus-resources their devices use and are thus able to communicate
effectively with the devices they control.
For example, suppose a card needs one interrupt (IRQ number) and 1 MB
of shared memory. The PnP program reads this request from the card.
It then assigns the card IRQ5 and 1 MB of memory addresses space,
starting at address 0xe9000000. It then informs the device driver of
what it's done (except the BIOS can't do this). It's not always this
simple as the card (or routing table for PCI) may specify that it can
only use certain IRQ numbers or that the 1 MB of memory must lie
within a certain range of addresses. The details are different for
the PCI and ISA buses with more complexity on the ISA bus.
One way commonly used to allocate resources is to start with one
device and allocate it bus-resources. Then do the same for the next
device, etc. Then if finally all devices get allocated resources
without conflicts, then all is OK. But if allocating a needed
resource would create a conflict, then it's necessary to go back and
try to make some changes in previous allocations so as to obtain the
needed bus-resource. This is called rebalancing. Linux doesn't do
rebalancing but MS Windows does in some cases. For Linux, all this is
done by the BIOS and/or kernel and/or device drivers. In Linux the
device driver doesn't allocate any resources until the driver starts
up, so one way to avoid conflicts is just not to start any device that
might cause a conflict.
There are some shortcuts that PnP software may use. One is to keep
track of how it assigned bus-resources at the last configuration (when the
computer was last used) and reuse this. Windows9x (and later) and
PnP BIOSs do this but standard Linux doesn't. Windows9x (and later)
stores this info in its "Registry" on the hard disk and a PnP BIOS
stores it in non-volatile memory in your PC (known as ESCD; see <ref
id="escd_" name="The BIOS's ESCD Database">).
While MS Windows (starting with Windows 95) is a PnP OS, Linux was not
originally a PnP OS but has been gradually becoming a PnP OS. PnP
originally worked in Linux because a PnP BIOS would configure the
bus-resources and the device drivers would find out (using programs
supplied by the Linux kernel) what the BIOS has done. Today, most
drivers can issue commands to do their own bus-resource configuring
and don't need to rely on the BIOS. Unfortunately a driver might take
a bus-resource which another device will need later on. Some device
drivers may store the last configuration they used in a configuration
file and use it the next time the computer is powered on.
If the device hardware remembered their previous configuration, then
there wouldn't be any hardware to configure at the next boot-time, but
they seem to forget their configuration when the power is turned off.
Some devices contain a default configuration (but not necessarily the
last one used). Thus a PnP device needs to be re-configured each time
the PC is powered on. Also, if a new device has been added, then it
too needs to be configured. Allocating bus-resources to this new
device might involve taking some bus-resources away from an existing
device and assigning the existing device alternative bus-resources
that it can use instead. At present, Linux can't allocate with this
sophistication (and MS Windows XP may not be able to do it either).
<sect1> Starting Up the PC
<p> When the PC is first turned on the BIOS chip runs its program to
get the computer started (the first step is to check out the
hardware). If the operating system is stored on the hard-drive (as it
normally is) then the BIOS must know about the hard-drive. If the
hard-drive is PnP then the BIOS may use PnP methods to find it. Also,
in order to permit the user to manually configure the BIOS's CMOS and
respond to error messages when the computer starts up, a screen (video
card) and keyboard are also required. Thus the BIOS must always
PnP-configure devices needed to load the operating system from the
hard-drive.
Once the BIOS has identified the hard-drive, the video card, and the
keyboard it is ready to start booting (loading the operating system
into memory from the hard-disk). If you've told the BIOS that you
have a PnP operating system (PnP OS), it should start booting the PC
as above and let the operating system finish the PnP configuring.
Otherwise, a PnP-BIOS will (prior to booting) likely try to do the
rest of the PnP configuring of devices (but not inform their
drivers of what it did).
<sect1> Buses
<p> ISA is the old bus of the old IBM PCs while PCI is a newer and
faster bus from Intel. The PCI bus was designed for what is today
called PnP. This makes it easy (as compared to the ISA bus) to find out
how PnP bus-resources have been assigned to hardware devices. To see
what's on the PCI bus type <tt/lspci/. Or type <tt/scanpci/ but it's
not as easy to read. The -v option will show more detail. And/or
look at the "file" <tt>/proc/pci</tt>. The boot-up messages on your
display show devices which have been found on various buses (use
shift-PageUp to back up thru them). See <ref id="boot_time_msgs"
name="Boot-time Messages">
For the ISA bus there was a real problem with implementing PnP since no
one had PnP in mind when the ISA bus was designed and there are almost
no I/O addresses available for PnP to use for sending configuration info
to a physical device. As a result, the way PnP was shoehorned onto the
ISA bus is very complicated. Whole books have been written about it.
See <ref id="pnp_book" name="PnP Book">. Among other things, it
requires that each PnP device be assigned a temporary "handle" by the
PnP program so that one may address it for PnP configuring. Assigning
these "handles" is call "isolation". See <ref id="isolation_"
name="ISA Isolation"> for the complex details.
Eventually, the ISA bus should become extinct. When this happens, PnP
will be a little easier since it will be easier to find out how the
BIOS has configured the hardware. There will still be the need to
match up device drivers with devices and also a need to configure
devices that are added when the PC is up and running.
<sect1> How Linux Does PnP <label id="how_linux_pnps">
<p> Linux has had serious problems dealing with PnP and still has a
problem but it's not as severe as it once was. It's debatable
whether or not Linux is really a PnP operating system. It seems to
mainly rely on and device drivers and the PnP BIOS to configure
bus-resources for devices.
But the kernel provides help for the drivers in the form of programs
they may call on that do PnP. In many cases, the device driver, with
the help of such programs, does all the needed configuring. In some
cases the BIOS may configure and then the device driver may find out
how the BIOS has configured it. The kernel provides the drivers with
some functions (program code) that the drivers may use to find out if
their device exists, how it's been configured, and functions to modify
the configuration. Kernel 2.2 could do this only for the PCI bus but
Kernel 2.4 has this feature for both the ISA and PCI buses (provided
that the PNP options have been selected when compiling the kernel).
This by no means guarantees that all drivers will fully and correctly
use these features.
In addition, the kernel helps avoid resource conflicts by not allowing
two devices to use the same bus-resources at the same time.
Originally this was only for IRQs, and DMAs but now it's for address
resources as well. For PCI, it allocates address resources while
booting.
Prior to Kernel 2.4, the standalone program: isapnp was often run to
configure and/or get info from PnP devices on the ISA bus. isapnp is
still needed for cases where the device driver is not fully PnP for
the ISA bus.. There was at least one attempt to make Linux a true PnP
operating system. See <url
url="http://www.astarte.free-online.co.uk">. But it never was put
into the kernel.
To see what help the kernel may provide to device drivers see the
directory /usr/.../.../Documentation where one of the ... contains the
word "kernel-doc" or the like. Use the "locate" command to find it.
In this documentation directory see pci.txt ("How to Write Linux PCI
Drivers") and the file: /usr/include/linux/pci.h. Unless you are a
driver guru and know C Programming, these files are written so tersely
that they will not actually teach you how to write a driver. But it
will give you some idea of what PnP type functions are available for
drivers to use. For the ISA bus see isapnp.txt and possibly (for
kernel 2.4) /usr/include/linux/isapnp.h.
When the PC starts up you may note from the messages on the screen
that some Linux device drivers often find their hardware devices (and
the bus-resources the BIOS has assigned them). But there are a number
of things that a real PnP operating system could handle better:
<itemize>
<item>Allocate bus-resources when they are in short supply
<item>Deal with more than one driver for a physical device
<item>Find a driver for a detected device (instead of making
drivers do the searching)
<item>Central allocation of bus-resources would ease the job of
programmers of device drivers
</itemize>
The "shortage of bus-resources" problem is becoming less of a problem
for two reasons: One reason is that the PCI bus is replacing the ISA
bus. Under PCI there is no shortage of IRQs since IRQs may be shared
(even though sharing is less efficient). Also, PCI doesn't use DMA
resources (although it does the equivalent of DMA without needing such
resources).
The second reason is that more and more physical devices
are using main memory addresses instead of IO address space. On
32-bit PCs there is 4GB of main memory address space and much of this
bus-resource is available for device IO (unless you have 4GB of main
memory installed). Compare this to the IO address space which is
limited to 64KB. So the memory space for device IO is not (yet ?) in
short supply.
<sect> Setting up a PnP BIOS <label id="conf_pnp_bios">
<p> When the computer is first turned on, the BIOS runs before the
operating system is loaded. Modern BIOSs are PnP and can configure
some or all of the PnP devices. Old PCI BIOS will only configure for
the PCI bus. Here are some of the choices which may exist in your
BIOS's CMOS menu:
<itemize>
<item> <ref id="bios_pnp_os" name="Do you have a PnP operating
system?">
<item> <ref id="bios_resources" name="How are bus-resources to be controlled?">
<item> <ref id="bios_reset" name="Reset the configuration?">
</itemize>
<sect1> Do you have a PnP operating system? <label id="bios_pnp_os">
<p> In any case the PnP BIOS will PnP-configure the hard-drive, video
card, and keyboard to make the system bootable. If you said you had a
PnP OS it will leave it up to the operating system (or device drivers)
to finish the configuration job. If you said no PnP OS then the BIOS
should configure everything. If you only run Linux on your PC, you
should probably tell it that you don't have a PnP operating system.
If you also run MS Windows on your PC and said it was a PnP OS when
you installed Windows, then you might try saying that you have a PnP
OS to keep Windows 95/98 happy (but it might cause problems for Linux.
For Windows 2000 it's claimed that Windows worked OK even if you say
you don't have a PnP OS. In this case Windows 2000 will report
finding new hardware (even though it already knew about the hardware
but didn't know how the BIOS Pnp-configured it).
If you say you have a PnP OS then you rely on the Linux device drivers
and possibly the program isapnp to take care of the bus-resource
configuring. This often works OK but sometimes doesn't. Doing it
this way has sometimes actually fixed problems. This could be because
the BIOS didn't do it's job right but Linux did.
If you tell the BIOS you don't have a PnP OS, then the BIOS will do
the configuring itself. Unless you have added new PnP devices, it
should use the configuration which it has stored in its non-volatile
memory (ESCD). See <ref id="escd_" name="The BIOS's ESCD Database">.
If the last session on your computer was with Linux, then there should
be no change in configuration. See <ref id="bios_conf" name= "BIOS
Configures PnP">. But if the last session was with Windows9x (which
is PnP) then Windows could have modified the ESCD. It supposedly does
this only if you "force" a configuration or install a legacy device.
See <ref id="W9x_ESCD" name="Using Windows to set ESCD">. Device
drivers that do configuring may modify what the BIOS has done. So
will the isapnp or PCI Utilities programs.
<sect2> Interoperability with Windows
<p> If you are running both Linux and Windows on the same PC, how do
you answer the BIOS's question: Do you have a PnP OS? In the 1990's
Windows suggested a yes answer and since Linux wasn't much of a PnP OS
your could say no for Linux. Having different answers for Windows and
Linux means that you would have to set up the BIOS's CMOS menu
manually each time you want to switch OSs. This is a lot of bother,
so it's best to have the same answer to the question for both Linux
and Windows.
In the 21st century, Windows 2000 and XP both suggest that you say no,
it's not a PnP OS. But Linux has become more PnP-like so you may want
to say yes. The situation is now sort of reversed from what it was.
If you have no idea what to say, you might as well just say no (it's
not a PnP OS). Then if you have problems you might change the no to a
yes. Both Windows 2000/XP and Linux have become more tolerant about
this and in many cases everything will work fine regardless of how you
answer. But if you want the BIOS to configure for Linux (and
Windows), you would say no.
<sect2> I have a PnP OS
<p>If you say that you have a PnP OS, then Linux may work OK if all
the drivers and isapnp (if you use it) are able to configure OK.
Perhaps updating of the Linux OS and/or drivers will help. Windows
95 and 98 should work OK too. Windows 2000 and XP will probably work
OK too, but they might not.
<sect2> I don't have a PnP OS: Windows 2000 and XP
<p>See the next section for Window 9x. If you have Windows 2000 or XP
it should work out OK (even if you said it was a
PnP-OS when you first installed Windows 2000). When you change to
"not a PnP-OS", Windows 2000 (and XP ??) will automatically
PnP-reconfigure it's devices and tell you that it's finding new
hardware and installing new devices. What it really means is that
it's finding hardware which is already configured by the BIOS whereas
before it found hardware that wasn't configured by the BIOS. Perhaps
it considers the hardware to be "new" since Windows 2000 may be
finding it at a different address/irq than it has recorded in its
registry.
<sect2> I don't have a PnP OS: Windows 95/98:
<p> Now you are fibbing to Windows9x. Since one might expect Windows
be more sophisticated at handling PnP than Linux, one would expect
Windows9x to be able to cope with with hardware that has been fully
configured by the BIOS. But it can't (although Windows 2000/XP can).
What Windows9x seems to do when it finds hardware that is already
configured by the BIOS is to just leave it alone and not reconfigure
it. Now Windows9x keeps a record of the bus-resource configuration in
its registry. If the BIOS configuration is different, it should
either correct what's in its registry to conform to what the BIOS has
set or reconfigure everything per what's in the registry. Bad news.
It seems to do neither.
So it seems that Windows9x may just tell its device drivers what has
been stored in the Windows Registry but this info may be wrong. The
actual hardware configuration (done by the BIOS) is what was stored in
the ESCD and may not be the same as the Registry. This means trouble.
So for Windows to work OK you need to get the Registry to contain the
bus-resource configuration which the BIOS creates from the ESCD.
One way to try to get the Registry and the ESCD the same is to install
(or reinstall) Windows when the BIOS is set for "not a PnP OS". This
should present Windows with hardware configured by the BIOS. If this
configuration is without conflicts, Windows will hopefully leave it
alone and save it in it's Registry. Then the ESCD and the registry
are in sync.
Another method is to remove devices that are causing problems in
Windows by clicking on "remove" in the Device Manager. Then reboot with
"Not a PnP OS" (set it in the CMOS as you start to boot). Windows
will then reinstall the devices, hopefully using the bus-resource
settings configured by the BIOS. Be warned that Windows will likely
ask you to insert the Window installation CD since it sometimes can't
find the driver files (and the like) even though they are still
there. A workaround for this is to select "skip file" and continue.
As a test I "removed" a NIC card which used a Novell compatible
driver. Upon rebooting, Windows reinstalled it with Microsoft
Networking instead of Novell. This meant that the Novell Client
needed to be reinstalled --a lot of unnecessary work. So it may be
better to not fib to Windows95/98 but instead to get Linux to
configure bus-resources.
<sect1> How are bus-resources to be controlled? <label
id="bios_resources"> <p> Unless you have old non-pnp ISA cards, just
set this to "auto". If set to manual, you manually reserve some
IRQ's, etc. for use on "legacy" (non-pnp) ISA cards. The BIOS may or
may not otherwise know about such legacy cards. The BIOS will only
know about these legacy cards if you ran ICU (or the like) under
Windows to tell the BIOS about them. If the BIOS knows about them,
then try using "auto". If it doesn't know about them, then manually
reserve the IRQ's needed for the legacy ISA cards and let the rest be
for the BIOS PnP to allocate.
<sect1> Reset the configuration? <label id="bios_reset">
<p> Don't try this unless... This will erase the BIOSs ESCD data-base
of how your PnP devices should be configured as well as the list of
how legacy (non-PnP) devices are configured. Never do this unless you
are convinced that this data-base is wrong and needs to be remade. It
was stated somewhere that you should do this only if you can't get
your computer to boot. If the BIOS loses the data on legacy ISA
devices, then you'll need to run ICA again under DOS/Windows to
reestablish this data.
<sect> How to Deal with PnP Cards
<sect1> Introduction to Dealing with PnP Cards
<p> Today most all new internal boards (cards) are Plug-and-Play
(PnP). The configuring of bus-resources is normally done by the
various device drivers using pnp support provided by modules or built
into the kernel. If this doesn't work, there are 4 other methods
listed below to cope with PnP (but some may not be feasible in your
situation). If the BIOS configures it, you hope that the driver can
find out what the BIOS did, otherwise you may need to tell the driver
this in a configuration file or the like.
<itemize>
<item> <ref id="dev_d_conf" name="Device Driver Configures">
<item> <ref id="bios_conf" name= "BIOS Configures"> (For the PCI bus
you only need a PCI BIOS, otherwise you need a PnP BIOS)
<item> <ref id="disable_pnp" name="ISA cards only: Disable PnP"> by jumpers or
DOS/Windows software (but many cards can't do this)
<item> <ref id="isapnp_" name="Isapnp"> is a program you can always
use to configure PnP devices on the ISA bus only
<item> <ref id="pciutils_" name="PCI Utilities"> is for configuring the PCI
bus but the device driver should handle it
<item> <ref id="windows_conf" name="Windows Configures"> and then you
boot Linux from within Windows/DOS. Use as a last resort
</itemize>
Any of the above will set the bus-resources in the hardware but only
the first one tells the driver what has been done. How the driver gets
informed depends on the driver. You may need to do something to
inform it. See <ref id="tell_driver_config" name="Tell the Driver the
Configuration">
<sect1> Device Driver Configures, Reserving Resources <label id="dev_d_conf">
<p> Many device drivers (with the help of code provided by the kernel)
will use PnP methods to set the bus-resources in the hardware but only
for the device that they control. Since the driver has done the
configuring, it obviously knows the configuration and there is no need
for you to tell it this info. This is obviously the easiest way to do
it since you don't have to do anything if the driver does it all.
If you have old pre-pnp ISA hardware, the Linux Pnp software may not
know about it and the bus-resources it requires. So it might
erroneously allocate the resources that this old hardware needs to
some other device. The result is a resource conflict but there's a way
to try to avoid it. You can reserve the resources that the old ISA
card needs by giving arguments to the isa-pnp module or to the kernel
(if the pnp is built into the kernel). For example, to reserve irq 5
give this argument to the isa-pnp module (or to the kernel):
isapnp_reserve_irq=5. See BootPrompt-HOWTO. Instead of ..._irq there
are also _io, _dma, and _mem. Is this clever enough to prevent a PCI
device from using such reserved resources ??
For PCI devices, most drivers will configure PnP but for ISA devices
it's problematical. This is because PCI has always been inherently
PnP (called "PCI Configuration"). For ISA, the kernel provided
no functions for PnP configuring until version 2.4. So if you have a
modern version of both the kernel and the driver then the driver is more
likely to configure ISA PnP (bus-resources). But if you have older
versions (or if the driver maintainer failed to add PnP support to it)
then the driver may not configure ISA PnP.
Unfortunately, a driver may grab bus-resources that are needed by other
devices (but not yet allocated to them by the kernel). Thus a true
PnP Linux kernel would be better where the kernel did the allocation
after all requests were in. See <ref id="how_linux_pnps" name="How
Linux Does PnP">.
<sect1> BIOS Configures <label id="bios_conf">
<sect2> Intro to Using the BIOS to Configure PnP
<p> If you have a PnP BIOS, it can configure the hardware. If the
driver can't do it, the BIOS probably can. This means that your BIOS
reads the resource requirements of all devices and configures them
(allocates bus-resources to them). It is a substitute for a PnP OS
except that the BIOS doesn't match up the drivers with their devices
nor tell the drivers how it has done the configuring. It should
normally use the configuration it has stored in its non-volatile
memory (ESCD). If it finds a new device or if there's a conflict, the
BIOS should make the necessary changes to the configuration and may
not use the same configuration as was in the ESCD. In this case it
should update the ESCD to reflect the new situation.
Your BIOS needs to support such configuring and there have been cases
where it doesn't do it correctly or completely. The BIOS also
needs to be told via the CMOS menu that it's not a PnP OS. While
many device drivers will be able to automatically detect what the
BIOS has done, in some cases you may need to determine it (not always
easy). See <ref id="current_config" name="What Is My Current
Configuration?"> A possible advantage to letting the BIOS do it is
that it does its work before Linux starts so it all gets done early in
the boot process.
According to MS it's only optional (not required) that a PnP BIOS be
able to PnP-configure the devices (without help from MS Windows). But
it seems that most of the ones made after 1996 ?? or so can do it. We
should send them thank-you notes if they do it right. They configure
both the PCI and ISA buses, but it has been claimed that some older
BIOSs can only do the PCI. To try to find out more about your BIOS,
look on the Web. Please don't ask me as I don't have data on this.
The details of the BIOS that you would like to know about may be hard
to find (or not available). Some BIOSs may have minimal PnP
capabilities and seemingly expect the operating system to do it
right. If this happens you'll either have to find another method or
try to set up the ESCD database if the BIOS has one. See the next
section.
<sect2> The BIOS's ESCD Database <label id="escd_">
<p> The BIOS maintains a non-volatile database containing a
PnP-configuration that it will try to use (if you claim that it's not
a PnP OS). It's called the ESCD (Extended System Configuration Data).
Again, the provision of ESCD is optional but most PnP-BIOSs have it.
The ESCD not only stores the resource-configuration of PnP devices but
also stores configuration information of non-PnP devices (and marks
them as such) so as to avoid conflicts. The ESCD data is usually
saved on a chip and remains intact when the power is off, but
sometimes it's kept on a hard-drive??
The ESCD is intended to hold the last used configuration, but if you
use a program such as Linux's isapnp or pci utilities (which doesn't
update the ESCD) then the ESCD will not know about this and will not
save this configuration in the ESCD. A good PnP OS might update the
ESCD so you can use it later on for a non-PnP OS (like standard
Linux). MS Windows9x does this only in special cases. See <ref
id="W9x_ESCD" name="Using Windows to set ESCD">.
To use what's set in ESCD be sure you've set "Not a PnP OS" or the
like in the BIOS's CMOS. Then each time the BIOS starts up (before
the Linux OS is loaded) it should configure things this way. If the
BIOS detects a new PnP card which is not in the ESCD, then it must
allocate bus-resources to the card and update the ESCD. It may even
have to change the bus-resources assigned to existing PnP cards and
modify the ESCD accordingly.
If each device saved its last configuration in its hardware, hardware
configuring wouldn't be needed each time you start your PC. But it
doesn't work this way. So all the ESCD data needs to be kept correct
if you use the BIOS for PnP. There are some BIOSs that don't have an
ESCD but do have some non-volatile memory to store info regarding
which bus-resources have been reserved for use by non-PnP cards. Many
BIOSs have both.
<sect2> Using Windows to set the ESCD <label id="W9x_ESCD">
<p> If the BIOS doesn't set up the ESCD the way you want it (or the
way it should be) then it would be nice to have a Linux utility to
set the ESCD. As of early 1999 there wasn't any and now in 2002
no one has told me about any. Thus one may resort to attempting to
use Windows (if you have it on the same PC) to do this.
There are three ways to use Windows to try to set/modify the ESCD. One
way is to use the ICU utility designed for DOS or Windows 3.x. It
should also work OK for Windows 9x/2k ?? Another way is to set up
devices manually ("forced") under Windows 9x/2k so that Windows will
put this info into the ESCD when Windows is shut down normally. The
third way is only for legacy devices that are not plug-and-play. If
Windows knows about them and what bus-resources they use, then Windows
should put this info into the ESCD.
If PnP devices are configured automatically by Windows without the
user "forcing" it to change settings, then such settings probably will
not make it into the ESCD. Of course Windows may well decide on its
own to configure the same as what is set in the ESCD so they could
wind up being the same by coincidence.
Windows 9x are PnP operating systems and automatically PnP-configure
devices. They maintain their own PnP-database deep down in the
Registry (stored in binary Windows files). There is also a lot of
other configuration stuff in the Registry besides PnP-bus-resources.
There is both a current PnP resource configuration in memory and
another (perhaps about the same) stored on the hard disk. To look at
this in Windows98 or to force changes to it you use the Device Manager.
In Windows98 there are 2 ways to get to the Device Manager: 1. My
Computer --> Control Panel --> System Properties --> Device Manager.
2. (right-click) My Computer --> Properties --> Device Manager. Then
in Device Manager you select a device (sometimes a multi-step process
if there are a few devices of the same class). Then click on
"Properties" and then on "Resources". To attempt to change the
resource configuration manually, uncheck "Use automatic settings" and
then click on "Change Settings". Now try to change the setting, but
it may not let you change it. If it does let you, you have "forced" a
change. A message should inform you that it's being forced. If you
want to keep the existing setting shown by Windows but make it
"forced" then you will have to force a change to something else and
then force it back to its original setting.
To see what has been "forced" under Windows98 look at the "forced
hardware" list: Start --> Programs --> Accessories --> System Tools
--> System Information --> Hardware Resources --> Forced Hardware.
When you "force" a change of bus-resources in Windows, it should put
your change into the ESCD (provided you exit Windows normally).
From the "System Information" window you may also inspect how IRQs and
IO ports have been allocated under Windows.
Even if Windows shows no conflict of bus-resources, there may be a
conflict under Linux. That's because Windows may assign bus-resources
differently than the ESCD does. In the the rare case where all
devices under Windows are either legacy devices or have been "forced",
then Windows and the ESCD configurations should be identical.
<sect2> Adding a New Device (under Linux or Windows)
<p> If you add a new PnP device and have the BIOS set to "not a PnP
OS", then the BIOS should automatically configure it and store the
configuration in ESCD. If it's a non-PnP legacy device (or one made
that way by jumpers, etc.) then here are a few options to handle it:
You may be able to tell the BIOS directly (via the CMOS setup menus)
that certain bus-resources it uses (such as IRQs) are reserved and are
not to be allocated by PnP. This does not put this info into the
ESCD. But there may be a BIOS menu selection as to whether or not to
have these CMOS choices override what may be in the ESCD in case of
conflict. Another method is to run ICU under DOS/Windows. Still
another is to install it manually under Windows 9x/2k and then make
sure its configuration is "forced" (see the previous section). If
it's "forced" Windows should update the ESCD when you shut down the
PC.
<sect1> ISA cards only: Disable PnP ? <label id="disable_pnp">
<p> PCI devices are inherently PnP so it can't be disabled. But a few
ISA devices had options for disabling PnP by jumpers or by running a
Windows program that comes with the device (jumperless configuration).
If the device driver can't configure it, this will avoid the possibly
complicated task of doing PnP configuring. Don't forget to tell the
BIOS that these bus-resources are reserved. There are also some
reasons why you might not want to disable PnP:
<enum>
<item> If you have MS Windows on the same machine, then you may want
to allow PnP to configure devices differently under Windows from what
it does under Linux.
<item> The range of selection for IRQ numbers (or port addresses) etc.
may be quite limited unless you use PnP.
<item> You might have a Linux device driver that uses PnP methods to
search for the device it controls.
<item> If you need to change the configuration in the future, it may
be easier to do this if it's PnP (no setting of jumpers or running a
Dos/Windows program).
</enum>
Once configured as non-PnP devices, they can't be configured by PnP
software or a PnP-BIOS (until you move jumpers and/or use the
Dos/Windows configuration software again).
<sect1> Isapnp (part of isapnptools) <label id="isapnp_">
<p> The <tt/isapnp/ standalone program is only for PnP devices on the
ISA bus (non-PCI). It was much needed prior to the 2.4 kernels.
After the 2.4 kernel, which provided functionality to allow drivers
deal with ISA PnP, the isapnp standalone program is less significant.
But the isa-pnp module (or the equivalent built into the kernel) is now
very significant. This module is called on by various device drivers
to do configure bus-resources.
In some cases Linux distributions have been set up to run isapnp
automatically at startup. If you need to set it up yourself much of
the documentation for isapnp is difficult to understand unless
you know the basics of PnP. This HOWTO should help you understand it
as well the FAQ that comes with it. Running the Linux program
"isapnp" at boot-time will configure such devices to the resource
values specified in /etc/isapnp.conf. Its possible to create this
configuration file automatically but you then should edit it manually
to choose between various options.
With isapnp there's a danger that a device driver which is built into
the kernel may run too early before isapnp has set the address, etc.
in the hardware. This results in the device driver not being able to
find the device. The driver tries the right address but the address
hasn't been set yet in the hardware.
If your Linux distribution automatically installed isapnptools, isapnp
may already be running at startup. In this case, all you need to do
is to edit /etc/isapnp.conf per "<tt/man isapnp.conf/". Note that
this is like manually configuring PnP since you make the decisions as
to how to configure as you edit the configuration file.
If the configuration file is wrong or doesn't exist, you can use
the program "pnpdump" to help create the configuration file. It
almost creates a configuration file for you but you must skillfully
edit it a little before using it. It contains some comments to help
you edit it. While the BIOS may also configure the ISA devices (if
you've told it that you don't have a PnP OS), isapnp will redo it.
The terminology used in the /etc/isapnp.conf file may seem odd at
first. For example for an I0 address of 0x3e8 you might see "(IO 0
(BASE 0x3e8))" instead. The "IO 0" means this is the first (0th) IO
address-range that this device uses. Another way to express all this
would be: "IO[0] = 0x3e8" but isapnp doesn't do it this way. "IO 1"
would mean that this is the second IO address range used by this
device, etc. "INT 0" has a similar meaning but for IRQs (interrupts).
A single card may contain several physical devices but the above
explanation was for just one of these devices.
<sect1> PCI Utilities <label id="pciutils_">
<p> The package PCI Utilities (= pciutils, sometimes called
"pcitools"), should let you manually PnP-configure the PCI bus.
"lspci" or "scanpci" (Xwindows) lists bus-resources while "setpci"
sets resource allocations in the hardware devices. It appears that
setpci is mainly intended for use in scripts and presently one needs to
know the details of the PCI configuration registers in order to use it.
That's a topic not explained here nor in the manual page for setpci.
People have used this to configure PCI devices where the driver failed
to do it. An example is found in my Modem-HOWTO and Serial-HOWTO in
the subsection "PCI: Enabling a disabled port". However, enabling a
device is of no use unless you have a working driver for the device.
<sect1> Windows Configures <label id="windows_conf">
<p> This method uses MS Windows to configure and should be used only
if all else fails. If you have Windows9x (or 2k) on the same PC, then
just start Windows and let it configure PnP. Then start Linux from
Windows (or DOS). But there may be a problem with IRQs for PCI
devices. As Windows shuts down to make way for Linux, it may erase
(zero) the IRQ which is stored in one of the PCI device's
configuration registers. Linux will complain that it has found an IRQ
of zero.
The above is reported to happen if you start Linux using a shortcut
(PIF file). But a workaround is reported where you still use the
shortcut PIF. A shortcut is something like a symbolic link in Linux
but it's more than that since it may be "configured". To start Linux
(from DOS you create a batch file (script) which starts Linux. (The
program that starts Linux is in the package called "loadlin"). Then
create a PIF shortcut to that batch file and get to the "Properties"
dialog box for the shortcut. Select "Advanced" and then check "MS-DOS
mode" to get it to start in genuine MS-DOS.
Now here's the trick to prevent zeroing the PCI IRQs. Chick "Specify
a new MS-DOS configuration". Then either accept the default
configuration presented to you or click on "Configuration" to change
it. Now when you start Linux by clicking on the shortcut, new
configuration files (Config.sys and Autoexec.bat) will be created per
your new configuration.
The old files are stored as "Config.wos and Autoexec.wos". After you
are done using Linux and shut down your PC then you'll need these
files again so that you can run DOS the next time you start your PC.
You need to ensure that the names get restored to *.sys and *.bat.
When you leave Windows/DOS to enter Linux, Windows is expecting that
when you are done using Linux you will return to Windows so that
Windows can automatically restore these files to their original names.
But this doesn't happen since when you exit Linux you shut down your
PC and don't get back to Windows. So how do you get these files
renamed? It's easy, just put commands into your "start-Linux" batch
file to rename these files to their *.bat and *.sys names. Put these
renaming commands into your batch file just before the line that loads
Linux.
Also it's reported that you should click on the "General" tab (of the
"Properties" dialog of your shortcut) and check "Read-only".
Otherwise Windows may reset the "Advanced Settings" to "Use current
MS-DOS configuration" and PCI IRQs get zeroed. Thus Windows erases
the IRQs when you use the current MS-DOS configuration but doesn't
erase when you use a new configuration (which may actually configure
things identical to the old configuration). Windows does not seem to
be very consistent.
<sect1> PnP Software/Documents <label id="sw_and_docs">
<p><itemize>
<item><url url="http://www.roestock.demon.co.uk/isapnptools/"
name="Isapnptools homepage">
<item><url url="http://www.astarte.free-online.co.uk" name="Proposal
for a Configuration Manager for Linux"> (Never got into kernel.)
<item> <url url="http://www.io.com/~cdb/mirrors/lpsg/pnp-linux.html"
name="Failed PnP driver project">
<item <url url="http://www.microsoft.com/hwdev/tech/pnp/default.asp"
name="PnP Specs. from Microsoft">
<item> Book: PCI System Architecture, 4th ed. by Tom Shanley +,
MindShare 1999. Covers PnP-like features on the PCI bus.
<item> <label id="pnp_book"> Book: Plug and Play System Architecture,
by Tom Shanley, Mind Share 1995. Details of PnP on the ISA bus. Only
a terse overview of PnP on the PCI bus.
<item> Book: Programming Plug and Play, by James Kelsey, Sams 1995.
Details of programming to communicate with a PnP BIOS. Covers ISA,
PCI, and PCMCIA buses.
</itemize>
<sect> Tell the Driver the Configuration <label id="tell_driver_config">
<sect1> Introduction
<p>A modern driver for a device will find out the bus-resource
configuration without you having to tell it anything. It may even set
the bus-resources in the hardware using PnP methods. Some drivers
have more than one way to find out how their physical device is
configured. In the worst case you must hard-code the bus-resources
into the kernel (or a module) and recompile.
In the middle are cases such as where you run a program to give the
bus-resource info to the driver or put the info in a configuration
file. In some cases the driver may probe for the device at addresses
where it suspects the device resides (but it will never find a PnP
device if it hasn't been enabled by PnP methods). It may then try to
test various IRQs to see which one works. It may or may not
automatically do this. In other cases the driver may use PnP methods
to find the device and how the bus-resources have been set by the
BIOS, etc. but will not actually set them. It may also look at some
of the "files" in the /proc directory.
One may need to "manually" tell a driver what bus-resources it should
use. You give such bus-resources as a parameter to the kernel or to a
loadable module. If the driver is built into the kernel, you pass the
parameters to the kernel via the "boot-prompt". See The
Boot-Prompt-HOWTO which describes some of the bus-resource and other
parameters. Once you know what parameters to give to the kernel, one
may put them into a boot loader configuration file. For example, put
append="...". into the lilo.conf file and then use the lilo command to
get this info into the lilo kernel loader.
If the driver is loaded as a module, in many cases the module will
find the bus-resources needed and then set them in the device. In other
cases (mostly for older PCs) you may need to give bus-resources as
parameters to the module. Parameters to a module (including ones that
automatically load) may be specified in /etc/modules.conf. There are
usually tools used to modify this file which are
distribution-dependent. Comments in this file should help regarding
how to modify it. Also, any module your put in /etc/modules will get
loaded along with its parameters.
While there is great non-uniformity about how drivers find out about
bus-resources, the end goal is the same. If you're having problems
with a driver you may need to look at the driver documentation (check
the kernel documentation tree). Some brief examples of a few drivers
is presented in the following sections:
<sect1> Serial Port Driver Example
<p> For PCI serial ports (and for newer 2.4 kernels for ISA), the
serial driver detects the type of serial port and PnP configures it.
Unfortunately, there may be some PCI serial ports that are not
supported yet.
For the standard ISA serial port with older versions of the kernel and
serial driver (not for multiport cards) you use setserial to inform
the driver. Using setserial is also a must for non-pnp serial ports.
Setserial is often run from a start-up file. In newer versions there
is a /etc/serial.conf file that you "edit" by simply using the
setserial command in the normal way and what you set using
<tt/setserial/ is saved in the <tt>serial.conf</tt> configuration
file. The <tt>serial.conf</tt> file should be consulted when the
<tt/setserial/ command runs from a start-up file. Your distribution
may or may not set this up for you.
There are two different ways to use <tt/setserial/ depending on the
options you give it. One way is used to manually tell the driver the
configuration. The other way is to probe at a given address and
report if a serial port exists there. It can also probe this address
and try to detect what IRQ is used for this port. The driver runs
something like <tt/setserial/ at start-up but it doesn't probe for
IRQs, it just assigns the "standard" IRQ which may be wrong. It does
probe for the existence of a port. See Serial-HOWTO for more details.
<sect1> Some Sound Card Driver Examples
<sect2> OSS-Lite
<p> You must give the IO, IRQ, and DMA as parameters to a module
or compile them into the kernel. But some PCI cards will get
automatically detected. RedHat supplies a program "sndconfig" which
detects ISA PnP cards and automatically sets up the modules for
loading with the detected bus-resources.
<sect2> OSS (Open Sound System) and ALSA
<p> These will detect the card by PnP methods and then select the
appropriate driver and load it. It will also set the bus-resources on an
ISA-PnP card. You may need to manually intervene to avoid conflicts.
For the ALSA driver, support for ISA-PnP is optional and you may use
isapnp tools if you want to.
<sect>How Do I Find Devices and How Are They Configured? <label id="current_config">
<sect1>Finding and How-Configured Are Related
<p>Once you find your hardware, the same program that found it usually
tells you how it's configured. So finding out how it's configured is
usually the same procedure as finding the hardware.
<sect1>Devices Have Two "Configurations"
<p> Here "configuration" means the assignment of PnP bus-resources
(addresses, IRQs, and DMAs). For each device, there are two parts to
the configuration question:
<enum>
<item> What does the driver think the hardware configuration is?
<item> What configuration (if any) is actually set in the device hardware?
</enum>
Each part should have the same answer (the same configuration).
The configuration of the device hardware and its driver should be the
same (and usually is). But if things are not working right, it could
be because there's a difference. This means the the driver has
incorrect information about the actual configuration of the hardware.
This spells trouble. If the software you use doesn't adequately tell
you what's wrong (or automatically configure it correctly) then you
need to investigate how your hardware devices and their drivers are
configured. While Linux device drivers should "tell all" in some
cases it may not be easy to determine what has been set in the
hardware.
Another problem is that when you view configuration messages on the
screen, it's sometimes not clear whether the reported configuration is
that of the device driver, the device hardware, or both. If the
device driver has either set the configuration in the hardware or has
otherwise checked the hardware then the driver should have the correct
information.
But sometimes the driver has been provided incorrect resources by a
script, by incorrect resource parameters given to a module, or perhaps
just hasn't been told what the resources are and tries to use
incorrect default resources. For example, one can uses "setserial" to
tell the serial port driver an incorrect resource configuration and the
driver accepts it without question. But the serial port doesn't work
right (if at all).
<sect1>Finding Hardware
<p>A common problem is that the software doesn't detect your device
and/or determine the right driver for it. For PnP devices, detecting
them is easy via PnP software. This means that since the PCI bus is
inherently PnP, there are no hidden devices. Even though PnP devices
are easy to find by PnP methods, if the driver doesn't use PnP methods
but uses the old method of probing for them at likely address, they
may not be found. This is because that until the resources are set in
a PnP device (by the BIOS or Linux), the device may have no address at
all so probing at likely address yields nothing. For the old ISA
bus, some of the devices may be non-PnP and thus the old probing
methods may find them. So many drivers still probe, in addition to
using PnP methods.
Ways to Find Hardware Devices (and their configurations): (follow link
to more details)
<itemize>
<item>Watch the <ref id="boot_time_msgs" name="Boot-time Messages">
on the screen
<item>Look in <ref id="proc_dir" name="The /proc Directory Tree">
<item> PCI: <ref id="pci_" name="PCI Bus Inspection">
<item> ISA Bus: <ref id="isa_bus" name="ISA Bus Introduction">
<item> ISA Bus: <ref id="isa_pnp" name="PnP cards">
<item> ISA Bus: For <ref id="non_pnp" name="Non-PnP Cards">
<item> ISA Bus: For <ref id="jumpers_" name="Cards with jumpers">,
<item> ISA Bus: If <ref id="neither_" name="Neither PnP nor jumpers">,
<item> <ref id="check_ms" name="Use MS Windows">
</itemize>
<sect1> Boot-time Messages <label id="boot_time_msgs">
<p> Some info on configuration may be obtained by reading the messages
from the BIOS and from Linux that appear on the screen when you first
start the computer. These messages often flash by too fast to read
but once they stop type Shift-PageUp a few times to scroll back to
them. To scroll forward thru them type Shift-PageDown. Typing
"dmesg" at any time to the shell prompt will show only the Linux
kernel messages and may miss some of the most important ones (including
ones from the BIOS). The messages from Linux may sometimes only show
what the device driver thinks the configuration is, perhaps as told it
via an incorrect configuration file. Checking log files in /var/log
may also be useful.
For the PCI bus, the notation: 00:1a:0 means the PCI bus 00 (the main
PCI bus), PCI card (or chip) 1a, and function 0 (the first device) on
the card or chip. The 2nd device on card (or chip) 08 would be:
00:08:1.
The BIOS messages display first and will show the actual hardware
configuration at that time, but isapnp, or pci utilities, or device
drivers may change it later. As an alternative to eventually using
Shift-PageUp to read them, try freezing them by hitting the "Pause"
key. Press any key to resume. But once the messages from Linux start
to appear, it's too late to use "Pause" since it will not freeze the
messages from Linux.
Messages from the BIOS at boot-time tell you how the hardware
configuration was then. For the case where only the BIOS does the
configuring, then it should still be the same. Messages from Linux
may be from drivers that used kernel PnP functions to inspect and/or
set bus-resources. These should be correct, but beware of messages
that only show what the driver was told from a configuration file.
It could be wrong. Of course, if the device works fine, then it's
likely configured the same as the driver.
<sect1> The /proc Directory Tree <label id="proc_dir">
<p> The /proc directory tree is useful for finding configuration and
devices. It seems that there are many files buried deep in this tree
that contain bus-resource info. Only a couple of them will be
mentioned here. /proc/ioports shows the I/O addresses that the active
drivers use (or try if it's wrong). They might not be set this way in
hardware.
/proc/interrupts shows only interrupts currently in use. Many
interrupts that have been allocated to drivers don't show here at all
since they're not currently being used. For example, even though your
floppy drive has a floppy disk in it and is ready to use, the
interrupt for it will not show unless its in use. Again, just because
an interrupt shows up here doesn't mean that it exists in the
hardware. A clue that it doesn't exist in hardware will be if it
shows that 0 interrupts have been issued by this interrupt. Even if
it shows a few interrupts have been issued there is no guarantee that
they came from the device shown. It could be that some other device
which is not currently in use has issued them. A device not in use
(per the kernel) may still issue some interrupts for various reasons.
<sect1>PCI Bus Inspection <label id="pci_">
<p> It's easy to find out what bus-resources have been assigned to
devices on the PCI bus with the "lspci" and/or "scanpci" commands or
look at <tt>/proc/pci</tt>. The option -v will show more detail.
<tt>/proc/buspci/devices</tt> shows a cryptic display so you probably
want to avoid it. Note that IRQs for <tt>/proc/pci</tt> are in
hexadecimal.
In most cases, for PCI you will only see how the hardware is now
configured and not what resources are required. In some cases you
only see the base addresses (the starting addresses of the range) but
not the ending addresses. If you see the entire range then you can
determine how many bytes of address resources are needed.
<sect1>ISA Bus Introduction <label id="isa_bus">
<p>For cards on the ISA bus, it's not as simple as for the PCI bus
which is inherently PnP. Newer ISA cards are PnP but older ones are
not. Also, some cards that are PnP have had their PnP disabled by
special software which runs only on MS. The non PnP cards are
configured by jumpers on the card or by MS software.
<sect1>ISA PnP cards <label id="isa_pnp">
<p>If it's a PnP card you may try running <tt>pnpdump --dumpregs</tt>
but it's not a sure thing. The results may be seem cryptic but they
can be deciphered. Don't confuse the read-port address which
<tt/pnpdump/ uses for communication with PnP cards with the I/O
address of the found device. They are not the same.
<sect1>Non-PnP Cards <label id="non_pnp">
<p>In contrast to PnP cards, non-PnP cards always have their resources
set in the hardware. That is they always have an address and IRQ.
Sometimes this can be found by probing done by the device driver or by
other software that does probing. For example "scanport" (Debian only
??) probes most IO port address and may find ISA devices. But be
warned that it might hang your PC. Sometimes it will fail to find
hardware that's actually there (since the hardware has the default
0xff in it's registers). Even if It finds the hardware it will not
show the IRQ nor will it positively identify the hardware.
So one way to try to find such hardware is to start a driver, which
may probe for such hardware. By looking at the boot-time messages, you
might see a driver start and find the hardware. Otherwise, you may
need to find a driver and start it (for example, by having it load as
a module).
Finding the right driver may be difficult. Sometimes there just isn't
any driver since some devices aren't supported by Linux (yet ?). To
determine which driver you need, look at any documentation which might
identify the card. If this fails, look on the card itself, including
important names/numbers on the chips. But the identification of the
driver module you need may not be anywhere on the card. You could
find the FCC id on the card and then search the Internet with the FCC
id number to try to find more information about the card (or the chips
on it).
<sect1>Non-PnP Cards with jumpers <label id="jumpers_">
<p>If the card has jumpers to set the resources (configuration) then
one may look at how the jumpers are set. There are some cards that had
both PnP and jumpers. They worked like jumper cards if PnP was
somehow disabled. Sometimes a card has labels on it showing how the
jumpers are set (or at least giving some clue). You may need the
documentation that came with the card (either printed or on a floppy
disk). Perhaps you can find it on the Internet.
<sect1>Neither PnP nor jumpers <label id="neither_">
<p>One the most difficult cases is where software running under MS has
been used to configure either a non-PnP card or a PnP card where PnP
has been disabled by the same MS software. So you can't configure it
by PnP nor by jumpers. In this case your only hope is to probe for
addresses as described in <ref id="non_pnp" name="Non-PnP Cards">.
<sect1>Use MS Windows <label id="check_ms">
<p>Some people have attempted to use Windows to see how bus-resources
have been set up. Unfortunately, since PnP hardware forgets its
bus-resource configuration when powered down, the configuration may
not be the same under Linux. For non PnP hardware (or where someone
has disabled PnP inside the device by jumpers or Windows software),
then using Windows should work OK. Even for PnP, it often turns
out to be the same because in many cases both Windows and Linux simply
accept what the BIOS has set. But where Windows and/or Linux do the
configuring, they may do it differently. So don't count on PnP
devices being configured the same.
<sect>Error Messages
<sect1> Unexpected Interrupt
<p> This means that an interrupt happened that no driver expected.
It's unlikely that the hardware issued an interrupt by mistake. It's
more likely that the software has a minor bug and doesn't realize that
some software did something to cause the interrupt. In many cases you
can safely ignore this error message, especially if it only happens
once or twice at boot-time. For boot-time messages, look at the
messages which are nearby for a clue as to what is going on. For
example, if probing is going on, perhaps a probe for a physical device
caused that device to issue an interrupt that the driver didn't
expect. Perhaps the driver wasn't listening for the correct IRQ
number.
<sect1> Plug and Play Configuration Error (Dell BIOS)
<p>The BIOS was unable to configure bus-resource. There may be an
interrupt conflict which can't be avoided. Dell suggests that you
remove some of your non-essential cards and see if it goes away. In
one case this problem was due to a defective motherboard.
<sect>Appendix
<sect1> Universal Plug and Play (UPnP) <label id="UPnP_">
<p> This is actually a sort of network plug-and-play developed by
Microsoft but usable by Linux. You plug something into a network and
that something doesn't need to be configured provided it will only
communicate with other UPnP enabled devices on the network. Here
"configure" is used in the broad sense and doesn't mean just
configuring bus-resources. One objective is to allow people who know
little about networks or configuring to install routers, gateways,
network printers, etc. A major use for UPnP would be in wireless
networking.
UPnP uses:
<itemize>
<item> Simple Service Discovery Protocol to find devices
<item> General Event Notification Architecture
<item> Simple Object Access Protocol for controlling devices
</itemize>
This HOWTO doesn't cover UPnP. UPnP for Linux is supported by Intel
which has developed software for it. There are other programs which
do about the same thing as UPnP. A comparison of some of them is at
<url url="http://www.cs.umbc.edu/~dchakr1/papers/mcommerce.html">
<sect1> Address Details <label id="address_details">
<p> There are three types of addresses: main memory addresses, I/O
addresses (ports) and configuration addresses. On the PCI bus,
configuration addresses constitute a separate address space just like
I/O addresses do. Except for the complicated case of ISA
configuration addresses, whether or not an address on the bus is a
memory address, I/O address, or configuration address depends only on
the voltage on other wires (traces) of the bus. For the ISA
configuration addresses see <ref id="isa_conf_addresses" name="ISA Bus
Configuration Addresses (Read-Port etc.)"> for details
<sect2> Address ranges
<p> The term "address" is sometimes used in this document to mean a
contiguous range of addresses. Since addresses are in units of bytes,
a single address is only the location of a single byte but I/O (and
main memory) addresses need more than this. So a range of say 8 bytes
is often used for I/O address while the range for main memory
addresses allocated to a device is much larger. For a serial port (an
I/O device) it's sufficient to give the starting I/O address of the
device (such as 3F8) since it's well known that the range of addresses
for serial port is only 8 bytes. The starting address is known as the
"base address". Sometimes just the word "range" is used to mean
"address range".
<sect2> Address space
<p> For ISA, to access both I/O and (main) memory address "spaces"
the same address bus is used (the wires used for the address are
shared). How does the device know whether or not an address which
appears on the address bus is a memory address or I/O address? Well,
there are 4 dedicated wires on the bus that convey this information
and more. If a certain one of these 4 wires is asserted, it says that
the CPU wants to read from an I/O address, and the main memory ignores
the address on the bus. The other 3 wires serve similar purposes.
Thus read and write wires exist for both main memory and I/O addresses
(4 wires in all).
For the PCI bus it's the same basic idea (also using 4 wires) but it's
done a little differently. Instead of only one of the four wires
being asserted, a binary number is put on the wires (16 different
possibilities). Thus more info may be conveyed. Four of these 16
numbers serve the I/O and memory spaces as in the above paragraph. In
addition there is also configuration address space which uses up two
more numbers. Ten extra numbers are left over for other purposes.
<sect2> Range Check (ISA Testing for IO Address Conflicts)
<p> On the ISA bus, there's a method built into each PnP card for
checking that there are no other cards that use the same I/O address.
If two or more cards use the same IO address, neither card is likely
to work right (if at all). Good PnP software should assign
bus-resources so as to avoid this conflict, but even in this case a
legacy card might be lurking somewhere with the same address.
The test works by a card putting a known test number in its own IO
registers. Then the PnP software reads it and verifies that it reads
the same test number. If not, something is wrong (such as another
card with the same address. It repeats the same test with another
test number. Since it actually checks the range of IO addresses
assigned to the card, it's called a "range check". It could be better
called an address-conflict test. If there is an address conflict you
get an error message and need to resolve it yourself.
<sect2> Communicating Directly via Memory
<p> Traditionally, most I/O devices used only I/O memory to
communicate with the CPU. For example, the serial port does this.
The device driver, running on the CPU would read and write data
to/from the I/O address space and main memory. A faster way would be
for the device itself to put the data directly into main memory. One
way to do this is by using <ref id="dma_" name="DMA Channels"> or bus
mastering. Another way is to allocate some space in main memory to
the device. This way the device reads and writes directly to main
memory without having to bother with DMA or bus mastering. Such
a device may also use IO addresses.
<sect1> ISA Bus Configuration Addresses (Read-Port etc.)
<label id="isa_conf_addresses">
<p> These addresses are also known as the "Auto-configuration Ports".
For the ISA bus, there is technically no configuration address space,
but there is a special way for the CPU to access PnP configuration
registers on the PnP cards. For this purpose 3 @ I/O addresses are
allocated and each addresses only a single byte (there is no "range").
This is not 3 addresses for each card but 3 addresses shared by all
ISA-PnP cards.
These 3 addresses are named read-port, write-port, and address-port.
Each port is just one byte in size. Each PnP card has many
configuration registers so that just 3 addresses are not even
sufficient for the configuration registers on a single card. To solve
this problem, each card is assigned a card number (handle) using a
technique called "isolation". See <ref id="isolation_" name="ISA
Isolation"> for the complex details.
Then to configure a certain card, its card number (handle) is sent
out via the write-port address to tell that card that it is to listen
at its address port. All other cards note that this isn't their card
number and thus don't listen. Then the address of a configuration
register (for that card) is sent to the address-port (for all cards
--but only one is listening). Next, data transfer takes place with
that configuration register on that card by either doing a read on the
read-port or a write on the write-port.
The write-port is always at A79 and the address-port is always at 279
(hex). The read-port is not fixed but is set by the configuration
software at some address (in the range 203-3FF) that will hopefully
not conflict with any other ISA card. If there is a conflict, it will
change the address. All PnP cards get "programmed" with this address.
Thus if you use say isapnp to set or check configuration data it must
determine this read-port address.
<sect1> Interrupts --Details <label id="interrupt_detail">
<p> Interrupts convey a lot of information but only indirectly. The
interrupt request signal (a voltage on a wire) just tells a chip
called the interrupt controller that a certain device needs attention.
The interrupt controller then signals the CPU. The CPU then
interrupts whatever it was doing, finds the driver for this device and
runs a part of it known as an "interrupt service routine" (or
"interrupt handler"). This "routine" tries to find out what has
happened and then deals with the problem. For example, bytes may need
to be transferred from/to the device. This program (routine) can
easily find out what has happened since the device has registers at
addresses known to the the driver software (provided the IRQ number
and the I/O address of the device has been set correctly). These
registers contain status information about the device . The software
reads the contents of these registers and by inspecting the contents,
finds out what happened and takes appropriate action.
Thus each device driver needs to know what interrupt number (IRQ) to
listen to. On the PCI bus (and for some special cases on the ISA bus)
it's possible for two (or more) devices to share the same IRQ number.
When such an interrupt is issued, the CPU runs all interrupt service
routines for all devices using that interrupt. The first thing the
first service routine does is to check its device registers to see if
an interrupt actually happened for its device. If it finds that its
device didn't issue an interrupt (a false alarm) it likely will
immediately exit and the service routine begins for the second device
using that same interrupt, etc, etc.
The putting of a voltage on the IRQ line is only a request that the
CPU be interrupted so it can run a device driver. In almost all cases
the CPU is interrupted per the request. But interrupts may be
temporarily disabled or prioritized so that in rare cases the actual
interrupt doesn't happen (or gets delayed). Thus what was above
called an "interrupt" is more precisely only an interrupt request
and explains why IRQ stands for Interrupt ReQuest.
<sect1> PCI Interrupts
<p> There are two newer developments in PCI interrupts that are not
covered here. They are especially important for cases of more than
one CPU per computer. One is the Advanced Programmable Interrupt
Controller (APIC). See the file "IO-APIC" in the i386 directory of
the kernel documentation. Another new development is Message
Signalled Interrupts (MSI) where the interrupt is just a message sent
to a special address over the main computer bus (no interrupt lines
needed). But the device that sends such a message must first gain
control of the main bus so that it can send the interrupt message.
Such a message contains more info than just "I'm sending an
interrupt".
Ordinary PCI interrupts are different than ISA interrupts, but since
they are normally mapped to IRQs they behave in about the same way.
One major difference is that the BIOS does this mapping. Under Linux
it's not feasible to change it ?? unless the CMOS menu will let you do
it. But if you have the advanced APIC then there's a way to specify
it.
Another major difference is that PCI interrupts may be shared.
For example IRQ5 may be shared between two PCI devices. This sharing
ability is built into the hardware and all device drivers are supposed
to support it. Note that you can't share the same interrupt between
the PCI and ISA bus. However, illegal sharing will work provided the
devices which are in conflict are not in use at the same time. "In
use" here means that a program is running which "opened" the device in
its C programming code.
Here are some of the details of the PCI interrupt system. Each PCI
card (and device mounted on the motherboard) has 4 possible
interrupts: INTA#, INTB#, INTC#, INTD#. From now on we will call them
just A, B, C, and D. Each has its own pin on the edge connector of a
PCI card. Thus for a 7-slot system (for 7 cards) there could be 7 x 4
= 28 different interrupt lines for the cards. But the specs permit a
fewer number of interrupt lines, so many PCI buses seem to be made
with only 4 interrupt lines. This is not too restrictive since
interrupts may be shared. Call these lines (wires or traces) W, X, Y,
Z. There is an "interrupt router" chip that routes W, X, Y, Z to
selected IRQs. This routing can be changed by the BIOS or software.
For example, W may be routed to IRQ5. Suppose we designate the B
interrupt from slot 3 as interrupt 3B. Then interrupt 3B could be
permanently connected to W which is routed to IRQ5.
One simple method of connecting (hard-wiring) these lines from PCI
devices (such as 3B) to the interrupts W, etc. would be to connect all
A interrupts (INTA#) to line W, all B's to X, etc. This method was
once used many years ago but it is not a good solution. Here's
why. If a card only needs one interrupt, it's required that it use A.
If it needs two interrupts, it must use both A and B, etc. Thus INTA#
is used much more often than INTD#. So one winds up with an excessive
number of interrupts sharing the first line (W connected to all the
INTA#). To overcome this problem one may connect them in a more
complicated way so that each of the 4 interrupt lines (W, X, Y, Z)
will share about the same number of actual PCI interrupts.
One method of doing this would be to have wire W share interrupts 1A,
2B, 3C, 4D, 5A, 6B, 7C. This is done by physically connecting wire W
to wires 1A, 2B, etc. Likewise wire X could be connected to wires 1B,
2C, 3D, 4A, 5B, 6C, 7D, etc. Then on startup, the BIOS maps the X, W,
Y, Z to IRQs. After that it writes the IRQ that each device uses into
a hardware configuration register in each device. From then on, any
program interrogating this register can find out what IRQ the device
uses. Note that writing the IRQ in a register on a PCI card doesn't
in any way set the IRQ for that device.
A card in a slot may have up to 8 devices on it but there are only 4
PCI interrupts for it (A, B, C, D). This is OK since interrupts may
be shared so that each of the 8 devices (if they exist) can have an
interrupt. The PCI interrupt letter of a device is often fixed and
hardwired into the device. The assignment of interrupts is done by
the BIOS mapping the PCI interrupts to the ISA interrupts as mentioned
above. If there are only 4 lines (W, X, Y, and Z) as in the above
example, the mapping choices that the PCI BIOS has are limited. Some
motherboards may use more lines and thus have more choices. The BIOS
knows about how this is wired.
On the PCI bus, the BIOS assigns IRQs (interrupts) so as to avoid
conflicts with the IRQs it knows about on the ISA bus. Sometimes
the CMOS BIOS menu may allow one to assign IRQs to PCI cards or to
tell the BIOS what IRQs are to be reserved for ISA devices.
Also, a PnP operating system (for example MS Windows) could attempt to
assign IRQs after first finding out what the BIOS has done. The
assignments are known as a "routing table". If MS Windows makes such
IRQ assignment dynamically (such as a docking event) it's called
"IRQ steering". The BIOS may support it's own IRQ steering (which
Linux could use). Thus if Windows 9x changes what the BIOS set and you
use Linux after Windows without turning off your PC, the IRQs may be
different. Windows 2000 and XP doesn't change what the BIOS has set,
but it may add a new device (with a new IRQ).
You might think that since the PCI is using IRQs (designed for the ISA
bus) it might be slow since the ISA bus is slow. Not really. The ISA
Interrupt Controller Chip(s) has a direct interrupt wire going to the
CPU so it can get immediate attention. While signals on the ISA
address and data buses may be slow to get to the CPU, the IRQ
interrupt signals get there almost instantly.
<sect1> ISA Isolation <label id="isolation_">
<p> This is only for the ISA bus. Isolation is a complex method of
assigning a temporary handle (id number or Card Select Number = CSN)
to each PnP device on the ISA bus. Since there are more efficient
(but more complex) ways to do this, some might claim that it's a
simple method. Only one write address is used for PnP writes to all
PnP devices so that writing to this address goes to all PnP device
that are listening. This write address is used to send (assign) a
unique handle to each PnP device. To assign this handle requires that
only one device be listening when the handle is sent (written) to this
common address. All PnP devices have a unique serial number which
they use for the process of isolation. Doing isolation is something
like a game. It's done using the equivalent of just one common bus
wire connecting all PnP devices to the isolation program.
For the first round of the "game" all PnP devices listen on this wire
and send out simultaneously a sequence of bits to the wire. The
allowed bits are either a 1 (positive voltage) or an "open 0" of no
voltage (open circuit or tri-state). To do this, each PnP device just
starts to sequentially send out its serial number on this wire,
voltage (open circuit or tri-state). To do this, each PnP device just
starts to sequentially send out its serial number on this wire,
bit-by-bit, starting with the high-order bit. If any device sends a
1, a 1 will be heard on the wire by all other devices. If all devices
send an "open 0" nothing will be heard on the wire. The object is to
eliminate (by the end of this first round) all but highest serial
number device. "Eliminate" means to drop out of this round of the
game and thus temporarily cease to listen anymore to the wire. (Note
that all serial numbers are of the same length.) When there remains
only one device still listening, it will be given a handle (card
number).
First consider only the high-order bit of the serial number which is
put on the wire first by all devices which have no handle yet. If any
PnP device sends out a 0 (open 0) but hears a 1, this means that some
other PnP device has a higher serial number, so it temporarily drops
out of this round. Now the devices remaining in the game (for this
round) all have the same leading digit (a 1) so we may strip off this
digit and consider only the resulting "stripped serial number" for
future participation in this round. Then go to the start of this
paragraph and repeat until the entire serial number has been examined
for each device (see below for the all-0 case).
Thus it's clear that only cards with the lower serial number get
eliminated during a round. But what happens if all devices in the
game all send out a 0 as their high-order bit? In this case an "open
0" is sent on the line and all participants stay in the game. If they
all have a leading 0 then this is a tie and the 0's are stripped off
just like the 1's were in the above paragraph. The game then
continues as the next digit (of the serial number) is sent out.
At the end of the round (after the low-order bit of the serial number
has been sent out) only one PnP device with the highest serial number
remains in the game. It then gets assigned a handle and drops out of
the game permanently. Then all the dropouts from the previous round
(that don't have a handle yet) reenter the game and a new round begins
with one less participant. Eventually, all PnP devices are assigned
handles. It's easy to prove that this algorithm works. The actual
algorithm is a little more complex than that presented above since
each step is repeated twice to ensure reliability and the repeats are
done somewhat differently (but use the same basic idea).
Once all handles are assigned, they are used to address each PnP
device for sending/reading configuration data. Note that these
handles are only used for PnP configuration and are not used for
normal communication with the PnP device. When the computer starts
up a PnP BIOS will often do such an isolation and then a PnP
configuration. After that, all the handles are "lost" so that if one
wants to change (or inspect) the configuration again, the isolation
must be done over again.
END OF Plug-and-Play-HOWTO
</article>