Semplificando al massimo, il Plug-and-Play dice automaticamente al software (device driver o gestore (driver) di dispositivo) dove trovare i diversi pezzi hardware (i dispositivi) quali modem, schede di rete, schede audio, ecc. Il compito del Plug-and-Play è di far «accoppiare» dispositivi fisici con il software (gestori di dispositivo) che funziona con essi e di stabilire dei canali di comunicazione tra ogni dispositivo e il suo gestore. Più precisamente, il PnP alloca le seguenti «risorse-bus» sia al driver e che all'hardware: indirizzi I/O, IRQ, canali DMA (solo per il bus ISA) e regioni di memoria. Se non si capisce cosa siano queste 4 risorse-buse si leggano le sotto sezioni che seguono. Un articolo della Linux Gazette su 3 di queste risorse-bus è Introduction to IRQs, DMAs and Base Addresses. Una volta assegnate queste risorse-bus (e se è installato il gestore corretto) i file di dispositivo (device file) nella directory /dev/ sono pronti per l'uso.
Questo assegnamento PnP di certe risorse del bus è talvolta detto «configurazione», ma è solamente un tipo di configurazione a basso livello. Anche utilizzando pienamente il PnP, buona parte della configurazione dei dispositivi è fatta da qualche altra cosa. Ad esempio, per la configurazione dei modem, è inviata una «stringa di inizializzazione» al modem attraverso l'indirizzo di I/O del «canale». Questa «stringa di inizializzazione» non ha niente a che vedere con il PnP, sebbene il «canale» usato per inviarla al modem è stato allocato dal PnP. L'impostazione della velocità (e di molti altri parametri) di una porta seriale è fatta inviando messaggi al gestore del dispositivo («device driver») da programmi eseguiti dall'utente (spesso automaticamente all'avvio del sistema). Anche questa configurazione non ha niente a che spartire con il PnP. Quindi quando si parla di PnP con «configurazione» si intende solo un certo tipo di configurazione. Sebbene altra documentazione (come quella per MS Windows) chiama le risorse-bus semplicemente «risorse», io ho coniato il termine «risorse-bus» in modo da distringuerle dalla moltitudine di altri tipi di risorse.
Un computer consta di una CPU/processore per effettuare la computazione e di memoria per immagazzinare programmi e dati. Inoltre, ci sono diversi dispositivi come vari tipi di dischi, una scheda video, una tastiera, scheda di rete, schede modem, schede audio, porte seriali e parallele, ecc. C'è anche un alimentatore per fornire energia elettrica, diversi bus sulla scheda madre per connettere assieme i dispositivi e la CPU, e un case per metterci tutto dentro.
In tempi antichi quasi tutti i dispositivi avevano la proprio scheda di interfaccia (scheda a circuito stampato). Oggi, oltre a tali schede, molti «dispositivi» hanno un piccolo chip montato permanentemente sulla «scheda madre». Le schede che vengono inserite nella scheda madre possono contenere più di un dispositivo. I chip di memoria sono qualche volta considerati come dispositivi ma non sono Plug-and-Play nel senso usato in questo HOWTO.
Affinché un computer funzioni correttamente, ogni dispositivo dev'essere sotto il controllo del suo gestore o «device driver». È un software che è parte del sistema operativo (talvolta caricato come modulo) e che viene eseguito nella CPU. I gestori di dispositivo sono associati con «file speciali» nella directory /dev (notare che non sono propriamente dei file). Hanno nomi come hda1 (la prima partizione sul disco fisso a), ttyS0 (la prima porta seriale), eth1 (la seconda scheda ethernet), ecc. Per rendere le cose più complicate, il particolare device driver selezionato, diciamo per eth1, dipenderà dal tipo di scheda ethernet che si ha. Quindi eth1 non può semplicemente essere assegnato ad una qualsiasi gestore di scheda ethernet. Deve essere assegnato ad un particolare gestore che funzionerà con il tipo di scheda ethernet installata. Per controllare un dispositivo, la CPU (sotto il controllo del device driver) invia comandi (e dati) e legge informazioni dai vari dispositivi. Per poterlo fare ogni driver di dispositivo deve conoscere l'indirizzo del dispositivo che controlla. La conoscenza di tale indirizzo è equivalente all'impostazione di un canale di comunicazione, anche se il «canale» fisico è in realtà il bus dati dentro al PC che è condiviso praticamente da qualsiasi altra cosa presente nel computer.
Il canale di comunicazione è in realtà un po' più complesso di come appena descritto. Un «indirizzo» è in realtà un intervallo di indirizzi ed esiste la controparte del canale (nota come interrupt) che permette ai dispositivi di inviare richieste urgenti di «aiuto» ai loro gestori.
I PC hanno 3 spazi di indirizzi: I/O, memoria principale e configurazione (solo nel bus PCI). Tutti questi 3 tipi di spazi di indirizzi condividono lo stesso bus indirizzi (address bus) all'interno del PC. Ma il potenziale di alcune linee dedicate nel bus del PC segnala in quale «spazio» è un indirizzo: I/O, memoria principale o configurazione. Si veda la sezione Indirizzi per maggiori dettagli. I dispositivi sono originariamente posizionati nello spazio di indirizzi I/O, sebbene in alcuni casi questi allochino pure dello spazio in memoria principale. Un indirizzo I/O qualche volta è detto semplicemente «I/O», «IO», «i/o» o «io». È pure usato il termine «porta di I/O». Ci sono due passi principali per allocare gli indirizzi I/O (e altre risorse-bus, come gli interrupt):
Il precedente processo in due passi è qualcosa di simile al problema in due parti di trovare il numero di casa di qualcuno in una via. Si deve conoscere il numero di casa e qualcuno deve attaccare un numero nella facciata della casa in modo che possa essere trovata. Nei computer, il device driver deve conoscere l'indirizzo e il dispositivo hardware deve impostare lo stesso indirizzo in uno dei suoi registri. Entrambe queste cose devono essere fatte, ma alcuni fanno l'errore di farne solo una e poi si sorprendono quando il computer non riesce a trovare il dispositivo. Per esempio, provano ad usare «setserial» per assegnare un indirizzo ad una porta seriale senza realizzare che ciò comunica un indirizzo solamente al driver. Non imposta l'indirizzo nell'hardware della porta seriale stessa. Se la porta seriale ha in realtà un diverso indirizzo (o adirittura nessuno) e si dice qualcosa di errato a setserial, allora sì che si è nei casini.
Un altro vincolo ovvio è che un indirizzo deve essere per prima cosa impostato nella scheda prima che il gestore del dispositivo possa usarlo. Poiché i driver dei dispositivi spesso partono non appena è partito il computer, talvolta tentato di accedere ad una scheda (per vedere se è là, ecc.) prima che l'indirizzo sia stato impostato nella scheda dal programma PnP di configurazione. In tal caso si vede un messaggio d'errore che dice che non è possibile trovare la scheda sebbene questa ci sia (ma non ha ancora un indirizzo).
Quanto detto negli ultimi due paragrafi riguardo gli indirizzi I/O si applica tale e quale alle altre risorse-bus: IRQ -- Panoramica, Canali DMA, e Regioni di Memoria. Cosa siano queste cose verrà spiegato nelle tre sezioni che seguono.
Dopo aver letto questa sezione si può leggere Interrupt -- Dettagli per ulteriori dettagli. Quanto segue è intenzionalmente super semplificato. Oltre agli indirizzi, si deve gestire anche un numero di interruzione («interrupt») (come l'IRQ 5), detto numero di IRQ (Interrupt ReQuest = Richiesta di Interruzione). Si è già detto prima che il gestore del dispositivo deve conoscere l'indirizzo di una scheda per poter essere in grado di comunicare con quest'ultima. Ma cosa dire della comunicazione in senso opposto? Si supponga che il dispositivo debba comunicare qualcosa al suo gestore con una certa urgenza. Per esempio, il dispositivo potrebbe aver appena ricevuto un sacco di byte destinati alla memoria principale e quindi gli serve chiamare il suo gestore per trasferire questi dati dal suo buffer praticamente pieno alla memoria principale.
Il dispositivo come può chiedere aiuto? Non può usare il bus dati principali perché sicuramente è già in uso. Invece impone un particolare potenziale elettrico in una linea di interrupt dedicata (parte del bus), spesso riservata per quel particolare dispositivo. Questo segnale è detto interrupt («interruzione»). Ci sono l'equivalente di 16 linee di questo tipo in un PC e ognuna di queste comanda (indirettamente) da particolare gestore di dispositivo. Ogni linea ha un numero di IRQ (Interrupt ReQuest) univoco. Il dispositivo deve mettere il suo interrupt nella linea corretta e il gestore del dispositivo deve restare in attesa dell'interruzione sulla linea corretta. Su quale linea deve mettersi è specificato dal numero di IRQ salvato nel dispositivo. Lo stesso numero di IRQ dev'essere noto al gestore del dispositivo in modo che questo sappia su quale linea di IRQ restare in ascolto.
Una volta che il driver del dispositivo riceve l'interrupt (una chiamata di aiuto) deve capire perché è stato generato ed intraprendere l'azione appropriata per servire l'interrupt. Sul bus ISA ogni dispositivo ha bisogno di un proprio numero di IRQ univoco. Nel bus PCI, è permessa la condivisione degli IRQ.
I canali DMA esistono solo per il bus ISA. DMA sta per «Direct Memory Access» (Accesso Diretto alla Memoria). È il posto dove un dispositivo ha la possibilità di prendere (rubare) alla CPU il controllo del bus principale del computer e trasferire i dati direttamente nella memoria principale. Normalmente la CPU vorrebbe fare questo trasferimento in due passi: 1. leggendo i dati dallo spazio di I/O del dispositivo e mettendoli dentro la CPU stessa 2. scrivendo questi dati dalla CPU alla memoria principale. Con il DMA si fa solitamente un solo passo inviando i dati direttamente dal dispositivo alla memoria. Il dispositivo deve avere tale funzionalità nel suo hardware e quindi non tutti i dispositivi possono fare un DMA. Mentre è in esecuzione il DMA la CPU non può fare molto in quanto il bus principale è usato per il trasferimento DMA.
Il bus PCI non ha in realtà nessun DMA. Ha piuttosto qualcosa di ancora migliore: il bus mastering. Funziona in maniera simile al DMA e qualche volta è chiamato DMA (per esempio, i dischi fissi chiamati «UltraDMA»). Permette ad un dispositivo di diventare temporaneamente il padrone del bus (bus master) e di trasferire i dati in maniera analoga a quanto fa la CPU quando ne ha lei il potere. Non usa nessun numero di canale in quanto l'organizzazione del bus PCI è tale che l'hardware PCI sa quale dispositivo ha attualmente il controllo del bus e quali dispositivo lo sta chiedendo di diventare il prossimo bus master. Per il bus PCI non c'è quindi allocazione dei canali DMA.
Quando un dispositivo nel bus ISA vuole fare un DMA invia una richiesta DMA usando una linea dedicata per la richiesta di DMA in modo analogo ad una richiesta di interrupt. In realtà il DMA potrebbe essere gestito usando interrupt ma ciò introdurrebbe alcuni ritardi, cosicché è più veloce da fare utilizzando un tipo particolare di interrupt detto DMA-request. Come le interruzioni, le richieste DMA sono numerate in modo da identificare quale dispositivo sta facendo la richiesta. Questo numero è chiamato DMA-channel (canale DMA). Poiché tutti i trasferimenti DMA usano il bus principale (e solo uno può essere attivo in un determinato istante) in realtà usano tutti lo stesso canale, ma il numero del «canale DMA» serve per identificare chi sta usando il «canale». Nella scheda madre esistono dei registri hardware che contengono lo stato attuale di ogni «canale». Quindi per poter effettuare una richiesta DMA, il dispositivo deve conoscere il suo numero di canale DMA che deve essere salvato in un registro nel dispositivo fisico.
Ad alcuni dispositivi è assegnato dello spazio di indirizzi nella memoria principale. È spesso «memoria condivisa» (shared memory) o «I/O mappato in memoria» (memory mapped I/O). Altre volte è la memoria ROM stessa del dispositivo. Quando si parla delle risorse-bus si usa spesso semplicemente il termine «memoria». Quindi un dispositivo può anche usare uno spazio di indirizzi di I/O.
Quando di installa una scheda di questo tipo, in effetti si sta inserendo un modulo di memoria per la memoria principale. Questa memoria può essere sia ROM (Read Only Memory, Memoria a Sola Lettura) che memoria condivisa. Questa memoria può servire come mezzo di «trasferimento» diretto di dati tra il dispositivo e la memoria principale. Non è veramente un trasferimento in quanto il dispositivo mette i dati nella propria memoria che «casualmente» è la memoria principale. Sia la scheda che il gestore del dispositivo devono sapere dov'è questa memoria. L'indirizzo di memoria è solitamente molto alto in modo da non entrare in conflitto con gli indirizzi più bassi dei chip di memoria del computer.
La ROM è diversa. È come un programma (forse un gestore di dispositivo) che sarà usato con il dispositivo. Idealmente, dovrebbe funzionare con Linux e non solo con Windows ?? Può essere necessario che venga «oscurato» (shadowed), intendendo con ciò che viene copiato nei propri chip di memoria principale in modo da funzionare più velocemente. Un volta «oscurato» non è più a sola lettura.
I gestori di dispositivo devono quindi essere in qualche modo «collegati» all'hardware che controllano. Questo è fatto fornendo le risorse-bus (I/O, Memoria, IRQ e DMA) sia al dispositivo fisico che al software di gestione. Per esempio, una porta seriale usa solo 2 (delle 4 possibili) risorse: un IRQ e un indirizzo I/O. Entrambi questi valori deve essere comunicati sia al gestore del dispositivo che al dispositivo fisico stesso. Al gestore (e al suo dispositivo) è dato anche un nome (come ttyS1) nella directory /dev. L'indirizzo e il numero di IRQ sono salvati dal dispositivo in registri della scheda (o in un chip nella scheda madre). Nel caso di schede con i ponticelli (jumper), queste informazioni sono sempre salvate nell'hardware del dispositivo (sulla scheda, ecc.). Ma nel caso del PnP, i dati dei registri spesso vengono persi quanto il PC viene spento, cosicché le informazioni sulle risorse devono essere forniti di nuovo ad ogni dispositivo ogni volta che il PC viene riacceso.
L'architettura di un PC fornisce solo in numero limitato di IRQ, canali DMA, indirizzi I/O e regioni di memoria. Se ci fossero solo alcuni dispositivi e tutti questi avessero risorse-bus standardizzate (come indirizzi I/O e numeri IRQ unici) non ci sarebbero problemi a collegare i gestori di dispositivo ai dispositivi stessi. Ogni dispositivo avrebbe delle risorse fisse e non andrebbe in conflitto con qualsiasi altro dispositivo nel computer. Non ci sarebbero due dispositivi che vorrebbero avere gli stessi indirizzi, non ci sarebbero conflitti di IRQ, ecc. Ogni driver potrebbe quindi essere programmato con indirizzi, IRQ, ecc. univochi già codificati all'interno del programma. La vita sarebbe più semplice.
Ma così non è. Non solo oggi ci sono così tanti dispositivi che i conflitti sono frequenti, e qualche volta uno ha necessità di avere anche più di uno dello stesso tipo. Per esempio qualcuno potrebbe avere più di un disco fisso, un po' di porte seriali, ecc. Per queste ragioni i dispositivi devono possedere un minimo di flessibilità in modo che possano essere impostati a un qualsivoglia indirizzi, IRQ, ecc. siano necessari per evitare i conflitti. Ma alcuni IRQ e indirizzi, come quello del clock e della tastiera, sono piuttosto standard. Questi non hanno bisogno di tale flessibilità.
A parte il problema nel conflitto nell'allocazione delle risorse-bus, c'è anche un problema nel caso si commetta un errore nel dire al device driver quali sono le risorse-bus. Per esempio, si supponga di aver messo IRQ 4 in un file di configurazione quando in realtà il dispositivo è impostato all'IRQ 5. Questo è un altro tipo di errore nell'allocazione delle risorse-bus.
L'allocazione delle risorse-bus, se fatta correttamente, stabilisce i canali di comunicazione tra l'hardware fisico e i relativi device driver. Per esempio, se un determinato intervallo di indirizzi I/O (risorsa) è allocato sia al gestore di dispositivo che ad un pezzo di hardware, allora in questo modo si è stabilito un canale di comunicazione unidirezionale tra loro. Il driver può inviare comandi ed informazioni al dispositivo. In realtà è un po' più che unidirezionale, in quanto il driver può ottenere informazioni dal dispositivo leggendone i suoi registri. Ma il dispositivo in questo modo non può inizializzare una qualsiasi comunicazione. Per inizializzarla il dispositivo ha bisogno di un IRQ in modo da creare un canale bidirezionali nel quale sia il driver che il dispositivo possono iniziare una comunicazione.
Anche i dispositivi esterni connessi alla porta seriale attraverso un cavo (come i modem esterni) possono essere chiamati Plug-and-Play. Poiché solo la porta seriale stessa ha bisogno di risorse-bus (un IRQ e un indirizzo I/O) non è necessario allora risorse-bus per questo tipo di dispositivi. Quindi per essi il PnP non è in realtà necessario. Comunque, c'è una specifica PnP anche per questi dispositivi seriali esterni.
Un sistema operativo PnP troverà questi dispositivi esterni e leggerà il loro numero di modello, ecc. Poi può essere in grado di trovarne il gestore di dispositivo più adatto, e quindi non si deve dire ad un programma applicativo che si ha un certo dispositivo diciamo su /dev/ttyS1. Poiché si è in grado di informare manualmente il proprio programma applicativo (attraverso un file di configurazione, ecc.) su quale porta seriale è presente il dispositivo (ed eventualmente dicendogli anche qual'è il suo numero di modello) in realtà non si ha veramente bisogno di questa caratteristica PnP per le porte seriali.