Skip Menu |
 

Date: Fri, 21 Mar 2008 14:28:35 -0400 (EDT)
From: Nik Conwell <nik@bu.edu>
To: krb5-bugs@mit.edu
Subject: Non-unique microseconds in TGS_REQ authenticator causing KRB5KRB_AP_ERR_REPEAT Request is a replay
Download (untitled) / with headers
text/plain 1.2KiB

I have a short running yet frequently run app that gets a TGT with a
keytab and then does a TGS request. From time to time the TGS_REQ is
denied with KRB5KRB_AP_ERR_REPEAT "Request is a replay".

Turns out that as part of the TGT request, get_in_tkt.c
verify_as_reply() calls krb5_set_real_time() to account for the time
offset between client and server. Since only seconds come from the
server it is called with microseconds of 0 which effectively sets the
microseconds in the client to 0. (Effectively since these values are
offsets that the client library applies to the real system time.)

Since the app code between the AS_REQ and TGS_REQ is the same from
invocation to invocation, the time between them is often the same, and
so if there are multiple invocations in the same second (frequently
run app), the time in the authenticator (seconds and microseconds) is
occasionally the same, running afoul of the replay detection on the
KDC.

As a workaround, the krb5.conf can have:

[libdefaults]
kdc_timesync = 0

but that disables all time synchronization which is not desirable.

Attached are 2 patches. One to leave the microseconds unchanged, and one
debugging hack to see the time values in the authenticator.

-nik

Nik Conwell
nik@bu.edu
Boston University Information Technology

Message body is not shown because sender requested not to inline it.

Message body is not shown because sender requested not to inline it.

