Sur scène à nouveau vainqueurs des compétitions internationales SSH et sudo. Sous la direction de Honored Conductor Active Directory

Historiquement, les droits sudo étaient réglementés par le contenu des fichiers de /etc/sudoers.d et visudo , et l'autorisation de clé était effectuée à l' aide de ~ / .ssh / authorized_keys . Cependant, avec la croissance des infrastructures, on souhaite gérer ces droits de manière centralisée. À ce jour, il peut y avoir plusieurs solutions:

  • Système de gestion de la configuration - Chef , Puppet , Ansible , Salt
  • Active Directory + sssd
  • Différentes distorsions sous forme de scripts et édition manuelle de fichiers

À mon avis, la meilleure option pour une gestion centralisée est toujours un tas d' Active Directory + sssd . Les avantages de cette approche sont:

  • Vraiment un seul répertoire utilisateur centralisé.
  • La distribution des droits sudo consiste à ajouter un utilisateur à un groupe de sécurité spécifique.
  • Dans le cas de divers systèmes Linux, il est nécessaire d'introduire des vérifications supplémentaires pour déterminer le système d'exploitation lors de l'utilisation des systèmes de configuration.

La suite d'aujourd'hui sera dédiée au bundle Active Directory + sssd pour la gestion des droits sudo et le stockage des clés ssh dans un référentiel unique.
Alors, le public se figea dans un silence tendu, le chef d'orchestre leva sa baguette, l'orchestre se prépara.
Allons-y.

Étant donné:

  • Domaine Active Directory testopf.local sur Windows Server 2012 R2.
  • Hôte Linux exécutant Centos 7
  • Autorisation configurée à l'aide de sssd

Les deux solutions apportent des modifications au schéma Active Directory , nous vérifions donc tout sur un environnement de test et ensuite seulement apportons des modifications à l'infrastructure de travail. Je veux noter - toutes les modifications sont basées sur des points et, en fait, n'ajoutent que les attributs et les classes nécessaires.

Étape 1: gérer les rôles sudo via Active Directory .


Pour étendre le schéma Active Directory, vous devez télécharger la dernière version sudo - 1.8.27 aujourd'hui. Décompressez, copiez le fichier schema.ActiveDirectory du répertoire ./doc vers le contrôleur de domaine. À partir de la ligne de commande avec les droits d'administrateur du répertoire dans lequel vous avez copié le fichier, exécutez:

