Published by

Il y a 11 ans -

Temps de lecture 10 minutes

SpringOne 2009 – Sécurisation d’Apache Tomcat

Depuis le rachat de Covalent en Janvier 2008, SpringSource est le premier contributeur au projet Apache Tomcat avec plus de 80% des commits ; Mark Thomas et Philip Thomas en sont les principaux acteurs.

Tomcat est la pierre angulaire de l’offre middleware de SpringSource aujourd’hui composée de tc Server, une version professionnelle Open Source de Tomcat et dm Server, un serveur OSGi (le format d’assemblage que SpringSource préfère aux classiques .war).

Mark Thomas a présenté lors de SpringOne 2009 : Securing Apache Tomcat For Your Environment les points essentiels sur ce sujet qui se décompose en trois thèmes : la confidentialité, l’intégrité et la disponibilité.

Planifier la correction des vulnérabilités

Même si les failles de sécurité sont extrêmement rares dans l’écosystème Java, il est nécessaire de se préparer à répondre à une vulnérabilité en ayant élaboré un plan d’application de correctifs. La réalité sera sûrement différente des plans, mais il est important d’avoir imaginé les rôles et responsabilités de chaque équipe (administrateurs, développement, support, recette, etc.) et de savoir quelle équipe fournira le chef de projet qui coordonnera tous les acteurs. Un plan de correction de vulnérabilités Tomcat comprendra typiquement les étapes suivantes :

  1. Prise de connaissance de la vulnérabilité : ces informations sont publiées sur le site web de Tomcat, diffusées sur les mailing lists Tomcat (une liste dédiée aux annonces de sécurité et de mises à jour sera bientôt disponible) ; un contrat de support Tomcat permettra aussi d’être averti. Il faut également identifier l’équipe (admin, dév, support, etc.) responsable de suivre ces informations.
  2. Lorsqu’une vulnérabilité est connue, il faut déterminer si elle s’applique à l’architecture mise en place (e.g. un problème AJP ne concernera pas les utilisateurs de mod_proxy_http, etc.) ; les équipes d’admin et de dév seront vraisemblablement impliquées dans cette étape. Un contrat de support pourra faciliter cette tâche.
  3. S’il s’avère nécessaire d’appliquer le correctif, l’équipe de développement réalisera les premiers tests de non-régression sur un poste de travail avant que l’équipe d’administrateurs installe le fix sur un environnement de validation (e.g. intégration ou pré-production) pour que les équipes de recette réalisent des tests de non-régression plus poussés.
  4. Une fois la non-régression confirmée par les équipes de recette, l’équipe d’administrateurs déploiera le correctif en production.
  5. Le chef de projet qui gère la correction d’une vulnérabilité de sécurité pourra à tout moment décider d’arrêter tout ou partie de l’application en production pour prévenir une attaque.

Ce type de plan pourrait sembler alarmiste ou excessif pour le monde Java mais il faut garder en tête que nous développons des applications critiques dont la compromission pourrait avoir des impacts autant financier que de notoriété.

Bonnes pratiques d’installation Tomcat

Permissions OS, JVM et réseau

  • Pour limiter l’impact en cas d’attaque réussie, créer un utilisateur dédié à l’exécution des serveurs tomcat (e.g. ‘tomcat’) aux droits limités à l’arborescence de répertoires utilisés par Tomcat. On pourra compléter cette approche par la création d’un groupe ‘tomcat’ dont feront partie les utilisateurs qui auront accès en lecture seule aux fichiers de l’arborescence Tomcat. Sous Linux/Unix, cela correspond à une politique de répertoire owner=rwx, group=r, other=none.
  • En cas de doute sur la bienveillance des applications web déployées sur le serveur Tomcat, utiliser le Security Manager Java pour limiter les droits d’accès (fichiers, socket, etc.) de ces applications.
  • Utiliser des firewalls aussi bien entrants que sortants. Si les premiers sont le plus souvent installés, il est hélas fréquent de ne pas avoir les seconds. Sans cela, du code malicieux pourra sans difficulté faire sortir sur Internet des informations sensibles ou télécharger des programmes malveillants (chevaux de Troie, etc.).

Applications par défaut

