W3docs

Funzione PHP getservbyname(): Tutto Quello che Devi Sapere

Come sviluppatore PHP, potresti dover ottenere il numero di porta associato a un determinato nome di servizio: la funzione getservbyname() fa al caso tuo.

I servizi di rete sono identificati da nomi ben noti come http, ftp o smtp, ma il sistema operativo instrada il traffico in base al numero di porta (80, 21, 25 e così via). La funzione getservbyname() di PHP cerca quel numero di porta per te, leggendo lo stesso database di servizi utilizzato dal resto del sistema. Questa pagina illustra la sintassi, cos'è il database, i casi d'uso comuni e le insidie da tenere d'occhio.

Sintassi

getservbyname(string $service, string $protocol): int|false

La funzione accetta due parametri obbligatori:

  • $service — il nome del servizio Internet, ad esempio "http", "ssh" o "smtp".
  • $protocol — il protocollo di trasporto, "tcp" o "udp". Contrariamente a quanto suggerisce molta documentazione più datata, questo argomento non è opzionale: devi necessariamente passarlo.

Restituisce il numero di porta come intero in caso di successo, oppure false se la coppia servizio/protocollo non viene trovata. Poiché false e una porta valida possono entrambi sembrare "falsy", utilizza sempre l'operatore rigoroso === quando verifichi i fallimenti.

Da dove provengono i dati

getservbyname() non si connette a nulla e non effettua supposizioni. Legge una tabella di ricerca locale:

  • Su Linux e macOS si tratta del file /etc/services.
  • Su Windows è %SystemRoot%\system32\drivers\etc\services.

Se un servizio manca da quel file, la ricerca fallisce anche se il servizio "ovviamente" esiste. Il risultato dipende quindi dalla macchina che esegue lo script, non è una costante universale.

Un esempio di base

php— editable, runs on the server

Il controllo === false è importante: separa nettamente un vero fallimento da un risultato legittimo come la porta 0 (che risulterebbe falsy con un confronto debole ==).

Ricerca di più servizi

In pratica spesso si risolve un gruppo di nomi in una sola volta — ad esempio per costruire un report firewall o per validare una configurazione:

<?php

$services = ["http", "https", "ftp", "smtp", "ssh"];

foreach ($services as $name) {
  $port = getservbyname($name, "tcp");
  echo $port === false
    ? "{$name}: not found\n"
    : "{$name}: {$port}\n";
}
/*
Output:
http: 80
https: 443
ftp: 21
smtp: 25
ssh: 22
*/

TCP vs UDP

Lo stesso nome di servizio può risolversi in voci diverse a seconda del protocollo, e alcuni servizi esistono solo per uno di essi. Passa sempre il protocollo che ti interessa effettivamente:

<?php

var_dump(getservbyname("domain", "tcp")); // int(53) — DNS over TCP
var_dump(getservbyname("domain", "udp")); // int(53) — DNS over UDP
var_dump(getservbyname("ntp", "udp"));    // int(123)
var_dump(getservbyname("madeup", "tcp")); // bool(false) — unknown service

Quando utilizzarla?

  • Costruire client di rete in modo dinamico. Risolvi un nome di servizio in una porta prima di aprire un socket con fsockopen() o pfsockopen(), in modo che il tuo codice contenga "smtp" anziché un magico 25.
  • Validare la configurazione. Verifica che un nome di servizio preso da un file di configurazione sia effettivamente noto all'host prima di utilizzarlo.
  • Reportistica e strumenti. Traduci nomi di servizio leggibili in porte per log, dashboard o regole firewall.

Funzioni correlate

  • getservbyport() — l'inverso: dato un numero di porta e un protocollo, restituisce il nome del servizio.
  • getprotobyname() — cerca il numero di protocollo (es. tcp6) tramite il suo nome.

Insidie comuni

  • Entrambi gli argomenti sono obbligatori. Omettere $protocol genera un errore; non esiste un valore predefinito implicito.
  • Solo confronto rigoroso. Usa === false per rilevare i fallimenti così da non interpretare erroneamente la porta 0 o un caso limite di stringa numerica.
  • Risultati dipendenti dall'host. La risposta proviene dal database dei servizi locale; un nome sconosciuto a una macchina potrebbe essere risolto su un'altra.
  • È offline. Nessun DNS, nessuna rete — è puramente una ricerca nella tabella locale, quindi è veloce e sicura da chiamare frequentemente.

getservbyname() mappa un nome di servizio e un protocollo in un numero di porta utilizzando il database dei servizi del sistema operativo, restituendo una porta intera oppure false quando la coppia è sconosciuta. Abbinala a getservbyport() per la direzione inversa e a fsockopen() quando hai bisogno di trasformare quella porta in una connessione effettiva.

Esercitazione

Pratica
Qual è lo scopo della funzione getservbyname() in PHP?
Qual è lo scopo della funzione getservbyname() in PHP?
Was this page helpful?