I file dei socket Internet Unix sono?


23

Capisco che "Tutto è un file" è uno dei concetti principali di Unix, ma i socket usano API diverse fornite dal kernel (come socket, sendto, recv, ecc.), Non come le normali interfacce del file system.

Come si applica questo "Tutto è un file" qui?

Risposte:


26

i socket utilizzano API diverse

Questo non è del tutto vero. Esistono alcune funzioni aggiuntive da utilizzare con i socket, ma è possibile utilizzare, ad esempio, normale read()e write()su un socket fd.

come si applica questo "Tutto è un file" qui?

Nel senso che è coinvolto un descrittore di file.

Se la tua definizione di "file" è una sequenza discreta di byte memorizzati in un filesystem, allora non tutto è un file. Tuttavia, se la tua definizione di file è più simile a un handle - un canale di informazione, ovvero una connessione I / O - allora "tutto è un file" inizia a dare più senso. Queste cose implicano inevitabilmente sequenze di byte, ma la loro provenienza o destinazione potrebbe differire contestualmente.

Non è davvero inteso alla lettera, tuttavia. Un demone non è un file, un demone è un processo; ma se stai facendo IPC, il tuo metodo di relazione con un altro processo potrebbe essere mitigato da entità di stile file.


5
Direi che una riformulazione accurata di "tutto è un file" dovrebbe essere "tutte le interfacce sono attraverso i file". Interagisci con i processi attraverso i file (stdin / out / err, / proc / $ pid, ecc.). Si interagisce con la rete tramite file (socket / descrittori di file). Interagisci con il mouse attraverso un file (/ dev / mouse).
Patrick,

Una volta ho clonato un handle di socket aprendolo da / proc.
Giosuè,

12

"Tutto è un file" è solo un'esagerazione. Era un romanzo degli anni '70 ed era una caratteristica distintiva primaria di UNIX. Ma è solo un concetto di marketing, non una vera base di UNIX, perché ovviamente non è vero. Non è utile o sensato trattare TUTTO come un file.

La CPU è un file? Il tuo programma legge () una CPU per ottenere una nuova istruzione? La RAM è un file? Il tuo programma legge () il byte successivo?

Allora, c'erano tipi di sistemi operativi che ti davano un'API per un disco floppy e un'API diversa per un disco rigido, un'API diversa per il nastro magnetico e un mucchio di API diverse per terminali diversi e così via. I sistemi mainframe IBM avevano diversi tipi di file sui dischi rigidi e ti davano un'API diversa per ognuno di essi, che ci crediate o no! Quindi l'approccio UNIX "è un file", insieme all'approccio "stdin / stdout / stderr", ha portato un'astrazione molto elegante sia per gli utenti che per i programmatori.

Con la rete, questa particolare astrazione non ha funzionato. E non c'è nulla di male, solo un po 'meno eleganza generale e coerenza del sistema operativo. Ma funziona Vedi un file chiamato /dev/myinternetz/www/google/com/tcp/80oggi sul tuo sistema? Puoi aprire (), scrivere () una query e leggere () la risposta in un bel HTML? No? Questo perché l'astrazione "è un file" non era molto utile per interagire in rete. In pratica non funzionerebbe troppo bene. Legge delle astrazioni che perdono in azione.


9
Curiosità: alcune versioni di bash ti permetteranno di aprire /dev/tcp/www.google.com/80. Non è un vero file però - bash lo sta solo fingendo.
user253751

2
@immibs: Più il punto, sarebbe ragionevolmente possibile creare un filesystem che lo implementa effettivamente.
Giosuè,

Suppongo che potresti leggere /dev/memo /dev/kmemse lo desideri.
Jason C,

4
Si noti che il piano 9 va oltre e in effetti i protocolli di rete sono indirizzati attraverso uno pseudo filesystem all'effetto del tuo esempio / dev / myinternetz / www / google / com / tcp / 80 (con un percorso diverso ovviamente). Inoltre, ram fisico in realtà funziona in modo molto simile a un file, mmap ram nello spazio degli indirizzi virtuali proprio come mmap un file in esso. (malloc è implementato su questa idea).
Valità,

1
Il piano 9 che porta "tutto è un file" all'estremo e "tutto è trasparente in rete" ha delle implicazioni piuttosto potenti. Ad esempio, non è necessario NAT, puoi semplicemente montare lo stack TCP / IP del tuo router (che è solo un file (sistema) trasparente di rete) sul tuo computer locale e inviare pacchetti direttamente dal tuo router.
Jörg W Mittag,

7

I socket sono file. Puoi usare reade writesu un socket: sono equivalenti a chiamare recve sendcon flags=0. Li chiudi con close. Puoi spostarli con dupe gli amici se devi mescolare i descrittori di file. È possibile impostare alcuni flag con fcntle utilizzare il buffering stdio dopo la chiamata fdopen. L'elenco continua. È molto importante, è possibile chiamare selecte pollsu qualsiasi tipo di file, inclusi i socket, quindi queste funzioni consentono a un programma di bloccare fino a quando non riceve input in qualsiasi modo semplicemente elencando i descrittori di file.

Esistono chiamate di sistema aggiuntive per alcuni tipi di socket ( recve send, shutdownecc.), Come una chiamata di sistema aggiuntiva per dispositivi ( ioctl).

Non tutti i file hanno nomi e, tra quelli che lo fanno, non vivono sempre nella struttura delle directory. Le pipe create da pipe(ad esempio in una pipeline di shell) e le socket create da socketpairnon hanno nomi, ma sono comunque file. I socket creati da sockethanno un nome la cui sintassi dipende dal dominio. Questo nome viene passato in una struct sockaddra binde altre funzioni. Per un AF_UNIXsocket Unix ( ), il nome è a struct sockaddr_un, che è una famiglia e una stringa; a seconda della stringa, questo può essere un nome di file (i socket nominati possono essere creati con mknodsu molte varianti unix) oppure no (lo spazio dei nomi astratto). Per un AF_INETsocket IPv4 ( ), il nome è a struct sockaddr_in, contenente un numero di porta e un indirizzo IP, più il protocoldalla socketchiamata.


7

Se sei statun socket, vedrai che ha un numero di inode e altre caratteristiche dei file normali, quindi lo classificherei come file sul filesystem. Esempio:

# file live
live: socket
# stat live
File: `live'
  Size: 0               Blocks: 0          IO Block: 4096   socket
Device: fc03h/64515d    Inode: 198817      Links: 1
Access: (0660/srw-rw----)  Uid: (23129/  icinga)   Gid: (23130/icinga-cmd)
Access: 2014-11-07 09:27:59.000000000 -0800
Modify: 2014-11-05 09:27:03.000000000 -0800
Change: 2014-11-05 09:27:03.000000000 -0800

11/17. Informazioni aggiuntive per Linux (ext3): un socket ha un inode (che è un blocco di 256 byte sul disco) ma non ha blocchi di dati (è possibile verificarlo estraendo l'inode ed esaminando i puntatori del blocco di dati; oppure eseguendo debugfs 'stat' che mostra un Blockcount di 0). Quindi, ha metadati di file (proprietario, gruppo, autorizzazioni, ecc.) Ma nessun contenuto di dati sul disco. Questo è identico a un normale file vuoto ( touch /tmp/foo) che ha anche un conteggio blocchi di 0. Nel primo caso, il campo "tipo" nell'inode mostra "socket"; nel secondo caso mostra "file normale".

Riferimenti: struttura dell'inode ext2 ; stat, dumpe2fse debugfscomandi.


1
Direi che avere qualcosa da eseguire fileo statsu lo rende un file.
Kevin,
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.