Il ne faut installer les applications fournies par défaut dans Tomcat que si elles sont utilisées :

  • Supprimer les applications docs et examples.
  • Remplacer l’application ROOT par une version épurée (e.g. ROOT.war). Notez qui si vous ne spécifiez pas d’application ROOT, les appels à des URLs non définies par une des applications déployées retourneront un message « 400 Bad Request » qui surprendra beaucoup plus que le traditionnel « 404 Not Found ».
  • Supprimer les applications manager et balancer-manager si vous reposez sur le classique déploiement d’applications par copie de fichier.

Realms

Les Realms fournis avec Tomcat avaient jusqu’à présent pour forte limitation de ne pas offrir de mécanisme de verrouillage des comptes utilisateurs et étaient donc exposés aux attaques par force brute. Tomcat 6.0.19 introduit un LockOutRealm qui offre ce verrouillage ainsi qu’un CombinedRealm qui permet de combiner des users déclarés dans plusieurs realms. Par ailleurs, les MemoryRealm et JDBCRealm ne devraient pas être utilisés en production respectivement parce que le premier ne permet pas de rechargement des users sans redémarrage et le second parce qu’il est limité à une seule connexion JDBC simultanée.

Shutdown Port, un reliquat des premières heures de Java

Le shutdown port servait pour les JVM inférieures à 1.3 qui ne supportaient pas les shutdownHook mais représente aujourd’hui une faille de sécurité : n’importe quel utilisateur connecté sur la machine peut arrêter le serveur Tomcat avec un simple telnet ; les mécanismes de permissions liés au propriétaire du processus sont ignorés.

Ce shutdown port doit être désactivé (server port="-1" ... ) au profit du classique kill Unix ou d’un service Windows . Désactiver ce mécanisme nécessite une adaptation du script catalina.sh et, sur les plateformes linux/unix qui utilisent kill, s’accompagne de la déclaration dans setenv.sh de la variable CATALINA_PID pour créer un fichier qui porte l’id du processus Tomcat.

Si vous ne pouvez désactiver le shutdown port, remplacez la commande d’arrêt par défaut « SHUTDOWN » par un mot secret imprédictible. Il n’est hélas pas possible de filtrer l’adresse IP de l’appelant.
Exemple (Shutdown port avec un commande d’arrêt imprédictible) :


Logs et audit

L’AccessLogValve doit être utilisée pour tracer les requêtes HTTP. On déclarera communément un fichier de log par host pour identifier le host saisi dans l’url d’appel qui, à la différence de l’URI, n’apparaît pas dans le fichier access_log. Si Tomcat est positionné derrière un load balancer ou un reverse proxy, il faut gérer le header X-Forwarded-For (voir « Tomcat – Adresse IP de l’internaute, load balancer, reverse proxy et header Http X-Forwarded-For« ).

Ces fichiers de log, au même titre que les logs applicatives, doivent être archivés.

Exemple (configuration d’un Access Log par Host) :


Filtrage des requêtes entrantes

Tomcat permet de filtrer les requêtes en fonction de l’adresse IP ou du host de l’appelant (respectivement RemoteAddrValve et RemoteHostValve). Le deuxième filtre connaît peu de scénarios d’utilisation. Comme pour l’AccessLogValve, si Tomcat est positionné derrière un load balancer ou un reverse proxy, il faut gérer le header X-Forwarded-For (voir infra « Adresse IP de l’internaute, reverse proxy et header Http X-Forwarded-For »). Exemple (Filtrage des IP appelantes) :


Protection des mots de passe présents dans la configuration

Tomcat a exclu la mise en oeuvre de mécanismes de protection des mots de passe saisis dans les fichiers de configuration au motif que ces mécanismes nécessitent l’utilisation d’un nouveau secret d’obfuscation qui devient alors difficile à protéger et conduirait donc à un problème de type « serpent qui se mord la queue ».

Nous corroborerons ce raisonnement remettant en cause les mécanismes de type « protection pour qu’on ne se souvienne pas du mot de passe en regardant par dessus l’épaule d’un administrateur » : si un mot de passe est vraiment compliqué (majuscules, minuscules, chiffres et caractères de ponctuation), il n’est pas mémorisable d’un simple coup d’oeil ; la génération de tels mots de passe est très simple avec les nombreux sites web qui offrent gratuitement ce service (e.g. PC Tools Secure Password Generator).

Limitations des déploiements d’applications

