NetBSD Security Advisory 2023-006: KDC-spoofing in pam_krb5
29 June, 2023 by security-officer@netbsd.org | netbsd
-----BEGIN PGP SIGNED MESSAGE----- Hash: SHA256 NetBSD Security Advisory 2023-006 ================================= Topic: KDC-spoofing in pam_krb5 Version: NetBSD-current: affected prior to 2023-06-20 NetBSD 10.0_BETA: affected prior to 2023-06-21 NetBSD 9.3: affected NetBSD 9.2: affected NetBSD 9.1: affected NetBSD 9.0: affected NetBSD 8.2: affected NetBSD 8.1: affected NetBSD 8.0: affected Severity: Remote attacker may be able to log in as any user Fixed: NetBSD-current: 2023-06-20 NetBSD-10 branch: 2023-06-21 NetBSD-9 branch: 2023-06-21 NetBSD-8 branch: 2023-06-21 Please note that NetBSD releases prior to 8.2 are no longer supported. It is recommended that all users upgrade to a supported release. Abstract ======== On a NetBSD system with: - - ftpd, sshd, or some other network services enabled with default configuration, and - - /etc/krb5.conf created (possibly an empty file), an adversary on the network can log in as any user via pam_krb5 by spoofing a Kerberos KDC (Key Distribution Center) on the network, bypassing Kerberos's normal cryptographic verification methods. NetBSD installations without /etc/krb5.conf (the default) are not affected. This vulnerability has been assigned CVE-2023-3326. Technical Details ================= Normally, Kerberos works like this: 1. An organization is named by a realm like EXAMPLE.COM and has a server called a KDC storing secrets shared with all users and services in the organization. 2. Each user and service is identified by a `principal name' like user@EXAMPLE.COM or imap/mail.example.com@EXAMPLE.COM. 3. Each principal (user or service) has a secret shared with the KDC: . passwords, for users; . random keys, for services, stored in a file called a `keytab' with the service. 4. To log in as a user, you run `kinit user@EXAMPLE.COM' and enter your password. kinit(1) talks to the KDC to get a `ticket-granting ticket' (tgt) which is typically good for 10h or 24h, so you only have to do this once per day to get access to any services as a single-sign-on (SSO) system. In this process, the KDC and kinit(1) use your password in a cryptographic protocol to authenticate one another -- if you enter the wrong password, or if the KDC is actually spoofed and doesn't know your password, kinit(1) fails to obtain a tgt. 5. To use a service like IMAP at mail.example.com: (a) your mail reader requests a service ticket for imap/mail.example.com@EXAMPLE.COM from the KDC using the tgt, (b) your mail reader sends the service ticket to mail.example.com, (c) mail.example.com uses its keytab to verify the service ticket came from the legitimate KDC before letting you read your mail. pam_krb5 is an authentication module that verifies a password on behalf of login programs like sshd and xdm. It works by effectively running kinit(1) with the password, and getting a tgt from the KDC, as a way to verify the password. - - For local logins, like xdm, pam_krb5 incorporates the single-sign-on aspect of Kerberos into the local login prompt, so users can proceed to use the tickets obtained by pam_krb5 for applications in their login session. - - For logins from remote users, like sshd, pam_krb5 serves as a fallback for users who are familiar with passwords, but are unfamiliar with Kerberos or the normal kinit(1) path. (Note: pam_krb5 is not for normal Kerberos authentication in sshd -- for that, you must set `GSSAPIAuthentication yes' in /etc/ssh/sshd_config.) If there is a keytab, pam_krb5 also uses the tgt to get a service ticket and verifies the service ticket with the keytab. But without a keytab, the only way pam_krb5 can verify the KDC's response and get a tgt is with the password, and yet pam_krb5's job is to verify the password with a tgt. If both the password _and_ the KDC are controlled by an adversary, the adversary can provide a password that the adversary's spoofed KDC will return a valid tgt for. Currently, without a keytab, pam_krb5 is vulnerable to this attack. pam_krb5 is not necessary for you to use Kerberos just for client-side SSO, but to use that, you need to create an /etc/krb5.conf (which may be empty) before kinit(1) and any kerberized client software like Thunderbird or Firefox will use Kerberos. Creating /etc/krb5.conf -- even an empty file -- has the side effect of enabling pam_krb5, which is on by default in /etc/pam.d for system, ftpd, display_manager, and sshd. Even if /etc/krb5.conf is empty and doesn't specify a default realm or KDC, pam_krb5 will attempt to discover the realm and KDC by DNS TXT and SRV records based on the local hostname. All of these can be forged by an adversary on the network. Alternatively, for client-side SSO, you use ~/.krb5/config, or create a different file and set the environment variable KRB5_CONFIG to point to it in any processes like kinit(1) and client programs that use Kerberos. This approach does not enable pam_krb5. Solutions and Workarounds ========================= Any one of the following steps will prevent the attack: - - If you are not using Kerberos at all: Ensure you have no /etc/krb5.conf. - - If you are using Kerberos for client-side SSO, as in kinit/klist for login to remote hosts, but not to authenticate users logging in with sshd, xdm, etc.: Either: . Comment out the `pam_krb5.so' lines in /etc/pam.d. . Delete /etc/krb5.conf and use ~/.krb5/config instead. - - If you want to use Kerberos for authenticating users logging in: Obtain a keytab for your host from your Kerberos administrator. (For sshd, you should generally use `GSSAPIAuthentication yes' in /etc/ssh/sshd_config to get native Kerberos authentication, not pam_krb5, which is a form of password authentication that just uses Kerberos to check a password.) If you want to use Kerberos for authenticating users logging in with passwords, and you do not have a keytab from your Kerberos administrator: This use-case is inherently vulnerable to the attack, and you must rely on physical security or a closed network to prevent it. Once you update NetBSD, you must enable the new `allow_kdc_spoof' option on any pam_krb5.so lines in /etc/pam.d for this to continue to function. To apply a fixed version from a releng build, fetch a fitting base.tar.xz (or base.tgz on older architectures) from nycdn.NetBSD.org and extract the fixed binaries: cd /var/tmp ftp https://nycdn.NetBSD.org/pub/NetBSD-daily/REL/BUILD/ARCH/binary/sets/base.tar.xz cd / tar xzpf /var/tmp/base.tar.xz ./usr/lib/security/pam_krb5.so.4 with the following replacements: REL = the release version you are using BUILD = the source date of the build. 20230621* and later will fit ARCH = your system's architecture The following instructions describe how to upgrade your pam_krb5 binaries by updating your source tree and rebuilding and installing a new version of pam_krb5: * NetBSD-current: Systems running NetBSD-current dated from before 2023-06-20 should be upgraded to NetBSD-current dated 2023-06-21 or later. The following files/directories need to be updated from the netbsd-current CVS branch (aka HEAD): lib/libpam/modules/pam_krb5 To update from CVS, re-build, and re-install pam_krb5: # cd src # cvs update -d -P lib/libpam/modules/pam_krb5 # cd lib/libpam/modules/pam_krb5 # make USETOOLS=no cleandir dependall # make USETOOLS=no install * NetBSD 10.*: Systems running NetBSD 10.* sources dated from before 2023-06-21 should be upgraded from NetBSD 10.* sources dated 2023-06-22 or later. The following files/directories need to be updated from the netbsd-10 branch: lib/libpam/modules/pam_krb5 To update from CVS, re-build, and re-install pam_krb5: # cd src # cvs update -r netbsd-10 -d -P lib/libpam/modules/pam_krb5 # cd lib/libpam/modules/pam_krb5 # make USETOOLS=no cleandir dependall # make USETOOLS=no install * NetBSD 9.*: Systems running NetBSD 9.* sources dated from before 2023-06-21 should be upgraded from NetBSD 9.* sources dated 2023-06-22 or later. The following files/directories need to be updated from the netbsd-9 branch: lib/libpam/modules/pam_krb5 To update from CVS, re-build, and re-install pam_krb5: # cd src # cvs update -r netbsd-9 -d -P lib/libpam/modules/pam_krb5 # cd lib/libpam/modules/pam_krb5 # make USETOOLS=no cleandir dependall # make USETOOLS=no install * NetBSD 8.*: Systems running NetBSD 8.* sources dated from before 2023-06-21 should be upgraded from NetBSD 8.* sources dated 2023-06-22 or later. The following files/directories need to be updated from the netbsd-8 branch: lib/libpam/modules/pam_krb5 To update from CVS, re-build, and re-install pam_krb5: # cd src # cvs update -r netbsd-8 -d -P lib/libpam/modules/pam_krb5 # cd lib/libpam/modules/pam_krb5 # make USETOOLS=no cleandir dependall # make USETOOLS=no install Thanks To ========= Taylor R. Campbell for finding and fixing the issue. Revision History ================ 2023-06-28 Initial release More Information ================ Advisories may be updated as new information becomes available. The most recent version of this advisory (PGP signed) can be found at https://cdn.NetBSD.org/pub/NetBSD/security/advisories/NetBSD-SA2023-NNN.txt.asc Information about NetBSD and NetBSD security can be found at https://www.NetBSD.org/ https://www.NetBSD.org/Security/ Copyright 2023, The NetBSD Foundation, Inc. All Rights Reserved. Redistribution permitted only in full, unmodified form. $NetBSD: NetBSD-SA2023-006.txt,v 1.1 2023/06/28 15:33:55 christos Exp $ -----BEGIN PGP SIGNATURE----- iQJQBAEBCAA6FiEEJxEzJivzXLUNT1BGiSYeF/XvSf8FAmScUuUcHHNlY3VyaXR5 LW9mZmljZXJAbmV0YnNkLm9yZwAKCRCJJh4X9e9J/6ltD/4nED/6kgoALRhLoKY0 82Z9wyG1Pf9mE9K8GzqYWjZe3OZnPfmngFebPIdVL0zNufw+SGKK8ADmDaiYN82V LI8/AvvzsBiG0DL4TA4Uik6VHMlRsLfDXAnjaGiLMFpIVVsFzIqtSWJDcJhP+Nrx bSlVD0xEPyCdV39wE+R27aEq0AlIqFwagxBjMGmeY81+P+yHh2YBqfhDkUe62cDY 7lR3Nz5rEgpRUQBVXGZjx84pA9a1EHXt8JJ9tP1YAoslEAnPpBSo08/qzqDA/D2n lXX2+dyKFmPIV4lN1vSRRhOl5Sz/alU6/+/m9Fg1jxNQZFzYa7tfWrwEX642yfeq CbzukCbu10jzNh6yg+DhhS4e/KzmCU46wTZhQksC5ScUrjREGmss4hBqQnhUpqes 9ownElapJ7hDvAgL0t/AZ8m5jxaBI8WBTjwKTQzQ/7Oc5NUnpmJwbmFQF60Gq9SY UVPyGeeX8A9BmajSQcd4Ej+kXcrLclQsIS8VH2r64vVz5kz13AaJzHLAMdCFQn+S pUwZHqdVk4C+JVTRYVmED0/K2bko5KdnSi5vu/QGozER9BHtyxMt66Lfqsgv+lMg EiSlHzgOcVWtVzaCkIBzuxbuJ5Kf6IW7SsW7FPJ7HXlJ5ldXVS/a/wYC9/rbYoiJ NTB+ZeMxjKObDrK45AuM5qqGQg== =pZak -----END PGP SIGNATURE-----