Date: Tue, 25 Mar 2008 14:41:46 -0400 (EDT)
From: Nik Conwell <nik@bu.edu>
To: krb5 <rt@krbdev.mit.edu>
Subject: [krbdev.mit.edu #5924] Non-unique microseconds in TGS_REQ authenticator causing KRB5KRB_AP_ERR_REPEAT Request is a replay
RT-Send-Cc:
Download (untitled) / with headers
text/plain 1.5KiB

[Looks like the RT gateway sent only the last attachment to the list and not the
first (interesting one) and the actual message. All the info is in the ticket;
I thought I'd send this to the list for reference.]

I have a short running yet frequently run app that gets a TGT with a
keytab and then does a TGS request. From time to time the TGS_REQ is
denied with KRB5KRB_AP_ERR_REPEAT "Request is a replay".

Turns out that as part of the TGT request, get_in_tkt.c
verify_as_reply() calls krb5_set_real_time() to account for the time
offset between client and server. Since only seconds come from the
server it is called with microseconds of 0 which effectively sets the
microseconds in the client to 0. (Effectively since these values are
offsets that the client library applies to the real system time.)

Since the app code between the AS_REQ and TGS_REQ is the same from
invocation to invocation, the time between them is often the same, and
so if there are multiple invocations in the same second (frequently
run app), the time in the authenticator (seconds and microseconds) is
occasionally the same, running afoul of the replay detection on the
KDC.

As a workaround, the krb5.conf can have:

[libdefaults]
kdc_timesync = 0

but that disables all time synchronization which is not desirable.

Attached are 2 patches. One to leave the microseconds unchanged, and one
debugging hack to see the time values in the authenticator.

[Patches are in the RT ticket krbdev.mit.edu #5924.]

-nik
Nik Conwell
nik@bu.edu
Boston University Information Technology
[nik@bu.edu - Tue Mar 25 14:41:49 2008]:

Show quoted text
> Attached are 2 patches. One to leave the microseconds unchanged, and
> one
> debugging hack to see the time values in the authenticator.
>

I have reviewed these patches and believe that the patch to leave the
microseconds unchanged is correct and should be applied to the tree.
Attached is a revised patch that I believe is more readable but is
logically equivalent.
Download rt5924.patch
application/octet-stream 1.3KiB

Message body not shown because it is not plain text.

From: jaltman@mit.edu
Subject: SVN Commit
Download (untitled) / with headers
text/plain 1.5KiB

This patch is derived from a patch originally submitted to RT
by: Nik Conwell <nik@bu.edu>

krb5_set_real_time() accepts as input the time of the KDC
or an application server as a combination of seconds and
microseconds. Often it is the case that the time source
does not provide the real time with less than one second
granularity. Up until this patch such a caller would fill
in the microseconds parameter as zero. krb5_set_real_time()
would treat the zero microseconds as the actual reported
time and compute a microsecond based offset.

During a one second window subsequent calls to
krb5_set_real_time() would have an ever increasing offset
size until the number of seconds is incremented. This
in turn produces a side effect in which the microseconds
value of the local clock is effectively erased.

If there are multiple processes or threads on the same
machine each requesting service tickets using the same
client principal for the same service principal where
the number of seconds reported by the KDC are equivalent,
then they will now all create authenticators with
exactly the same timestamp. As a result, the authenticating
service will detect a replay attack even though the
authenticators are actually unique. The replay cache
only maintains a tuple of client, server and timestamp.

This patch modifies the interpretation of the microseconds
parameter. If -1 is specified, the microseconds offset is
ignored.


Commit By: jaltman



Revision: 20413
Changed Files:
U trunk/src/lib/krb5/krb/get_in_tkt.c
U trunk/src/lib/krb5/os/toffset.c
From: Nik Conwell <nik@bu.edu>
To: rt-comment@krbdev.mit.edu
Subject: Re: [krbdev.mit.edu #5924] SVN Commit
Date: Thu, 19 Jun 2008 04:41:34 -0400
RT-Send-Cc:

On Jun 18, 2008, at 3:36 PM, Jeffrey Altman via RT wrote:

[...]

Show quoted text
> If there are multiple processes or threads on the same
> machine each requesting service tickets using the same
> client principal for the same service principal where

This multiple process thing is a more tricky design issue. Apparently
multiple processes on the same box can get the same time
(microseconds) and so the authenticator is not unique. I see this
from time to time. The SMP OS or the hardware could put a lock around
returning the time to ensure it's unique but evidently that is not
done... I don't think there is much K5 can do about this since the
threads can't communicate with each other. Possibly some /dev/random
could be used instead of the time. My hack was to have the app retry
whenever this error is seen.

-nik
From: tlyu@mit.edu
Subject: SVN Commit
Download (untitled) / with headers
text/plain 1.7KiB

pull up r20413 from trunk

r20413@cathode-dark-space: jaltman | 2008-06-18 15:36:49 -0400
ticket: 5924
tags: pullup

This patch is derived from a patch originally submitted to RT
by: Nik Conwell <nik@bu.edu>

krb5_set_real_time() accepts as input the time of the KDC
or an application server as a combination of seconds and
microseconds. Often it is the case that the time source
does not provide the real time with less than one second
granularity. Up until this patch such a caller would fill
in the microseconds parameter as zero. krb5_set_real_time()
would treat the zero microseconds as the actual reported
time and compute a microsecond based offset.

During a one second window subsequent calls to
krb5_set_real_time() would have an ever increasing offset
size until the number of seconds is incremented. This
in turn produces a side effect in which the microseconds
value of the local clock is effectively erased.

If there are multiple processes or threads on the same
machine each requesting service tickets using the same
client principal for the same service principal where
the number of seconds reported by the KDC are equivalent,
then they will now all create authenticators with
exactly the same timestamp. As a result, the authenticating
service will detect a replay attack even though the
authenticators are actually unique. The replay cache
only maintains a tuple of client, server and timestamp.

This patch modifies the interpretation of the microseconds
parameter. If -1 is specified, the microseconds offset is
ignored.




Commit By: tlyu



Revision: 20519
Changed Files:
_U branches/krb5-1-6/
U branches/krb5-1-6/src/lib/krb5/krb/get_in_tkt.c
U branches/krb5-1-6/src/lib/krb5/os/toffset.c