Tomcat offre le déploiement de nouvelles applications lorsque le serveur est déjà démarré. Cette fonctionnalité se désactive en positionnant la propriété autoDeploy à false :
Désactivation du déploiement d’applications lorsque Tomcat est démarré :


Tomcat permet également de déployer de nouvelles applications présentes sous le répertoire webapps (nom de répertoire défini par la propriété appbase). Cette fonctionnalité se désactive en positionnant la propriété deployOnStartup à false :
Désactivation du déploiement d’applications au démarrage de Tomcat :


Lorsque ces deux propriétés sont désactivées, seules les applications déclarées dans server.xml sont déployées.

Par ailleurs, la propriété deployXML permet, en la mettant à false, de désactiver les éléments de configuration embarqués par les web applications dans le fichier /META-INF/context.xml

Protection contre les dénis de service

Les connecteurs Http et AJP intègrent une protection contre les dénis de service en limitant la taille des requêtes (attribut maxPostSize dont la limite par défaut est de 2 Mo) et limitant la taille des requêtes lors d’authentification par certificat client ou formulaire géré par Tomcat (attribut maxSavePostSize dont la limite par défaut est de 4 Ko). Cette limite s’applique au corps de la requête et pas aux uploads de fichiers dont la limitation est déléguée au framework qui gère l’upload. Par exemple, Apache Commons File Upload offre pour cela un paramètre maxSize.

Apache Httpd offre un mécanisme similaire avec la directive LimitRequestBody mais cette protection n’est pas activée par défaut.

Autres bonnes pratiques de sécurité

La taille d’un fichier server.xml ne devrait pas dépasser un écran, il faut retirer ce qui est inutile (dans l’hypothèse où les applications ne sont pas déclarées dans ce fichier).

Si vous migrez de Tomcat 5.5 ou inférieur à Tomcat 6.0, il ne faut pas réutiliser les anciens fichiers server.xml mais en réécrire de nouveau, à partir du modèle standard livré avec Tomcat.

