Since 5d51ae5, principal keys were dropped in case user auth indicator
was not including password. Thereafter, the key removal behavior was
removed by 15ff9c8 in the context of the kdcpolicy plugin introduction.
Support for hardened pre-auth methods (FAST and SPAKE) was added in
d057040, and the removal of principal keys was restored afterwards by
f0d12b7, but not taking the new hardened auth indicator into account.
Fixes: https://pagure.io/freeipa/issue/9065
Related to: https://pagure.io/freeipa/issue/8001
Signed-off-by: Julien Rische <jrische@redhat.com>
Reviewed-By: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-By: Francisco Trivino <ftrivino@redhat.com>
MIT Kerberos 1.20 changes DAL interface around PAC record issuance:
sign_authdata callback is removed and replaced with issue_pac one.
The signatures are different and logic changed as well.
Prepare for KDB version 9 by moving PAC implementation into separate
source files. ipa_kdb_mspac.c is left with most of the common code.
FreeIPA supports sign_authdata callback since KDB version 6, move current
implementation to ipa_kdb_mspac_v6.c.
KDB version 8 actually changed sign_authdata interface and we accounted
to that in ipa_kdb.c with a stub that re-uses v6 version. Keep it as it
is right now.
Finally, add KDB version 9 stub files. Compiling against MIT Kerberos
1.20 does not work yet, thus explicit #error message in ipa_kdb.c. This
will be worked on later.
Related: https://pagure.io/freeipa/issue/9083
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-By: Rob Crittenden <rcritten@redhat.com>
New versions of MS-KILE and MS-SFU after Windows Server November 2021
security updates add PAC_REQUESTER_SID buffer check behavior:
- PAC_REQUESTER_SID should only be added for TGT requests
- if PAC_REQUESTER_SID is present, KDC must verify that the cname on
the ticket resolves to the account with the same SID as the
PAC_REQUESTER_SID. If it doesn't KDC must respond with
KDC_ERR_TKT_REVOKED
Change requester SID check to skip exact check for non-local
PAC_REQUESTER_SID but harden to ensure it comes from the trusted domains
we know about.
If requester SID is the same as in PAC, we already do cname vs PAC SID
verification.
With these changes FreeIPA works against Windows Server 2019 with
November 2021 security fixes in cross-realm S4U2Self operations.
Fixes: https://pagure.io/freeipa/issue/9031
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-By: Rob Crittenden <rcritten@redhat.com>
MS-KILE 3.3.5.6.4.8 in revision after Windows Server November 2021
security fixes added the following requirement:
- PAC_REQUESTER_SID is only added in TGT case (including referrals and
tickets to RODCs)
Fixes: https://pagure.io/freeipa/issue/9031
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-By: Rob Crittenden <rcritten@redhat.com>
Previously, ipadb_check_logon_info() was called only for cross-realm
case. Now we call it for both in-realm and cross-realm cases. In case of
the S4U2Proxy, we would be passed a PAC of the original caller which
might be a principal from the trusted realm. We cannot validate that PAC
against our local client DB entry because this is the proxy entry which
is guaranteed to have different SID.
In such case, validate the SID of the domain in PAC against our realm
and any trusted doman but skip an additional check of the DB entry in
the S4U2Proxy case.
Related: https://pagure.io/freeipa/issue/9031
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-By: Rob Crittenden <rcritten@redhat.com>
If the SID was explicitly set for the host or service entry, honor it
when issuing PAC. For normal services and hosts we don't allocate
individual SIDs but for cifs/... principals on domain members we do as
they need to login to Samba domain controller.
Related: https://pagure.io/freeipa/issue/9031
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-By: Rob Crittenden <rcritten@redhat.com>
As part of CVE-2020-25717 mitigations, Samba expects correct user
account flags in the PAC. This means for services and host principals we
should be using ACB_WSTRUST or ACB_SVRTRUST depending on whether they
run on IPA clients ("workstation" or "domain member") or IPA servers
("domain controller").
Fixes: https://pagure.io/freeipa/issue/9031
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-By: Rob Crittenden <rcritten@redhat.com>
PAC_ATTRIBUTES_INFO PAC buffer allows both client and KDC to tell
whether a PAC structure was requested by the client or it was provided
by the KDC implicitly. Kerberos service then can continue processing or
deny access in case client explicitly requested to operate without PAC.
Fixes: https://pagure.io/freeipa/issue/9031
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Signed-off-by: Andrew Bartlett <abartlet@samba.org>
Reviewed-By: Rob Crittenden <rcritten@redhat.com>
CVE-2020-25721 mitigation: KDC must provide the new PAC_REQUESTER_SID
buffer with ObjectSID value associated with the requester's principal.
The mitigation only works if NDR library supports the PAC_REQUESTER_SID
buffer type. In case we cannot detect it at compile time, a warning will
be displayed at configure stage.
Fixes: https://pagure.io/freeipa/issue/9031
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-by: Rob Crittenden <rcritten@redhat.com>
Reviewed-By: Rob Crittenden <rcritten@redhat.com>
CVE-2020-25721 mitigation: KDC must provide the new HAS_SAM_NAME_AND_SID
buffer with sAMAccountName and ObjectSID values associated with the
principal.
The mitigation only works if NDR library supports the
PAC_UPN_DNS_INFO_EX buffer type. In case we cannot detect it at compile
time, a warning will be displayed at configure stage.
Fixes: https://pagure.io/freeipa/issue/9031
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-by: Rob Crittenden <rcritten@redhat.com>
Reviewed-By: Rob Crittenden <rcritten@redhat.com>
When working with aliased entries, we need a reliable way to detect
whether two principals reference the same database entry. This is
important in S4U checks.
Ideally, we should be using SIDs for these checks as S4U requires PAC
record presence which cannot be issued without a SID associated with an
entry. This is true for user principals and a number of host/service
principals associated with Samba. Other service principals do not have
SIDs because we do not allocate POSIX IDs to them in FreeIPA. When PAC
is issued for these principals, they get SID of a domain computer or
domain controller depending on their placement (IPA client or IPA
server).
Since 389-ds always returns unique entry DN for the same entry, rely on
this value instead. We could have used ipaUniqueID but for Kerberos
principals created through the KDB (kadmin/kdb5_util) we don't have
ipaUniqueID in the entry.
Fixes: https://pagure.io/freeipa/issue/9031
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-by: Rob Crittenden <rcritten@redhat.com>
Reviewed-By: Rob Crittenden <rcritten@redhat.com>
If the principal entry in LDAP has SID associated with it, store it to
be able to quickly assess the SID when processing PAC.
Also rename string_to_sid to IPA-specific version as it uses different
prototype than Samba version.
Fixes: https://pagure.io/freeipa/issue/9031
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-by: Andreas Schneider <asn@samba.org>
Reviewed-by: Robert Crittenden <rcritten@redhat.com>
Reviewed-By: Rob Crittenden <rcritten@redhat.com>
Add prototype to the exported function
Replace few tabs by spaces and mark static code as static.
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-By: Robbie Harwood <rharwood@redhat.com>
Reviewed-By: Rob Crittenden <rcritten@redhat.com>
On Fedora 33 GCC defaults to -Wmissing-prototypes and emits warnings
about function prototypes missing. If -Werror is specified, this breaks
compilation.
We also default to -Werror=implicit-function-declaration
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-By: Robbie Harwood <rharwood@redhat.com>
Reviewed-By: Rob Crittenden <rcritten@redhat.com>
There are few fields in KDB structures that have 'conflicting' types but
need to be compared. They come from MIT Kerberos and we have no choice
here.
In the same way, SID structures have own requirements.
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-By: Robbie Harwood <rharwood@redhat.com>
Reviewed-By: Rob Crittenden <rcritten@redhat.com>
Calling to ipadb_get_connection() will remove LDAP context if any error
happens. This means upper layers must always verify that LDAP context
exists after such calls.
ipadb_get_user_auth() may re-read global configuration and that may fail
and cause IPA context to have NULL LDAP context.
Fixes: https://pagure.io/freeipa/issue/8681
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-By: Robbie Harwood <rharwood@redhat.com>
Reviewed-By: Rob Crittenden <rcritten@redhat.com>
When MS-PAC structure is created, we get passed the time of
authentication from KDC. Use this to record logon time in MS-PAC
structure.
Set allow password change time to the last password change. We need to
refer to the actual password policy here in future.
Also use INT64_MAX to represent the resulting value for logoff
and kickoff times according to MS-PAC 2.6.
Fixes: https://pagure.io/freeipa/issue/8659
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-By: Christian Heimes <cheimes@redhat.com>
Reviewed-By: Rob Crittenden <rcritten@redhat.com>
Reviewed-By: Christian Heimes <cheimes@redhat.com>
Reviewed-By: Rob Crittenden <rcritten@redhat.com>
ipadb_get_principal() allocates client_actual. Call
ipadb_free_principal to release it.
Rather than spreading the free() amongst the code introduce
done as a target to match behavior in similar functions.
Discovered by coverity.
Signed-off-by: Rob Crittenden <rcritten@redhat.com>
Reviewed-By: Robbie Harwood <rharwood@redhat.com>
Reviewed-By: Alexander Bokovoy <abokovoy@redhat.com>
The purpose is to set a default if the RID doesn't match
expectations.
Discovered by coverity
Signed-off-by: Rob Crittenden <rcritten@redhat.com>
Reviewed-By: Robbie Harwood <rharwood@redhat.com>
Reviewed-By: Alexander Bokovoy <abokovoy@redhat.com>
In case we've got a principal name as '*', we don't need to specify
the principal itself, use pre-defined filter for a wild-card search.
Previously, we had to escape the '*' as specifying it with an explicit
matching rule would have violated RFC 4515 section 3. However, since we
don't really need to specify a different matching rule for a wild-card
search, we can remove this part completely.
Use this change as an opportunity to simplify the code and reduce
number of duplicated filter constants -- if extra filter is NULL, we can
simply pass "" and use _EXTRA filter constants to format the final
filter.
Fixes: https://pagure.io/freeipa/issue/8624
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-By: Christian Heimes <cheimes@redhat.com>
Commit 8b6d1ab854 added support for
subordinate UPN suffixes but missed the case where subordinate UPN is a
subdomain of the forest root domain and not mentioned in the UPN
suffixes list.
Correct this situation by applying the same check to the trusted domain
name as well.
Fixes: https://pagure.io/freeipa/issue/8554
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-By: Alexander Bokovoy <abokovoy@redhat.com>
We use string_to_sid() from internal Samba libraries, so we have to link
to it properly.
In addition, size_t is (long unsigned int), just cast to (int) in
asprintf.
Fixes: https://pagure.io/freeipa/issue/8585
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-By: Rob Crittenden <rcritten@redhat.com>
In file included from /usr/include/string.h:519,
from /usr/include/lber.h:30,
from /usr/include/ldap.h:30,
from ipa_kdb.h:37,
from ipa_kdb_mspac.c:26:
In function 'strncpy',
inlined from 'get_server_netbios_name' at ipa_kdb_mspac.c:2358:5,
inlined from 'ipadb_reinit_mspac' at ipa_kdb_mspac.c:2813:39:
/usr/include/bits/string_fortified.h:91:10: warning: 'strncpy' specified bound 255 equals destination size [-Wstringop-truncation]
91 | return __builtin___strncpy_chk (__dest, __src, __len, __bos (__dest));
| ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Fixes: https://pagure.io/freeipa/issue/8585
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-By: Rob Crittenden <rcritten@redhat.com>
When initializing UPN suffixes, we calculate their sizes and didn't use
the right variable to allocate their size. This affects us if there are
more than one UPN suffix available for a trust due to memory corruption
while filling in sizes.
Add unit test for multiple UPN suffixes.
Fixes: https://pagure.io/freeipa/issue/8566
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-By: Rob Crittenden <rcritten@redhat.com>
Reviewed-By: Robbie Harwood <rharwood@redhat.com>
[MS-ADTS] 6.1.6.9.3.2 requires msDS-TrustForestTrustInfo attribute of
trusted domain information in Active Directory to conform certain rules.
One side-effect of those rules is that list of UPN suffixes reported
through the netr_DsRGetForestTrustInformation function is dynamically
filtered to deduplicate subordinate suffixes.
It means that if list of UPN suffixes contains the following top level
names (TLNs):
fabrikam.com
sub.fabrikam.com
then netr_DsRGetForestTrustInformation would only return 'fabrikam.com'
as the TLN, fully filtering 'sub.fabrikam.com'.
IPA KDB driver used exact comparison of the UPN suffixes so any
subordinate had to be specified exactly.
Modify logic so that if exact check does not succeed, we validate a
realm to test being a subordinate of the known UPN suffixes. The
subordinate check is done by making sure UPN suffix is at the end of the
test realm and is immediately preceded with a dot.
Because the function to check suffixes potentially called for every
Kerberos principal, precalculate and cache length for each UPN suffix at
the time we retrieve the list of them.
Fixes: https://pagure.io/freeipa/issue/8554
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-By: Rob Crittenden <rcritten@redhat.com>
Reviewed-By: Robbie Harwood <rharwood@redhat.com>
ipa_gethostfqdn() now returns a pointer to a statically allocated buffer
or NULL in case of an error. The caller no longer has to supply a
correctly allocated buffer.
Rename IPA_HOST_HOST to_LEN IPA_HOST_FQDN_LEN and use IPA_HOST_FQDN_LEN
wherever code copies a hostname supplied from ipa_gethostfqdn().
Clarify that MAXHOSTNAMELEN and MAXHOSTFQDNLEN are different things.
Signed-off-by: Christian Heimes <cheimes@redhat.com>
Reviewed-By: Fraser Tweedale <ftweedal@redhat.com>
ipa_kdb and ipa-join now use ipa_gethostfqdn() instead of uname()'s nodename.
The code for hostname in ipa-join is simplified. Now the hostname is
auto-detected and verified in main(). All sub functions can now use the
hostname without additional checks. This removes a bunch of strdup(),
NULL checks, and free() calls.
Fixes: https://pagure.io/freeipa/issue/8501
Signed-off-by: Christian Heimes <cheimes@redhat.com>
Reviewed-By: Fraser Tweedale <ftweedal@redhat.com>
kadmin.local getprincs command results in passing '*' as a principal to
KDB driver function that looks up the principals.
The whole filter looks like this
(&(|
(objectclass=krbprincipalaux)
(objectclass=krbprincipal)
(objectclass=ipakrbprincipal))
(|(ipakrbprincipalalias=*)
(krbprincipalname:caseIgnoreIA5Match:=*)))
There are two parts of the LDAP filter we use to look up principals, the
part with 'krbprincipalname' uses extensible filter syntax of RFC 4515
section 3:
extensible = ( attr [dnattrs]
[matchingrule] COLON EQUALS assertionvalue )
/ ( [dnattrs]
matchingrule COLON EQUALS assertionvalue )
In case we've got a principal name as '*' we have to follow RFC 4515
section 3 and reencode it using <valueencoding> rule from RFC 4511
section 4.1.6 but only to the part of the filter that does use assertion
value.
Fixes: https://pagure.io/freeipa/issue/8490
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-By: Rob Crittenden <rcritten@redhat.com>
Restructure logic of ipadb_get_principal() to separate retrieval of a
principal by a name and by an alias. Separate enterprise principal name
type processing into a helper function to be able to reuse it for own
aliases.
Unify code in client referrals part to do the same and use krb5 API to
deal with principals rather than parsing strings. The end result is the
same but we follow common rules in MIT Kerberos to process principals.
An enterprise principal is typically "name@SOMEREALM@REALM", but any
principal might be parsed as enterprise principal, so we could get
"name@REALM" marked as such. When unparsing the enterprise principal,
re-parse it again with default realm values, to get our realm
normalization.
This behavior would fix situations when GSSAPI calls are operating on a
non-qualified principal name that was imported as a
GSS_KRB5_NT_ENTERPRISE_NAME when calling gss_import_name().
Related: https://pagure.io/freeipa/issue/8319
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Signed-off-by: Isaac Boukris <iboukris@redhat.com>
Reviewed-By: Isaac Boukris <iboukris@redhat.com>
Reviewed-By: Florence Blanc-Renaud <flo@redhat.com>
For Kerberos principal lookup we always need to check whether principal
is from our realm. Keep the reference to our realm TGS handy to avoid
memory allocations on every lookup.
Related: https://pagure.io/freeipa/issue/8319
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-By: Isaac Boukris <iboukris@redhat.com>
Reviewed-By: Florence Blanc-Renaud <flo@redhat.com>
Previously, FreeIPA only allowed to issue PAC record in a ticket
for the following principal types:
- for IPA users
- for a host principal of one of IPA masters
- for a cifs/ or HTTP/ service on one of IPA masters
To allow S4U2Self operations over trust to AD, an impersonating service
must have PAC record in its TGT to be able to ask AD DCs for a S4U2Self
ticket. It means any IPA service performing S4U2Self would need to have
PAC record and the constraints above prevent it from doing so.
However, depending on whether the service or host principal belongs to
one of IPA masters, we need to set proper primary RID to 516 (domain
controllers) or 515 (domain computers).
Fixes: https://pagure.io/freeipa/issue/8319
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-By: Isaac Boukris <iboukris@redhat.com>
Reviewed-By: Florence Blanc-Renaud <flo@redhat.com>
Depending on whether identity of a principal was asserted by the KDC or
by a service doing protocol transition (S4U2Self), AD DCs add a
special extra SID to a PAC record:
- S-1-18-1 is a SID for an Authentication Authority Asserted Identity
- S-1-18-2 is a SID for a Service Asserted Identity
This behavior is governed by [MS-SFU] 3.2.5.1.2 "KDC replies with Service
Ticket".
In order to add an asserted identity SID, we need to pass down the
client flags as set by the KDC and check for a protocol transition bit.
Fixes: https://pagure.io/freeipa/issue/8319
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-By: Isaac Boukris <iboukris@redhat.com>
Reviewed-By: Florence Blanc-Renaud <flo@redhat.com>
Implement minimal server referrals support for enterprise principals as
defined in RFC 6806.
Use krb5_pac_verify_ext() and krb5_pac_sign_ext() to support cross-realm
S4U extensions. We have to verify/sign PAC and take the realm into
account for S4U in these cases.
The use of extended functions require krb5 1.17+.
For PAC verification, we have to filter existing PAC CLIENT-INFO
structure in cross-realm S4U case because otherwise old CLIENT-INFO
would change the PAC principal due to adding or ommiting the realm in
transition. Since a new PAC CLIENT-INFO will be provided by
k5_insert_client_info() anyway, we can filter it in all cases.
Generate PAC only for the first S4U2Self request to the client realm
(client != NULL). Otherwise, use the PAC from the cross-realm ticket.
The latter PAC belongs to the impersonated user.
Foreign (inner) principal look up in non-AS request returns
KRB5_KDB_NOENTRY.
Finally, in PAC signing we have to take the realm into account as well
for S4U2Self cross-realm operation. This does not work when compiling
against krb5 1.17 at the moment because sign_authdata() callback does
not know whether we are dealing with an issuing referral or not. In 1.18
a KDC will set a special client flag to signify this when asking KDB
driver to sign a PAC record.
Fixes: https://pagure.io/freeipa/issue/8319
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Signed-off-by: Isaac Boukris <iboukris@redhat.com>
Reviewed-By: Isaac Boukris <iboukris@redhat.com>
Reviewed-By: Florence Blanc-Renaud <flo@redhat.com>
Helper utility to investigate PAC content of users in trusted
environments. Supports direct ticket acquisition and S4U2Self protocol
transition.
1. Direct ticket acquisition
In direct ticket acquisition mode the utility first does one of the
following actions:
- obtain a TGT ticket for a user principal using supplied password
- import existing TGT from a default credentials cache
Once a user TGT is available, the utility will attempt to acquire a service
ticket to a service which key is specified in a keytab (default or
passed with --keytab option) and simulate establishing context to the
service application.
If establishing context succeeds, MS-PAC content of the service ticket
will be printed out.
2. S4U2Self protocol transition
In protocol transition case a service application obtains own TGT using
a key from the keytab and then requests a service ticket to itself in
the name of the user principal, performing S4U2Self request.
If accepting this service ticket succeeds, MS-PAC content of the service
ticket will be printed out.
If KDC does not support or rejects issuing MS-PAC record for a user, an
error message 'KDC has no support for padata type' will be printed.
Related: https://pagure.io/freeipa/issue/8319
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Signed-off-by: Isaac Boukris <iboukris@redhat.com>
Reviewed-By: Isaac Boukris <iboukris@redhat.com>
Reviewed-By: Florence Blanc-Renaud <flo@redhat.com>
UPN_DNS_INFO structure contains the client's user principal name (UPN)
and a fully qualified domain name. It is used to provide the UPN and the
FQDN that corresponds to the client of the ticket.
The structure is defined in MS-PAC section 2.10. MS-KILE specification
says in the section 3.3.5.6.4.5 that KDCs should return this buffer. It
further clarifies in section 3.3.5.2 that if the user account object has no
userPrincipalName attribute, UPN_DNS_INFO should be constructed by
concatenating user name, the "@" symbol, and the DNS name of the domain.
IPA users don't really have userPrincipalName attribute. Instead, we
always construct their account names in LOGON Info3 structure by
unparsing the canonical principal name without realm, meaning that user
principal can be recovered by concatenating the account name and the
realm (domain).
Unless the account name and unparsed client principal name are different
or the primary Info3 gid (group RID) is the one for machine accounts,
mark the UPN as constructed.
Related: https://pagure.io/freeipa/issue/8319
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-By: Isaac Boukris <iboukris@redhat.com>
Reviewed-By: Florence Blanc-Renaud <flo@redhat.com>
BER structure representing a string might not have termination '\0'
character, thus we should use length-bound functions to operate on it.
Memory handling of LDAP values was leaving previous vals over iteration.
Also, when freeing vals, we need to explicitly set it to NULL.
Fixes: https://pagure.io/freeipa/issue/8291
Signed-off-by: Alexander Bokovoy <abokovoy@redhat.com>
Reviewed-by: Simo Sorce <ssorce@redhat.com>
Reviewed-By: Christian Heimes <cheimes@redhat.com>
Reviewed-By: Simo Sorce <ssorce@redhat.com>