|
xinetd
ArticleCategory:
System Administration
TranslationInfo:
Original
in fr Frédéric Raynal
AboutTheAuthor:
Frédéric Raynal is preparing a thesis about computed image watermarking
at the INRIA (Institut National de Recherche en Informatique et
Automatique).
Abstract
xinetd - extented Internet services daemon - fournit une excellente
sécurité contre les intrusions, et limite certains risques d'attaques
par Deny of Services (DoS). Comme la paire plus
connue (inetd+tcpd), il permet de fixer des droits d'accès à une
machine, mais ses capacités s'étendent bien au-delà. Cet article
vous propose de les découvrir.
Kesako
xinetd ?
Le désormais classique inetd a rendu de fiers services pour contrôler
les connexions vers une machine. Lorsqu'une requête arrive sur
un port géré par inetd, celui-ci la transmet alors au wrapper
qui décide de l'action à entreprendre relativement aux instructions
contenues dans hosts.{allow, deny}. Si la requête est autorisée,
le serveur associé la traite.
xinetd offre des capacités de
contrôle d'accès similaires à celles offertes par tcp_wrapper.
Toutefois, ses possibilités s'étendent bien au-delà :
- contrôle
d'accès pour des services TCP, UDP et RPC (pour ces derniers,
tout ne fonctionne pas très bien) ;
- contrôle
d'accès fondé sur des plages horaires ;
- logging
puissant, autant en cas de succès que d'échec de la connexion
;
- prévention
efficace contre les attaques de type Deny of Services
(DoS) qui bloquent une machine en saturant ses ressources
:
- limitations
du nombre de serveurs d'un même type qui peuvent tourner
en même temps ;
- limitations
du nombre total de serveur ;
- limitations
sur la taille des fichiers de log.
- attachement
d'un service à une interface particulière : ceci permet, par
exemple, de rendre des services accessibles à votre réseau
interne mais pas au reste du monde ;
- peut
faire office de proxy vers d'autres systèmes, ce qui s'avère
très pratique dans le cas de l'ip masquarading (ou de NAT)
afin d'atteindre des machines situées sur le réseau interne.
Le principal inconvénient, déjà mentionné, concerne les RPC qui
ne sont pas encore très bien supportés. Toutefois, portmap et
xinetd cohabitent parfaitement :)
La
première partie de cet article explique le fonctionnement général
de xinetd. Nous nous attarderons, par l'intermédiaire d'exemples,
sur la configuration générale d'un service, sur quelques options
particulières (attachement à une interface, redirection). La seconde
partie illustre le fonctionnement de xinted, les logs qu'il génère
et finit avec une petite astuce très utile.
Compilation
& Installation
Vous pouvez récupérer xinetd sur le site http://www.xinetd.org/.
La version utilisée pour cet article est la 2.1.8.9pre10.
La compilation et l'installation sont tout à fait classiques :
le triplet ./configure; make; make install fait tout :) Les options
habituelles sont supportées par le configure. Trois options particulières
sont également disponibles pour compiler ce programme :
- --with-libwrap
: avec cette option, xinetd commence par examiner les fichiers
de configuration de tcpd (/etc/hosts.{allow, deny}) et ensuite,
si l'accès est accordé, il utilise ses propres mécanismes
de contrôle. Cette option nécessite la présence du tcp_wrapper
et des librairies qui l'accompagnent. (Note de l'auteur :
ce qui est réalisable avec le wrapper l'est tout aussi bien
par xinetd. Autoriser cette compatibilité conduit à multiplier
les fichiers de configuration, ce qui complique l'administration
... bref, je ne le recommande pas) ;
- --with-loadavg
: cette option permet à xinetd de supporter l'option de configuration
max_load (charge maximale). Cela permet de désactiver certains
services lorsque la charge de la machine dépasse le seuil
donné, ce qui est essentiel pour prévenir certains DoS (voir
l'attribut max_load dans le tableau 1 ;
- --with-inet6
: si vous voulez utilisez IPv6, cette option en garantit le
support. Les connexions IPv4 et IPv6 sont gérées, mais
les adresses IPv4 se transforment au format IPv6.
Avant de démarrer xinetd, il n'est pas obligatoire d'arrêter inetd.
Toutefois, ne pas le faire entraîne un comportement relativement
imprévisible des deux démons !
Certains
signaux influencent le comportement de xinted :
- SIGUSR1
: reconfiguration soft : le fichier de configuration est relu
et les paramètres des services sont ajustés ;
- SIGUSR2
: reconfiguration hard : comme ci-dessus, mais tue en plus
les démons qui ne correspondent plus aux critères ;
- SIGTERM
: termine xinetd et tous les démons qu'il a générés.
Il en existe quelques autres (signalons juste une erreur dans
les documentations et pages man : le signal SIGHUP génère son
dump dans le fichier /var/run/xinetd.dump et non dans /tmp/xinetd.dump),
mais ces trois là permettent d'écrire rapidement un petit script
pour le gérer facilement à l'aide des options start, stop, restart,
soft, hard (ces deux dernières correspondent respectivement aux
signaux SIGUSR1 et SIGUSR2).
Configuration
Le fichier /etc/xinetd.conf configure, par défaut, le démon xinetd
(une option de la ligne de commande permet d'en désigner un autre).
Si la configuration de xinetd n'est pas très compliquée, elle
est longue et la syntaxe diffère malheureusement de celle employée
par son prédécesseur inetd.
Deux utilitaires (itox et xconv.pl)
sont fournis avec xinetd et permettent de convertir le fichier
/etc/inetd.conf en fichier de configuration pour xinetd. Bien
évidemment, ceci ne suffit pas dans la mesure où les règles stipulées
dans les fichiers de configuration du wrapper sont ignorées. itox
n'évolue plus, même s'il est encore maintenu. xconv.pl offre une
meilleure solution, même si le résultat nécessite d'être modifié,
ne serait-ce que parce que xinetd offre plus de possibilités qu'inetd.
>>/usr/local/sbin/xconv.pl
< /etc/inetd.conf > /etc/xinetd.conf
Le fichier de configuration commence par une section par défaut
dont les attributs seront utilisés pour tous les services pris
en charge par xinetd. Suivent alors autant de sections que de
services désirés, chacun pouvant redéfinir des options qui lui
seront spécifiques par rapport à celles par défaut.
La
section des valeurs par défauts s'écrit :
defaults
{
attribut opérateur valeur(s)
...
}
Chacun des attributs défini dans cette section conserve la (les)
valeur(s) fournie(s) pour les services décrits ensuite. Ainsi,
l'attribut only_from permet de stipuler une liste d'adresses autorisées
à se connecter aux serveurs :
only_from
= 192.168.1.0/24 192.168.5.0/24 192.168.10.17
Par la suite, tous les services déclarés autorisent l'accès aux
machines dont les adresses correspondent à l'une de celles indiquées.
Il est toutefois possible de modifier ces valeurs par défaut au
sein de chaque service (voir les opérateurs expliqués ci-après).
Cependant, cette démarche comporte certains risques. En effet,
il vaut mieux, pour des raisons de simplicité et de sécurité,
ne jamais définir de valeur par défaut qui soit ensuite modifiée
dans un service. Dans le cas de droits d'accès par exemple, la
politique la plus simple et la plus efficace consiste à interdire
par défaut l'accès à tout le monde pour ensuite autoriser l'accès
à chaque service seulement à ceux qui en ont besoin (avec tcp_wrapper,
cette politique se traduit par un hosts.deny contenant ALL:ALL@ALL,
et un hosts.allow ne contenant que les services autorisés avec
les adresses adéquates).
Chaque
section décrivant un service dans le fichier de configuration
est de la forme :
service
nom_du_service
{
attribut opérateur valeur(s)
...
}
Il existe trois opérateurs : '=', '+=' et '-='. La plupart des
attributs ne supporte que l'opérateur '=', qui fixe une valeur
à un attribut. L'opérateur '+=' ajoute un élément à une liste
de valeurs, alors que '-=' retire cet élément.
Le
tableau 1 décrit succinctement quelques uns des attributs. Nous
verrons leur utilisation dans les exemples qui suivront. La lecture
de la page man de xinetd.conf fournit de plus amples informations.
Attribut |
Valeurs
et description |
flags |
Seules
les valeurs les plus courantes sont décrites ici, regarder
dans la documentation pour découvrir les autres :
- IDONLY
: n'accepte de connexions que des clients qui disposent
d'un serveur d'identification ;
- NORETRY
: évite que le processus soit à nouveau "forké"
en cas d'échec ;
- NAMEINARGS
: le premier argument de l'attribut server_args est
utilisé en tant que argv[0] pour le server. Ceci permet
d'utiliser tcpd en le mettant dans l'attribut server,
puis d'écrire le nom du serveur et ses arguments comme
server_args, exactement comme avec inetd.
|
log_type |
xinetd
utilise syslogd et le sélecteur daemon.info par défaut.
- SYSLOG
sélecteur [level] : permet de choisir parmi les
entrées daemon, auth, user ou local0-7 de syslogd
;
- FILE
[taille_max [taille_max_absolue]] : le fichier spécifié
reçoit les informations. Les deux options fixent
des limites de taille du fichier. La première, lorsqu'elle
est atteinte, provoque l'émission d'un message vers
syslogd, la seconde arrête l'enregistrement des
logs pour le service concerné (s'il s'agit d'un
fichier commun - ou fixé par défaut - plusieurs
services peuvent alors être affectés).
|
log_on_success |
Différentes
informations sont enregistrables quand un serveur démarre
:
- PID
: le PID du serveur (s'il s'agit d'un service interne
à xinetd, le PID vaut alors 0) ;
- HOST
: l'adresse de du client ;
- USERID
: l'identité de l'utilisateur distant, en accord avec
la RFC1413 qui définit le protocole d'identification;
- EXIT
: le statu de sortie du processus ;
- DURATION
: la durée de la session.
|
log_on_failure |
Là
encore, xinetd dispose de multiples informations à enregistrer
quand un serveur ne peut démarrer, soit par manque de
ressource, soit à cause des règles d'accès :
- HOST,
USERID : comme ci-dessus ;
- ATTEMPT
: enregistre la fait qu'une tentative d'accès a eu
lieu. Cette option est automatique dès qu'une autre
valeur est stipulée ;
- RECORD
: enregistre toutes les informations disponibles sur
le client.
|
nice |
Modifie
la priorité du serveur, exactement comme avec la commande
nice. |
no_access |
Liste
de clients dont on refuse les connexions à ce service. |
only_from |
Liste
de clients autorisés. Si cet attribut n'a pas de valeur,
l'accès à ce service est interdit. |
port |
Le
port associé au service. Si celui-ci est également défini
dans /etc/service, les 2 numéros de port doivent correspondre. |
protocol |
Le
protocole stipulé doit exister dans /etc/protocols. S'il
n'en est pas fournit, le protocole par défaut associé
à ce service est employé. |
server |
Le
chemin vers le serveur à utiliser. |
server_args |
Des
arguments à passer au serveur. |
socket_type |
stream
(TCP), dgram (UDP), raw (accès direct à IP) ou seqpacket
(). |
type |
xinetd
gère 3 types de services :
- RPC
: pour ceux décrit dans /etc/rpc ... mais ne fonctionne
pas très bien ;
- INTERNAL
: pour les services pris directement en charge par
xinetd (echo, time, daytime, chargen et discard) ;
- UNLISTED
: pour les services non décrit soit dans /etc/rpc,
soit dans /etc/services ;
Notons qu'il est possible de combiner plusieurs de ces
valeurs, comme nous le verrons avec les services internes
servers, services et xadmin. |
wait |
Définit
la comportement du service vis-à-vis des threads. Deux
valeurs sont possibles :
- yes
: le service est mono-thread, une seule connexion
de ce type peut-être gérée à la fois par le service
;
- no
: à chaque nouvelle requête vers le service, un nouveau
serveur est démarré par xinetd, dans la limite maximale
définie (Attention, cette
limite est infinie par défaut).
|
cps |
Limite
le nombre le connexions entrantes. Le premier argument
est ce nombre lui-même. Lorsque ce seuil est dépassé,
le service se désactive pour un délai, exprimé en secondes,
fournit par le second argument. |
instances |
Détermine
le nombre maximal de serveurs d'un même type pouvant fonctionner
en même temps. |
max_load |
Ce
réel indique la charge maximale que peut occuper un serveur
(par exemple, 2 ou 2.5). Au-delà de cette limite, les
requêtes sur ce serveur sont rejetées. |
per_source |
Soit
un entier, soit UNLIMITED, pour restreindre le nombre
de connexions ayant une même origine à un serveur |
Tab. 1 : quelques attributs utilisables avec xinetd
Les
quatre derniers attributs présentés dans le tableau 1 permettent
de contrôler les ressources attachées aux serveurs. Ceci permet
de lutter efficacement contre certaines attaques par Deny of
Service (DoS), dont le but est de paralyser une machine en
occupant toutes ses ressources.
Cette
partie présentait quelques unes des possibilités offertes par
xinetd. Les parties suivantes montrent comment s'en servir et
précisent certaines règles de bon fonctionnement.
defaults
pour les services
La section defaults permet de fixer des valeurs pour certains
attributs (voir les documentations pour la liste complète). Parmi
cette liste, certains (only_from, no_access, log_on_success, log_on_failure,
...) cumulent les valeurs allouées dans cette section avec celles
fournies dans les services.
Interdire,
par défaut, tout accès à sa machine est la première étape
d'une politique de sécurisation viable. Ensuite, il ne restera
qu'à autoriser, en fonction des services, l'accès à qui de droit.
Nous avons vu deux attributs permettant de contrôler l'accès à
sa machine fondés sur les adresses IP : only_from et no_access.
Choisir le second en mettant :
no_access
= 0.0.0.0/0
bloque complètement l'accès aux services. Cependant, si vous souhaitez
autoriser tout le monde à accéder, par exemple, à echo, vous devrez
alors mettre dans le service echo :
only_from
= 0.0.0.0/0
Voici le message enregistré dans les log avec cette configuration
:
Sep
17 15:11:12 charly xinetd[26686]: Service=echo-stream: only_from
list and no_access list match equally the address 192.168.1.1
En fait, le contrôle d'accès se fait en comparant les listes d'adresses
contenues dans les deux attributs. Quand l'adresse du client correspond
aux 2 listes, la liste la moins générale l'emporte. En cas d'égalité,
comme c'est le cas dans notre exemple, xinetd se met dans une
situation d'indécidabilité et refuse la connexion. Pour
lever l'ambiguité, il aurait suffit de mettre :
only_from
= 192.0.0.0/8
Un autre solution, moins problématique, consiste à contrôler l'accès
uniquement avec l'attribut :
only_from
=
Ne rien préciser comme valeur condamne toutes les connexions à
l'échec :) Ensuite, chaque service délivre ses autorisations d'accès
au moyen de ce même attribut.
Détail
important, voire essentiel : en cas d'absence
complète de règles d'accès (i.e. ni only_from, ni no_access)
pour un service (allouées soit de manière directe, soit par le
biais de la section default), l'accès au
service est autorisé !
Voici
un exemple de defaults :
defaults
{
instances = 15
log_type =
FILE /var/log/servicelog
log_on_success = HOST PID USERID DURATION EXIT
log_on_failure = HOST USERID RECORD
only_from =
per_source = 5
disabled = shell login exec comsat
disabled = telnet ftp
disabled = name uucp tftp
disabled = finger systat netstat
#INTERNAL
disabled = time daytime chargen servers services xadmin
#RPC
disabled = rstatd rquotad rusersd sprayd walld
}
Parmi les services internes, servers, services, et xadmin
permettent de gérer xinetd. Nous en reparlerons plus loin.
configurer
un service
Pour configurer un service, nous avons besoin de .. rien :) En
fait, tout se comporte exactement comme avec les valeurs par défaut
: il suffit de préciser les attributs et leur(s) valeur(s) pour
paramétrer le service en question. Ceci entraîne soit une modification
des valeurs par défaut, soit l'ajout d'un attribut pour ce service.
Certains attributs doivent impérativement
apparaître en fonction du type du serveice (INTERNAL, UNLISTED
ou RPC) :
Attribut |
Commentaire |
socket-type |
Tous
les services. |
user |
Uniquement
pour les services non INTERNAL |
server |
Uniquement
pour les services non INTERNAL |
wait |
Tous
les services. |
protocol |
Tous
les services RPC et absents de /etc/services. |
rpc_version |
Tous
les services RPC. |
rpc_number |
Tous
les services RPC, absents de /etc/rpc. |
port |
Tous
les services non RPC, absents de /etc/services. |
Tab. 2 : attributs obligatoires
L'exemple
ci-dessous illustre la définition de services :
service
ntalk
{
socket_type = dgram
wait
= yes
user
= nobody
server = /usr/sbin/in.ntalkd
only_from = 192.168.1.0/24
}
service
ftp
{
socket_type = stream
wait
= no
user
= root
server = /usr/sbin/in.ftpd
server_args = -l
instances = 4
access_times = 7:00-12:30 13:30-21:00
nice
= 10
only_from = 192.168.1.0/24
}
Constatons
que ces services ne sont autorisés que sur le réseau interne (192.168.1.0/24).
Pour le FTP, des restrictions supplémentaires sont prévues : le
nombre d'instances est limité à 4 et il ne sera possible de l'utiliser
que pendant certaines plages horaires.
Attachement
à un port : l'attribut bind
Cet attribut permet de lier (to bind en Anglais) un service
à une adresse IP. Si votre machine ne dispose que d'une adresse,
ceci ne sert à rien. En revanche, prenons le cas d'un ordinateur
sur un réseau local mais également connecté à Internet : il dispose
au moins de deux adresses.
Par exemple, une société veut
mettre en place un serveur FTP pour ses employés (afin qu'ils
puissent consulter des documents internes). Elle tient également
à fournir à ses clients un accès FTP vers ses produits : bind
est fait pour cette société :) Nous allons définir deux services
FTP. Toutefois, xinetd doit pouvoir les distinguer : c'est là
qu'intervient l'attribut id, qui définit de manière unique un
service (lorsqu'il n'est pas défini dans un service, il vaut,
par défaut, le nom du service).
service
ftp
{
id
= ftp-public
wait
= no
user
= root
server = /usr/sbin/in.ftpd
server_args = -l
instances = 4
nice
= 10
only_from = 0.0.0.0/0 #autorisation
pour tous les clients
bind
= 212.198.253.142 #adresse IP publique de ce serveur
}
service
ftp
{
id
= ftp-private
socket_type = stream
wait
= no
user
= root
server = /usr/sbin/in.ftpd
server_args = -l
only_from = 192.168.1.0/24 #usage interne
seulement
bind
= 192.168.1.1 #adresse IP locale de ce serveur (charly)
}
L'utilisation de bind va permettre, selon la destination des paquets,
d'invoquer le démon correspondant. Ainsi, un client sur le réseau
local, dans cette configuration, doit préciser l'adresse locale
(ou le nom qui y est associé) pour accéder aux données internes.
Dans le fichier de logs, les traces suivantes apparaissent :
00/9/17@16:47:46:
START: ftp-public pid=26861 from=212.198.253.142
00/9/17@16:47:46: EXIT: ftp-public
status=0 pid=26861 duration=30(sec)
00/9/17@16:48:19: START: ftp-interne
pid=26864 from=192.168.1.1
00/9/17@16:48:19: EXIT: ftp-interne
status=0 pid=26864 duration=15(sec)
La première série résulte de la commande ftp
212.198.253.142, alors que la seconde, exécutée directement
de charly vers lui-même : ftp 192.168.1.1.
Un
problème apparaît clairement : que se passe-t-il si la machine
ne dispose pas de deux adresses IP fixes ? Ce cas de figure se
produit par exemple avec des connexions ppp ou si vous utilisez
le protocole dhcp. Il semble donc qu'il vaudrait mieux lier les
services aux interfaces qu'aux adresses. Toutefois, ceci n'est
pas encore prévu avec xinetd et pose de nombreux problèmes (entre
autre, écrire un module C pour accéder aux interfaces et aux adresses
dépend fortement de l'OS de l'ordinateur, or xinetd est supporté
par beaucoup d'OS différents ...) L'utilisation d'un script permet
de résoudre ce problème à moindre coût :
PUBLIC_ADDRESS=`/sbin/ifconfig
$1 | grep "inet addr" | awk '{print $2}'| awk -F:
'{print $2}'`
sed s/PUBLIC_ADDRESS/"$PUBLIC_ADDRESS"/g /etc/xinetd.base
> /etc/xinetd.conf
Ce script prend le fichier /etc/xinetd.base, qui contient la configuration
souhaitée avec PUBLIC_ADDRESS à la place de l'adresse variable,
et le transforme en /etc/xinetd.conf, en remplaçant la chaîne
de caractères PUBLIC_ADDRESS par l'adresse associée à l'interface
passée en argument du script. Ensuite, l'appel de ce script dépend
du type de connexion utilisé : le plus simple consiste à en ajouter
l'appel dans le fichier ifup-* adéquate et de (re)lancer xinetd.
Redirection
d'un service vers une autre machine : l'attribut redirect
xinetd peut se transformer en une sorte de proxy transparent (enfin,
presque ... comme nous le verrons) grâce à l'attribut redirect.
Il permet de réacheminer la requête parvenant à un service vers
une autre machine sur le port voulu.
service
telnet
{
flags = REUSE
socket_type = stream
wait = no
user = root
server = /usr/sbin/in.telnetd
only_from = 192.168.1.0/24
redirect = 192.168.1.15 23
}
Regardons ce qui se passe maintenant :
>>telnet
charly
Trying 192.168.1.1...
Connected to charly.
Escape character is '^]'.
Digital
UNIX (sabrina) (ttyp1)
login:
Effectivement, la connexion semble se faire sur charly, sauf que
la suite montre bien qu'en fait, sabrina (une alpha, d'où le "Digital
UNIX") a pris le relais. Ce mécanisme peut s'avérer à la
fois utile et dangereux. Lors de sa mise en place, des logs doivent
avoir lieu à chaque extrémité de la connexion. De plus, pour ce
type de service, l'utilisation d'une DMZ et de firewalls n'est
pas à négliger ;-)
services
spéciaux
xinetd dispose de trois services qui lui sont propres. Ces services
n'apparaissant ni dans /etc/rpc, ni dans /etc/services, doivent
avoir également le flag UNLISTED (en plus du flag INTERNAL qui
signale qu'il s'agit de services de xinetd)
- servers
: révèle les serveurs actuellement en cours d'utilisation
;
- services
: affiche les services disponibles, leur protocole et leur
port ;
- xadmin
: mélange les fonctions des deux précédents.
Bien évidemment, ces services exposent votre
ordinateur. Ils dévoilent des informations importantes.
Pour l'instant, leur accès n'est pas protégé (par un mot de passe
par exemple). Vous ne devez vous en servir que lors de la configuration
de xinetd. Ensuite, dans la section defaults, leur usage doit
être prohibé :
defaults
{
...
disabled = servers services xadmin
...
}
Avant de les initaliser, mieux vaut prendre quelques précautions
:
- seule
la machine sur laquelle tourne xinetd doit pouvoir s'y connecter
;
- limiter
le nombre d'instances à une ;
- n'autoriser
l'accès qu'à la machine sur laquelle tourne le serveur.
Prenons le cas du service xadmin (les deux autres se configurent
exactement de la même manière, au numéro de port près ;-) :
service
xadmin
{
type = INTERNAL UNLISTED
port = 9100
protocol = tcp
socket_type = stream
wait = no
instances = 1
only_from = 192.168.1.1 #charly
}
Le service xadmin dispose de 5 commandes :
- help
...
- show
run : comme pour le service servers, montre les serveurs actuellement
utilisés ;
- show
avail : comme pour le service services, affiche les services
disponibles (et quelques autres informations qui n'apparaissent
pas services) ;
- bye
ou exit ...
Vous savez maintenant qu'ils existent : oubliez-les ;-) Vous pouvez
tout à fait faire vos tests sans ces services Des commandes comme
(netstat, fuser, lsof, ... vous permettent justement de savoir
exactement ce qui se passe sur votre machine sans l'exposer autant
que ces services !
Jouons
un peu ...
Une
énigme pour commencer
Voici un petit exercice pour ceux qui ont survécu ;-) Après avoir
expliqué la configuration utilisée, une requête donne un résultat
surprenant. Nous mènerons l'enquête pour découvrir ce qui se passe.
Nous n'avons besoin que du service
finger :
service
finger
{
flags = REUSE NAMEINARGS
server = /usr/sbin/tcpd
server_args = in.fingerd
socket_type = stream
wait = no
user = nobody
only_from = 192.168.1.1 #charly
}
xinetd n'a pas été compilé avec l'option --with-libwrap (voir
l'attribut server). La section defaults est du même genre que
celle fournie précédemment : tout accès est interdit vers charly
quelle que soit la source de la connexion. Le service finger n'est
pas désactivé, et pourtant :
pappy@charly
>> finger pappy@charly
[charly]
pappy@charly >>
pappy@bosley
>> finger pappy@charly
[charly]
pappy@bosley
>>
Il semble que la requête n'ait pas fonctionné correctement, qu'elle
soit exécuté de charly (192.168.1.1), machine autorisée, ou bien
de bosley (192.168.1.10). Examinons les fichiers de logs :
/var/log/servicelog
:
00/9/18@17:15:42: START: finger pid=28857 from=192.168.1.1
00/9/18@17:15:47: EXIT: finger status=0 pid=28857 duration=5(sec)
00/9/18@17:15:55: FAIL: finger address from=192.168.1.10
La requête en provenance de charly (les deux premières lignes)
se déroule bien du point de vue de xinetd : l'accès est autorisé
et la requête prend 5 secondes. En revanche, la requête de issue
de bosley est rejeté (le FAIL).
Si on regarde la configuration du service finger, le serveur employé
n'est pas directement in.fingerd, mais le tcp_wrapper tcpd. Les
logs du wrapper contiennent les lignes suivantes :
/var/log/services
:
Sep 18 17:15:42 charly in.fingerd[28857]: refused connect from
192.168.1.1
Remarquons que nous ne découvrons qu'une seule ligne correspondant
à nos deux requêtes ! En effet, celle en provenance de bosley
(la seconde) a été interceptée par xinetd, donc, il est tout à
fait normal de ne pas la retrouver dans ce fichier. La ligne sélectionnée
correspond bien à la requête qu'a autorisé xinetd émise depuis
charly vers charly (la première) : l'heure et surtout le PID sont
identiques.
Résumons
les éléments en notre possession :
- xinetd
a autorisé la requête ;
- la
requête finger passe par tcpd ;
- in.fingerd
a refusé cette même requête.
Alors que se passe-t-il ? Puisque la requête est acceptée par
xinetd, elle est transmise au serveur spécifié (tcpd ici). Or,
tcpd refuse cette connexion. Il faut donc aller voir du côté de
hosts.{allow,deny}. En examinant ces fichiers, /etc/hosts.deny
ne contient que ALL:ALL@ALL, ce qui explique que la requête soit
rejetée par le wrapper !
En
fait, telles que les lignes server et server_args du service ont
été définies, les capacités du wrapper restent accessibles (banner
-il existe aussi un attribut banner avec xinetd-, spawn, twist,
...). Rappelons que l'option de compilation --with-libwrap ajoute
uniquement une vérification préalable, à l'aide des hosts.{allow,deny},
des droits d'accès avant que le processus propre à xinetd ne s'enclence.
Les écritures présentées ici permettent donc de continuer à employer
les mécanismes mis en oeuvre avec le wrapper.
Ce
chevauchement des capacités, s'il peut fonctionner, peut également
conduire à d'étranges comportements. Pour faire cohabiter xinetd,
inetd et portmap, il vaut mieux qu'un service ne soit géré que
par un seul de ces "super-démons".
chrooter
un service
Il est souvent conseillé de restreindre les domaines de certains
services, voire de créer un nouvel environnement. La commande
chroot permet de changer le répertoire racine pour la commande
(ou le script) qui sera exécutée ensuite :
chroot
[options] nouvelle_racine
Ceci s'utilise couramment pour protéger des services tels que
bind/DNS ou ftp. Pour reproduire ce comportement tout en bénéficient
des capacités de xinetd, il suffit de déclarer chroot en tant
que serveur. Il ne reste plus alors qu'à passer les autres arguments
par l'intermédiaire de l'attribut server_args :)
service
ftp
{
id
= ftp
socket_type = stream
wait
= no
user
= root
server = /usr/sbin/chroot
server_args = /var/servers/ftp /usr/sbin/in.ftpd
-l
}
Ainsi, lorsqu'une requête est destinée à ce service, la première
instruction utilisée est chroot. Ensuite, le premier argument
qui lui est passé est le premier de la ligne server_args, c'est-à-dire
la nouvelle racine. Enfin, le serveur désiré est démarrer.
Conclusion
Vous
pouvez vous demander quel démon choisir entre xinetd et inetd.
En fait, xinetd demande un petit effort supplémentaire d'administration,
surtout tant qu'il ne sera pas inclus directement dans les distributions
(il l'est dans la Red Hat 7.0). La solution la plus sûre consiste
à utiliser xinetd sur votre (vos) machine(s) ayant un accès public
(comme Internet) car il offre une meilleure ligne de défense.
Pour les autres, à l'intérieur de votre réseau, inetd suffit amplement.
Ne négliger toutefois pas l'emploi d'un firewall : son travail
ne se situe pas au même niveau.
pappy@users.sourceforge.net
Last modified: Sun Oct 1 18:41:37 CEST 2000
Copyright
(c) 2001 Linux Magazine France. Permission is granted to copy,
distribute and/or modify this document under the terms of the
GNU Free Documentation License, Version 1.1 or any later version
published by the Free Software Foundation; A copy of the license
is included in the section entitled "GNU Free Documentation
License".
|
|