L’InvokerServlet doit rester désactivée. D’ailleurs, elle sera retirée de Tomcat 7. La [Default Servlet|http://tomcat.apache.org/tomcat-6.0-doc/default-servlet.html] doit conserver le paramètre readonly à true (désactivation des requêtes PUT et DELETE sur les contenus statiques) et le paramètre listings à false (désactivation de la liste des fichiers d’un répertoire).

La possibilité d’utiliser des request dispatchers inter web applications (attribut crossContext ) devrait rester désactivée comme l’autorisation d’accéder à des composants internes Tomcat depuis les web applications (attribut privileged) et la possibilité d’utiliser des liens symboliques dans les web applications ( attribut allowLinking). L’activation de cette dernière option exposerait le serveur à des risques de type directory traversal.

Pour aller plus loin

* Apache Tomcat Tips and Tricks from the Pros (webinar),
* Performance Tuning Apache Tomcat for Production (webinar),
* Performance Tuning for Apache Tomcat (slides de SpringOne 2009),
* The Center for Internet Security : CIS Apache Tomcat Server Benchmark v.1.0.0. 55 pages très instructives sur la sécurisation de Tomcat. Si vous avez aimé, regardez aussi CIS Apache Web Server 1.3.37/2.0.59/2.2.4 Benchmark v2.2.0.

11/05/2009 : prise en compte de la remarque d’Arnaud : « n’importe qui peut arrêter le serveur Tomcat avec un simple telnet » -> « n’importe quel utilisateur connecté sur la machine peut arrêter le serveur Tomcat avec un simple telnet ; les mécanismes de permissions liés au propriétaire du processus sont ignorés ».
27/01/2010 : ajout des références à « CIS Apache Tomcat Server Benchmark v.1.0.0 » et « CIS Apache Web Server 1.3.37/2.0.59/2.2.4 Benchmark v2.2.0 »

Published by

Publié par Cyrille Le Clerc

CTO de Xebia, Cyrille est aussi committer sur le projet Apache CXF. Après être récemment intervenu sur les sites web et les plateformes de web service à fort traffic d'opérateurs de télécommunication, Cyrille est actuellement responsable de la mise en place d'une grille de données inter-continentale pour une grande institution financière française. Après 7 ans chez IBM Global Services et 5 ans chez Xebia, Cyrille a une expérience variée allant du monde commercial aux écosystèmes Open Source dans des approches aussi bien très cadrées et contractuelles que légères et agiles. Cyrille est aussi blogger sur blog.engineering.publicissapient.fr et speaker dans des conférences (In Memory Data Grids & NoSQL, applications prêtes pour la production, etc).

Commentaire

8 réponses pour " SpringOne 2009 – Sécurisation d’Apache Tomcat "

  1. Published by , Il y a 11 ans

    Comme d’habitude avec Cyrille, un excellent article qui déchire sa mémère. Et quand en plus Mark Thomas est de la partie, ça roxe carrément les poneys. Bravo et merci!

  2. Published by , Il y a 11 ans

    Merci pour ce résumé complet. J’attendais les slides mais je n’en n’ai plus besoin.

  3. Published by , Il y a 11 ans

    Merci pou vos encouragements. Nous avons encore plusieurs sujets de billets liés à SpringOne 2009. Nous nous y remettrons juste après la soirée Data Grid que nous animerons mardi 12 Mai au Paris JUG.
    Nous avons notamment en tête :

    • – Tomcat en production (complétant la présentation Performance Tuning for Apache Tomcat de nos expériences de terrain)
    • – Monitoring Tomcat : Hyperic HQ, SpringSource tc Server, Nagios et les autres.
    • – Roadmap de SpringSource : de tc Server au cloud computing en passant par le rachat d’Hyperic et le partenariat sur la virtualisation avec VMWare. Ce qui est disponible, ce qui se profile et la vision rêvée.
    • – Plain Old Java versus Spring ROO versus Groovy/Grails : comment SpringSource espère nous faire gagner en productivité ou « One Size Does Not Fit All ».

    Enfin, plein de beaux sujets mais avant, nous espérons vous voir à la soirée Data Grid au Paris JUG mardi 12 Mai ;-)

    Cyrille (Xebia)

  4. Published by , Il y a 11 ans

    « n’importe qui peut arrêter le serveur Tomcat avec un simple telnet. »
    Je ne crois pas, il faut au moins être sur la même machine:
    http://marc.info/?l=tomcat-user&m=103176795905127&w=2

    StandardServer.java:

    // Set up a server socket to wait on
    ServerSocket serverSocket = null;
    try {
    serverSocket =
    new ServerSocket(port, 1,
    InetAddress.getByName(« localhost »));

  5. Published by , Il y a 11 ans

    Merci pour votre clarification Arnaud, je modifie le billet pour prendre en compte votre ajout :
    « N’importe quel user connecté à la machine peut arrêter le serveur Tomcat avec un simple Telnet. Les mécanismes de permission liés au propriétaire du processus ne sont pas pris en compte ».

    Cyrille (Xebia)

  6. Published by , Il y a 11 ans

    Précisions bien utiles pour tenter d’optimiser tomcat, qui de base se montre -hélas- trop peu adapté à un véritable environnement de prod.

  7. Published by , Il y a 11 ans

    Merci Miguel pour cette ouverture !

    Nous souhaitons depuis des mois rédiger une série de billet « Tomcat en production » qui partirait de la configuration Apache Httpd pour aller jusqu’à la supervision en passant par les logs, le load balancing, la haute disponibilité, le déploiement, la gestion de configuration, etc

    Nous y retrouverions mod_proxy, mod_proxy_balancer, mod_expires, mod_cache, mod_deflate, les GUI /server-status & /balancer-manager, le connector Http11NioProtocol, le thread-pool tomcat, le layout avec séparation de TOMCAT_BASE et TOMCAT_HOME, la désactivation du java.util.logging.ConsoleHandler, le problème du passage de firewalls avec JMX, les solutions de monitoring comme Hyperic HQ et Nagios, les déploiements scriptés multi-phases, la mise sous SVN d’arborescences CATALINA_BASE, etc

    Et nous pourrions conclure avec un produit Open Source Professionnel qui règle la plupart des besoins de productions non traités dans la version de base de Tomcat : SpringSource Tc Server.

    Plein de choses à raconter, il ne reste plus qu’à se retrousser les manches pour rédiger ;-) .

    Cyrille (Xebia)

Laisser un commentaire

Votre adresse de messagerie ne sera pas publiée. Les champs obligatoires sont indiqués avec *

Nous recrutons

Être un Sapient, c'est faire partie d'un groupe de passionnés ; C'est l'opportunité de travailler et de partager avec des pairs parmi les plus talentueux.