ldifde -i -f schema.ActiveDirectory -c dc=X dc=testopf,dc=local
(N'oubliez pas de substituer vos valeurs)

Ouvrez adsiedit.msc et connectez-vous au contexte par défaut:

À la racine du domaine, créez une unité sudoers . (Les bourgeois soutiennent obstinément que c'est dans cette subdivision que le démon sssd recherche les objets sudoRole . Cependant, après avoir activé le débogage détaillé et examiné les journaux, il a été révélé que la recherche est effectuée dans l'arborescence du catalogue.)

Créez le premier objet de l'unité qui appartient à la classe sudoRole . Le nom peut être choisi de manière absolument arbitraire, car il sert uniquement à une identification pratique.

Parmi les attributs disponibles possibles de l'extension de schéma, les principaux sont:

  • sudoCommand - Détermine quelles commandes sont autorisées à s'exécuter sur l'hôte.
  • sudoHost - détermine à quels hôtes ce rôle s'applique. Il peut être défini comme TOUT ou pour un hôte individuel par son nom. Il est également possible d'utiliser un masque.
  • sudoUser - indique quels utilisateurs sont autorisés à exécuter sudo .
    Si un groupe de sécurité est spécifié, ajoutez le signe «%» au début du nom. S'il y a des espaces dans le nom du groupe, il n'y a rien à craindre. À en juger par les journaux, le mécanisme sssd prend la tâche d'échapper aux espaces.


Figure 1. Objets sudoRole dans l'unité sudoers à la racine du répertoire


Figure 2. Appartenance aux groupes de sécurité spécifiés dans les objets sudoRole.

La configuration suivante se fait côté Linux.

Dans le fichier /etc/nsswitch.conf , ajoutez la ligne à la fin du fichier:

 sudoers: files sss 

Dans le fichier /etc/sssd/sssd.conf de la section [sssd] , ajoutez sudo aux services

 cat /etc/sssd/sssd.conf | grep services services = nss, pam, sudo 

Après toutes les opérations, vous devez vider le cache du démon sssd. Les mises à jour automatiques sont effectuées toutes les 6 heures, mais pourquoi devons-nous attendre autant quand nous le voulons maintenant.

 sss_cache -E 

Il arrive souvent que l'effacement du cache n'aide pas. Ensuite, nous arrêtons le service, nettoyons la base, démarrons le service.

 service sssd stop rm -rf /var/lib/sss/db/* service sssd start 

Nous nous connectons sous le premier utilisateur et vérifions qu'il est accessible depuis sous sudo:

 su user1 [user1@testsshad log]$ id uid=1109801141(user1) gid=1109800513(domain users) groups=1109800513(domain users),1109801132(admins_) [user1@testsshad log]$ sudo -l [sudo] password for user1: Matching Defaults entries for user1 on testsshad: !visiblepw, always_set_home, match_group_by_gid, always_query_group_plugin, env_reset, env_keep="COLORS DISPLAY HOSTNAME HISTSIZE KDEDIR LS_COLORS", env_keep+="MAIL PS1 PS2 QTDIR USERNAME LANG LC_ADDRESS LC_CTYPE", env_keep+="LC_COLLATE LC_IDENTIFICATION LC_MEASUREMENT LC_MESSAGES", env_keep+="LC_MONETARY LC_NAME LC_NUMERIC LC_PAPER LC_TELEPHONE", env_keep+="LC_TIME LC_ALL LANGUAGE LINGUAS _XKB_CHARSET XAUTHORITY", secure_path=/sbin\:/bin\:/usr/sbin\:/usr/bin User user1 may run the following commands on testsshad: (root) /usr/bin/ls, /usr/bin/cat 

Nous faisons de même avec notre deuxième utilisateur:

 su user2 [user2@testsshad log]$ id uid=1109801142(user2) gid=1109800513(domain users) groups=1109800513(domain users),1109801138(sudo_root) [user2@testsshad log]$ sudo -l Matching Defaults entries for user2 on testsshad: !visiblepw, always_set_home, match_group_by_gid, always_query_group_plugin, env_reset, env_keep="COLORS DISPLAY HOSTNAME HISTSIZE KDEDIR LS_COLORS", env_keep+="MAIL PS1 PS2 QTDIR USERNAME LANG LC_ADDRESS LC_CTYPE", env_keep+="LC_COLLATE LC_IDENTIFICATION LC_MEASUREMENT LC_MESSAGES", env_keep+="LC_MONETARY LC_NAME LC_NUMERIC LC_PAPER LC_TELEPHONE", env_keep+="LC_TIME LC_ALL LANGUAGE LINGUAS _XKB_CHARSET XAUTHORITY", secure_path=/sbin\:/bin\:/usr/sbin\:/usr/bin User user2 may run the following commands on testsshad: (root) ALL 

Cette approche vous permet de définir de manière centralisée les rôles sudo pour différents groupes d'utilisateurs.

Stockage et utilisation des clés ssh dans Active Directory


Avec une petite extension du schéma, il est possible de stocker les clés ssh dans les attributs utilisateur Active Directory et de les utiliser pour l'autorisation sur les hôtes Linux.

L'autorisation via sssd doit être configurée.

Ajoutez l'attribut souhaité à l'aide du script PowerShell.

AddsshPublicKeyAttribute.ps1
Fonction New-AttributeID {
$ Prefix = "1.2.840.113556.1.8000.2554"
$ GUID = [System.Guid] :: NewGuid (). ToString ()
$ Parts = @ ()
$ Parts + = [UInt64] :: Parse ($ guid.SubString (0.4), "AllowHexSpecifier")
$ Parts + = [UInt64] :: Parse ($ guid.SubString (4,4), "AllowHexSpecifier")
$ Parts + = [UInt64] :: Parse ($ guid.SubString (9,4), "AllowHexSpecifier")
$ Parts + = [UInt64] :: Parse ($ guid.SubString (14,4), "AllowHexSpecifier")
$ Parts + = [UInt64] :: Parse ($ guid.SubString (19,4), "AllowHexSpecifier")
$ Parts + = [UInt64] :: Parse ($ guid.SubString (24.6), "AllowHexSpecifier")
$ Parts + = [UInt64] :: Parse ($ guid.SubString (30.6), "AllowHexSpecifier")
$ oid = [String] :: Format ("{0}. {1}. {2}. {3}. {4}. {5}. {6}. {7}", $ prefix, $ Parts [ 0],
$ Parts [1], $ Parts [2], $ Parts [3], $ Parts [4], $ Parts [5], $ Parts [6])
$ oid
}
$ schemaPath = (Get-ADRootDSE) .schemaNamingContext
$ oid = New-AttributeID
$ attributes = @ {
lDAPDisplayName = 'sshPublicKey';
attributeId = $ oid;
oMSyntax = 22;
attributeSyntax = "2.5.5.5";
isSingleValued = $ true;
adminDescription = 'Clé publique utilisateur pour la connexion SSH';
}

New-ADObject -Name sshPublicKey -Type attributeSchema -Path $ schemapath -OtherAttributes $ attributes
$ userSchema = get-adobject -SearchBase $ schemapath -Filter 'nom -eq "utilisateur"'
$ userSchema | Set-ADObject -Add @ {mayContain = 'sshPublicKey'}

Après avoir ajouté l'attribut, redémarrez les services de domaine Active Directory.
Nous passons aux utilisateurs d'Active Directory. D'une manière qui vous convient, nous générons une paire de clés pour la connexion ssh.

Lancez PuttyGen, cliquez sur le bouton "Générer" et cliquez frénétiquement sur la souris dans une zone vide.

À la fin du processus, nous pouvons enregistrer les clés publiques et privées, remplir la clé publique dans l'attribut utilisateur Active Directory et profiter du processus. Cependant, la clé publique doit être utilisée à partir de la fenêtre " Clé publique à coller dans le fichier OpenSSH authorized_keys: ".



Ajoutez la clé à l'attribut utilisateur.

Option 1 - GUI:



Option 2 - PowerShell:

get-aduser user1 | set-aduser -add @{sshPublicKey = 'AAAAB...XAVnX9ZRJJ0p/Q=='}

Donc, nous avons pour le moment: un utilisateur avec l'attribut sshPublicKey rempli, un client Putty configuré pour l'autorisation de clé. Il reste un petit point, comment faire en sorte que le démon sshd extrait la clé publique dont nous avons besoin des attributs utilisateur. Un petit script trouvé sur les espaces ouverts de l'Internet bourgeois y parvient.

 cat /usr/local/bin/fetchSSHKeysFromLDAP #!/bin/sh ldapsearch -h testmdt.testopf.local -xb "dc=testopf,dc=local" '(sAMAccountName='"${1%@*}"')' -D Administrator@testopf.local -w superSecretPassword 'sshPublicKey' | sed -n '/^ /{H;d};/sshPublicKey:/x;$g;s/\n *//g;s/sshPublicKey: //gp' 

Nous avons défini 0500 autorisations pour root dessus.

 chmod 0500 /usr/local/bin/fetchSSHKeysFromLDAP 

Dans cet exemple, le compte administrateur est utilisé pour la liaison au répertoire. Dans les conditions de combat, il devrait y avoir un compte séparé avec un ensemble minimum de droits.

Personnellement, j'ai été très confus par le moment du mot de passe dans sa forme pure dans le script, malgré les droits énoncés.

Option de solution:

  • J'enregistre le mot de passe dans un fichier séparé:

     echo -n Supersecretpassword > /usr/local/etc/secretpass 
  • J'ai défini les autorisations sur le fichier 0500 pour root

     chmod 0500 /usr/local/etc/secretpass 
  • Je change les paramètres de démarrage de ldapsearch: le paramètre -w superSecretPassword est changé en -y / usr / local / etc / secretpass

L'accord final dans la suite d'aujourd'hui est l'édition de sshd_config

 cat /etc/ssh/sshd_config | egrep -v -E "#|^$" | grep -E "AuthorizedKeysCommand|PubkeyAuthe" PubkeyAuthentication yes AuthorizedKeysCommand /usr/local/bin/fetchSSHKeysFromLDAP AuthorizedKeysCommandUser root 

Par conséquent, nous obtenons la séquence suivante avec l'authentification par clé configurée dans le client ssh:

  1. L'utilisateur se connecte au serveur en indiquant son nom d'utilisateur.
  2. Le démon sshd, via un script, extrait la valeur de la clé publique de l'attribut utilisateur dans Active Directory et autorise les clés.
  3. Le démon sssd authentifie davantage l'utilisateur en fonction de l'appartenance au groupe. Attention! Si ce n'est pas configuré, tout utilisateur de domaine aura accès à l'hôte.
  4. Lorsque sudo essaie, le démon sssd recherche dans l'annuaire Active Directory les rôles. S'il existe des rôles, les attributs et l'appartenance utilisateur du groupe sont vérifiés (si sudoRoles est configuré pour utiliser des groupes d'utilisateurs)

Résumé


Ainsi, les clés sont stockées dans les attributs utilisateur Active Directory, les autorisations sudo - de même, l'accès aux hôtes Linux par les comptes de domaine s'effectue en vérifiant l'appartenance au groupe Active Directory.

La dernière vague de la baguette du chef d'orchestre - et la salle se fige dans un silence impressionné.

Ressources utilisées par écrit:

Source: https://habr.com/ru/post/fr449702/


All Articles