Login
[x]
Log in using an account from:
Fedora Account System
Red Hat Associate
Red Hat Customer
Or login using a Red Hat Bugzilla account
Forgot Password
Login:
Hide Forgot
Create an Account
Red Hat Bugzilla – Attachment 925060 Details for
Bug 1127992
aggressive kinit timeout causes AS_REQ resent and subsequent OTP auth failure
[?]
New
Simple Search
Advanced Search
My Links
Browse
Requests
Reports
Current State
Search
Tabular reports
Graphical reports
Duplicates
Other Reports
User Changes
Plotly Reports
Bug Status
Bug Severity
Non-Defaults
|
Product Dashboard
Help
Page Help!
Bug Writing Guidelines
What's new
Browser Support Policy
5.0.4.rh83 Release notes
FAQ
Guides index
User guide
Web Services
Contact
Legal
This site requires JavaScript to be enabled to function correctly, please enable it.
[patch]
backport of TCP timeout patch to krb5-1.11/f20.
0001-add-tcp-timeout-backport.patch (text/plain), 57.01 KB, created by
Fraser Tweedale
on 2014-08-08 04:28:13 UTC
(
hide
)
Description:
backport of TCP timeout patch to krb5-1.11/f20.
Filename:
MIME Type:
Creator:
Fraser Tweedale
Created:
2014-08-08 04:28:13 UTC
Size:
57.01 KB
patch
obsolete
>From 6d05f437279a7ae036198b76fe5afb6e660ee75e Mon Sep 17 00:00:00 2001 >From: Fraser Tweedale <ftweedal@redhat.com> >Date: Tue, 5 Aug 2014 21:48:28 -0400 >Subject: [PATCH] add tcp timeout backport > >--- > ...amically-expand-timeout-when-TCP-connects.patch | 87 +++ > krb5-1.12-Get-rid-of-cm.c-and-cm.h.patch | 632 +++++++++++++++++++++ > ...ce-log-with-a-subset-of-struct-conn_state.patch | 425 ++++++++++++++ > ...-Use-millisecond-timeouts-in-sendto_kdc.c.patch | 235 ++++++++ > krb5.spec | 15 +- > 5 files changed, 1393 insertions(+), 1 deletion(-) > create mode 100644 krb5-1.12-Dynamically-expand-timeout-when-TCP-connects.patch > create mode 100644 krb5-1.12-Get-rid-of-cm.c-and-cm.h.patch > create mode 100644 krb5-1.12-Trace-log-with-a-subset-of-struct-conn_state.patch > create mode 100644 krb5-1.12-Use-millisecond-timeouts-in-sendto_kdc.c.patch > >diff --git a/krb5-1.12-Dynamically-expand-timeout-when-TCP-connects.patch b/krb5-1.12-Dynamically-expand-timeout-when-TCP-connects.patch >new file mode 100644 >index 0000000..7391e40 >--- /dev/null >+++ b/krb5-1.12-Dynamically-expand-timeout-when-TCP-connects.patch >@@ -0,0 +1,87 @@ >+From ffed2598a86e1f92e18fee66d7480ba3c7ceeb71 Mon Sep 17 00:00:00 2001 >+From: Nathaniel McCallum <npmccallum@redhat.com> >+Date: Tue, 9 Apr 2013 13:32:20 -0400 >+Subject: [PATCH 4/4] Dynamically expand timeout when TCP connects >+ >+Wait ten seconds for a TCP connection to succeed or fail before moving >+on. During this wait time, other TCP connections will be serviced if >+we already initiated them, but no new TCP connections will be created >+and no UDP packets will be retransmitted. >+ >+[ghudson@mit.edu: minor adjustments; commit message] >+ >+ticket: 7604 (new) >+--- >+ src/lib/krb5/os/sendto_kdc.c | 28 +++++++++++++++++++++++++++- >+ 1 file changed, 27 insertions(+), 1 deletion(-) >+ >+diff --git a/src/lib/krb5/os/sendto_kdc.c b/src/lib/krb5/os/sendto_kdc.c >+index ba0de65..bd9c7c1 100644 >+--- a/src/lib/krb5/os/sendto_kdc.c >++++ b/src/lib/krb5/os/sendto_kdc.c >+@@ -109,6 +109,7 @@ struct conn_state { >+ krb5_data callback_buffer; >+ size_t server_index; >+ struct conn_state *next; >++ time_ms endtime; >+ }; >+ >+ #undef DEBUG >+@@ -1054,6 +1055,10 @@ service_tcp_fd(krb5_context context, struct conn_state *conn, >+ goto kill_conn; >+ } >+ conn->state = WRITING; >++ >++ if (get_curtime_ms(&conn->endtime) == 0) >++ conn->endtime += 10000; >++ >+ goto try_writing; >+ >+ case WRITING: >+@@ -1199,6 +1204,22 @@ service_udp_fd(krb5_context context, struct conn_state *conn, >+ return 1; >+ } >+ >++/* Return the maximum of endtime and the endtime fields of all currently active >++ * TCP connections. */ >++static time_ms >++get_endtime(time_ms endtime, struct conn_state *conns) >++{ >++ struct conn_state *state; >++ >++ for (state = conns; state != NULL; state = state->next) { >++ if (state->addr.type == SOCK_STREAM && >++ (state->state == READING || state->state == WRITING) && >++ state->endtime > endtime) >++ endtime = state->endtime; >++ } >++ return endtime; >++} >++ >+ static krb5_boolean >+ service_fds(krb5_context context, struct select_state *selstate, >+ time_ms interval, struct conn_state *conns, >+@@ -1219,7 +1240,8 @@ service_fds(krb5_context context, struct select_state *selstate, >+ >+ e = 0; >+ while (selstate->nfds > 0) { >+- e = cm_select_or_poll(selstate, endtime, seltemp, &selret); >++ e = cm_select_or_poll(selstate, get_endtime(endtime, conns), >++ seltemp, &selret); >+ if (e == EINTR) >+ continue; >+ if (e != 0) >+@@ -1286,6 +1308,10 @@ service_fds(krb5_context context, struct select_state *selstate, >+ * >+ * Note that if you try to reach two ports (e.g., both 88 and 750) on >+ * one server, it counts as two. >++ * >++ * There is one exception to the above rules. Whenever a TCP connection is >++ * established, we wait up to ten seconds for it to finish or fail before >++ * moving on. This reduces network traffic significantly in a TCP environment. >+ */ >+ >+ krb5_error_code >+-- >+1.9.3 >+ >diff --git a/krb5-1.12-Get-rid-of-cm.c-and-cm.h.patch b/krb5-1.12-Get-rid-of-cm.c-and-cm.h.patch >new file mode 100644 >index 0000000..4832e08 >--- /dev/null >+++ b/krb5-1.12-Get-rid-of-cm.c-and-cm.h.patch >@@ -0,0 +1,632 @@ >+From 40da48108ed9227d28d6f56f4684934d90d353ce Mon Sep 17 00:00:00 2001 >+From: Greg Hudson <ghudson@mit.edu> >+Date: Wed, 10 Apr 2013 18:36:08 -0400 >+Subject: [PATCH 2/4] Get rid of cm.c and cm.h >+ >+Since net-server.c now uses libverto, only sendto_kdc.c consumes cm.c. >+Move stuff out of cm.c and cm.h into sendto_kdc.c and get rid of them. >+Change the sendto_kdc callback (used by chpw.c) to receive the socket >+descriptor instead of the entire conn_state structure, and move the >+declarations into os-proto.h. struct remote_address also needs to be >+in os-proto.h so that trace.c and t_trace.c can use it. k5_curtime >+isn't needed since k5-platform.h now guarantees the presence of >+gettimeofday(). >+--- >+ src/include/cm.h | 102 --------------------------------------- >+ src/include/k5-int.h | 2 - >+ src/lib/krb5/libkrb5.exports | 1 - >+ src/lib/krb5/os/Makefile.in | 3 -- >+ src/lib/krb5/os/changepw.c | 15 +++--- >+ src/lib/krb5/os/cm.c | 98 -------------------------------------- >+ src/lib/krb5/os/deps | 20 ++------ >+ src/lib/krb5/os/os-proto.h | 13 +++++ >+ src/lib/krb5/os/sendto_kdc.c | 110 +++++++++++++++++++++++++++++++++++-------- >+ src/lib/krb5/os/t_trace.c | 2 +- >+ src/lib/krb5/os/trace.c | 2 +- >+ 11 files changed, 115 insertions(+), 253 deletions(-) >+ delete mode 100644 src/include/cm.h >+ delete mode 100644 src/lib/krb5/os/cm.c >+ >+diff --git a/src/include/cm.h b/src/include/cm.h >+deleted file mode 100644 >+index 837a549..0000000 >+--- a/src/include/cm.h >++++ /dev/null >+@@ -1,102 +0,0 @@ >+-/* -*- mode: c; c-basic-offset: 4; indent-tabs-mode: nil -*- */ >+-/* include/cm.h */ >+-/* >+- * Copyright 2002 by the Massachusetts Institute of Technology. >+- * All Rights Reserved. >+- * >+- * Export of this software from the United States of America may >+- * require a specific license from the United States Government. >+- * It is the responsibility of any person or organization contemplating >+- * export to obtain such a license before exporting. >+- * >+- * WITHIN THAT CONSTRAINT, permission to use, copy, modify, and >+- * distribute this software and its documentation for any purpose and >+- * without fee is hereby granted, provided that the above copyright >+- * notice appear in all copies and that both that copyright notice and >+- * this permission notice appear in supporting documentation, and that >+- * the name of M.I.T. not be used in advertising or publicity pertaining >+- * to distribution of the software without specific, written prior >+- * permission. Furthermore if you modify this software you must label >+- * your software as modified software and not distribute it in such a >+- * fashion that it might be confused with the original M.I.T. software. >+- * M.I.T. makes no representations about the suitability of >+- * this software for any purpose. It is provided "as is" without express >+- * or implied warranty. >+- */ >+- >+-/* >+- * Since fd_set is large on some platforms (8K on AIX 5.2), this probably >+- * shouldn't be allocated in automatic storage. Define USE_POLL and >+- * MAX_POLLFDS in the consumer of this header file to use poll state instead of >+- * select state. >+- */ >+-struct select_state { >+-#ifdef USE_POLL >+- struct pollfd fds[MAX_POLLFDS]; >+-#else >+- int max; >+- fd_set rfds, wfds, xfds; >+-#endif >+- int nfds; >+- struct timeval end_time; /* magic: tv_sec==0 => never time out */ >+-}; >+- >+- >+-/* Select state flags. */ >+-#define SSF_READ 0x01 >+-#define SSF_WRITE 0x02 >+-#define SSF_EXCEPTION 0x04 >+- >+- >+-static const char *const state_strings[] = { >+- "INITIALIZING", "CONNECTING", "WRITING", "READING", "FAILED" >+-}; >+- >+- >+-/* connection states */ >+-enum conn_states { INITIALIZING, CONNECTING, WRITING, READING, FAILED }; >+-struct incoming_krb5_message { >+- size_t bufsizebytes_read; >+- size_t bufsize; >+- char *buf; >+- char *pos; >+- unsigned char bufsizebytes[4]; >+- size_t n_left; >+-}; >+-struct remote_address { >+- int family; >+- int type; >+- socklen_t len; >+- struct sockaddr_storage saddr; >+-}; >+-struct conn_state { >+- SOCKET fd; >+- krb5_error_code err; >+- enum conn_states state; >+- unsigned int is_udp : 1; >+- int (*service)(krb5_context context, struct conn_state *, >+- struct select_state *, int); >+- struct remote_address addr; >+- struct { >+- struct { >+- sg_buf sgbuf[2]; >+- sg_buf *sgp; >+- int sg_count; >+- unsigned char msg_len_buf[4]; >+- } out; >+- struct incoming_krb5_message in; >+- } x; >+- krb5_data callback_buffer; >+- size_t server_index; >+- struct conn_state *next; >+-}; >+- >+-struct sendto_callback_info { >+- int (*pfn_callback) (struct conn_state *, void *, krb5_data *); >+- void (*pfn_cleanup) (void *, krb5_data *); >+- void *context; >+-}; >+- >+- >+-krb5_error_code krb5int_cm_call_select (const struct select_state *, >+- struct select_state *, int *); >+diff --git a/src/include/k5-int.h b/src/include/k5-int.h >+index 75e6783..335912e 100644 >+--- a/src/include/k5-int.h >++++ b/src/include/k5-int.h >+@@ -567,8 +567,6 @@ extern char *strdup (const char *); >+ >+ #include "k5-gmt_mktime.h" >+ >+-struct sendto_callback_info; >+- >+ /* libos.spec */ >+ krb5_error_code krb5_lock_file(krb5_context, int, int); >+ krb5_error_code krb5_unlock_file(krb5_context, int); >+diff --git a/src/lib/krb5/libkrb5.exports b/src/lib/krb5/libkrb5.exports >+index 078c020..2a21619 100644 >+--- a/src/lib/krb5/libkrb5.exports >++++ b/src/lib/krb5/libkrb5.exports >+@@ -607,7 +607,6 @@ krb5int_build_conf_principals >+ krb5int_cc_default >+ krb5int_cleanup_library >+ krb5int_clean_hostname >+-krb5int_cm_call_select >+ krb5int_copy_data_contents >+ krb5int_copy_data_contents_add0 >+ krb5int_find_pa_data >+diff --git a/src/lib/krb5/os/Makefile.in b/src/lib/krb5/os/Makefile.in >+index 1db7cf1..24d02dd 100644 >+--- a/src/lib/krb5/os/Makefile.in >++++ b/src/lib/krb5/os/Makefile.in >+@@ -19,7 +19,6 @@ STLIBOBJS= \ >+ def_realm.o \ >+ ccdefname.o \ >+ changepw.o \ >+- cm.o \ >+ dnsglue.o \ >+ dnssrv.o \ >+ expand_path.o \ >+@@ -64,7 +63,6 @@ OBJS= \ >+ $(OUTPRE)def_realm.$(OBJEXT) \ >+ $(OUTPRE)ccdefname.$(OBJEXT) \ >+ $(OUTPRE)changepw.$(OBJEXT) \ >+- $(OUTPRE)cm.$(OBJEXT) \ >+ $(OUTPRE)dnsglue.$(OBJEXT) \ >+ $(OUTPRE)dnssrv.$(OBJEXT) \ >+ $(OUTPRE)expand_path.$(OBJEXT) \ >+@@ -109,7 +107,6 @@ SRCS= \ >+ $(srcdir)/def_realm.c \ >+ $(srcdir)/ccdefname.c \ >+ $(srcdir)/changepw.c \ >+- $(srcdir)/cm.c \ >+ $(srcdir)/dnsglue.c \ >+ $(srcdir)/dnssrv.c \ >+ $(srcdir)/expand_path.c \ >+diff --git a/src/lib/krb5/os/changepw.c b/src/lib/krb5/os/changepw.c >+index 4ad8f32..3a49688 100644 >+--- a/src/lib/krb5/os/changepw.c >++++ b/src/lib/krb5/os/changepw.c >+@@ -34,7 +34,6 @@ >+ #include "fake-addrinfo.h" >+ #include "k5-int.h" >+ #include "os-proto.h" >+-#include "cm.h" >+ #include "../krb/auth_con.h" >+ #include "../krb/int-proto.h" >+ >+@@ -100,23 +99,21 @@ locate_kpasswd(krb5_context context, const krb5_data *realm, >+ >+ >+ static void >+-kpasswd_sendto_msg_cleanup (void* callback_context, krb5_data* message) >++kpasswd_sendto_msg_cleanup(void *data, krb5_data *message) >+ { >+- struct sendto_callback_context *ctx = callback_context; >++ struct sendto_callback_context *ctx = data; >+ >+ krb5_free_data_contents(ctx->context, message); >+ } >+ >+ >+ static int >+-kpasswd_sendto_msg_callback(struct conn_state *conn, >+- void *callback_context, >+- krb5_data *message) >++kpasswd_sendto_msg_callback(SOCKET fd, void *data, krb5_data *message) >+ { >+ krb5_error_code code = 0; >+ struct sockaddr_storage local_addr; >+ krb5_address local_kaddr; >+- struct sendto_callback_context *ctx = callback_context; >++ struct sendto_callback_context *ctx = data; >+ GETSOCKNAME_ARG3_TYPE addrlen; >+ krb5_data output; >+ >+@@ -127,7 +124,7 @@ kpasswd_sendto_msg_callback(struct conn_state *conn, >+ */ >+ addrlen = sizeof(local_addr); >+ >+- if (getsockname(conn->fd, ss2sa(&local_addr), &addrlen) < 0) { >++ if (getsockname(fd, ss2sa(&local_addr), &addrlen) < 0) { >+ code = SOCKET_ERRNO; >+ goto cleanup; >+ } >+@@ -265,7 +262,7 @@ change_set_password(krb5_context context, >+ >+ addrlen = sizeof(remote_addr); >+ >+- callback_info.context = (void*) &callback_ctx; >++ callback_info.data = &callback_ctx; >+ callback_info.pfn_callback = kpasswd_sendto_msg_callback; >+ callback_info.pfn_cleanup = kpasswd_sendto_msg_cleanup; >+ krb5_free_data_contents(callback_ctx.context, &chpw_rep); >+diff --git a/src/lib/krb5/os/cm.c b/src/lib/krb5/os/cm.c >+deleted file mode 100644 >+index a9e1eb4..0000000 >+--- a/src/lib/krb5/os/cm.c >++++ /dev/null >+@@ -1,98 +0,0 @@ >+-/* -*- mode: c; c-basic-offset: 4; indent-tabs-mode: nil -*- */ >+-/* lib/krb5/os/cm.c - Connection manager functions */ >+-/* >+- * Copyright (C) 2011 by the Massachusetts Institute of Technology. >+- * All rights reserved. >+- * >+- * Export of this software from the United States of America may >+- * require a specific license from the United States Government. >+- * It is the responsibility of any person or organization contemplating >+- * export to obtain such a license before exporting. >+- * >+- * WITHIN THAT CONSTRAINT, permission to use, copy, modify, and >+- * distribute this software and its documentation for any purpose and >+- * without fee is hereby granted, provided that the above copyright >+- * notice appear in all copies and that both that copyright notice and >+- * this permission notice appear in supporting documentation, and that >+- * the name of M.I.T. not be used in advertising or publicity pertaining >+- * to distribution of the software without specific, written prior >+- * permission. Furthermore if you modify this software you must label >+- * your software as modified software and not distribute it in such a >+- * fashion that it might be confused with the original M.I.T. software. >+- * M.I.T. makes no representations about the suitability of >+- * this software for any purpose. It is provided "as is" without express >+- * or implied warranty. >+- */ >+- >+-/* >+- * This file include krb5int_cm_call_select, which is used by >+- * lib/apputils/net-server.c and sometimes by sendto_kdc.c. >+- */ >+- >+-#include "k5-int.h" >+-#include "os-proto.h" >+-#ifdef HAVE_SYS_SELECT_H >+-#include <sys/select.h> >+-#endif >+-#ifdef _WIN32 >+-#include <sys/timeb.h> >+-#endif >+-#include "cm.h" >+- >+-int >+-k5_getcurtime(struct timeval *tvp) >+-{ >+-#ifdef _WIN32 >+- struct _timeb tb; >+- _ftime(&tb); >+- tvp->tv_sec = tb.time; >+- tvp->tv_usec = tb.millitm * 1000; >+- /* Can _ftime fail? */ >+- return 0; >+-#else >+- if (gettimeofday(tvp, 0)) >+- return errno; >+- return 0; >+-#endif >+-} >+- >+-/* >+- * Call select and return results. >+- * Input: interesting file descriptors and absolute timeout >+- * Output: select return value (-1 or num fds ready) and fd_sets >+- * Return: 0 (for i/o available or timeout) or error code. >+- */ >+-krb5_error_code >+-krb5int_cm_call_select (const struct select_state *in, >+- struct select_state *out, int *sret) >+-{ >+- struct timeval now, *timo; >+- krb5_error_code e; >+- >+- *out = *in; >+- e = k5_getcurtime(&now); >+- if (e) >+- return e; >+- if (out->end_time.tv_sec == 0) >+- timo = 0; >+- else { >+- timo = &out->end_time; >+- out->end_time.tv_sec -= now.tv_sec; >+- out->end_time.tv_usec -= now.tv_usec; >+- if (out->end_time.tv_usec < 0) { >+- out->end_time.tv_usec += 1000000; >+- out->end_time.tv_sec--; >+- } >+- if (out->end_time.tv_sec < 0) { >+- *sret = 0; >+- return 0; >+- } >+- } >+- >+- *sret = select(out->max, &out->rfds, &out->wfds, &out->xfds, timo); >+- e = SOCKET_ERRNO; >+- >+- if (*sret < 0) >+- return e; >+- return 0; >+-} >+diff --git a/src/lib/krb5/os/deps b/src/lib/krb5/os/deps >+index 10b8975..e25a396 100644 >+--- a/src/lib/krb5/os/deps >++++ b/src/lib/krb5/os/deps >+@@ -63,7 +63,7 @@ changepw.so changepw.po $(OUTPRE)changepw.$(OBJEXT): \ >+ $(BUILDTOP)/include/autoconf.h $(BUILDTOP)/include/krb5/krb5.h \ >+ $(BUILDTOP)/include/osconf.h $(BUILDTOP)/include/profile.h \ >+ $(COM_ERR_DEPS) $(srcdir)/../krb/auth_con.h $(srcdir)/../krb/int-proto.h \ >+- $(top_srcdir)/include/cm.h $(top_srcdir)/include/fake-addrinfo.h \ >++ $(top_srcdir)/include/fake-addrinfo.h \ >+ $(top_srcdir)/include/k5-buf.h $(top_srcdir)/include/k5-err.h \ >+ $(top_srcdir)/include/k5-gmt_mktime.h $(top_srcdir)/include/k5-int-pkinit.h \ >+ $(top_srcdir)/include/k5-int.h $(top_srcdir)/include/k5-platform.h \ >+@@ -73,18 +73,6 @@ changepw.so changepw.po $(OUTPRE)changepw.$(OBJEXT): \ >+ $(top_srcdir)/include/krb5/plugin.h $(top_srcdir)/include/krb5/preauth_plugin.h \ >+ $(top_srcdir)/include/port-sockets.h $(top_srcdir)/include/socket-utils.h \ >+ changepw.c os-proto.h >+-cm.so cm.po $(OUTPRE)cm.$(OBJEXT): $(BUILDTOP)/include/autoconf.h \ >+- $(BUILDTOP)/include/krb5/krb5.h $(BUILDTOP)/include/osconf.h \ >+- $(BUILDTOP)/include/profile.h $(COM_ERR_DEPS) $(top_srcdir)/include/cm.h \ >+- $(top_srcdir)/include/k5-buf.h $(top_srcdir)/include/k5-err.h \ >+- $(top_srcdir)/include/k5-gmt_mktime.h $(top_srcdir)/include/k5-int-pkinit.h \ >+- $(top_srcdir)/include/k5-int.h $(top_srcdir)/include/k5-platform.h \ >+- $(top_srcdir)/include/k5-plugin.h $(top_srcdir)/include/k5-thread.h \ >+- $(top_srcdir)/include/k5-trace.h $(top_srcdir)/include/krb5.h \ >+- $(top_srcdir)/include/krb5/authdata_plugin.h $(top_srcdir)/include/krb5/locate_plugin.h \ >+- $(top_srcdir)/include/krb5/plugin.h $(top_srcdir)/include/krb5/preauth_plugin.h \ >+- $(top_srcdir)/include/port-sockets.h $(top_srcdir)/include/socket-utils.h \ >+- cm.c os-proto.h >+ dnsglue.so dnsglue.po $(OUTPRE)dnsglue.$(OBJEXT): $(BUILDTOP)/include/autoconf.h \ >+ $(BUILDTOP)/include/krb5/krb5.h $(BUILDTOP)/include/osconf.h \ >+ $(BUILDTOP)/include/profile.h $(COM_ERR_DEPS) $(top_srcdir)/include/k5-buf.h \ >+@@ -403,7 +391,7 @@ port2ip.so port2ip.po $(OUTPRE)port2ip.$(OBJEXT): $(BUILDTOP)/include/autoconf.h >+ sendto_kdc.so sendto_kdc.po $(OUTPRE)sendto_kdc.$(OBJEXT): \ >+ $(BUILDTOP)/include/autoconf.h $(BUILDTOP)/include/krb5/krb5.h \ >+ $(BUILDTOP)/include/osconf.h $(BUILDTOP)/include/profile.h \ >+- $(COM_ERR_DEPS) $(top_srcdir)/include/cm.h $(top_srcdir)/include/fake-addrinfo.h \ >++ $(COM_ERR_DEPS) $(top_srcdir)/include/fake-addrinfo.h \ >+ $(top_srcdir)/include/k5-buf.h $(top_srcdir)/include/k5-err.h \ >+ $(top_srcdir)/include/k5-gmt_mktime.h $(top_srcdir)/include/k5-int-pkinit.h \ >+ $(top_srcdir)/include/k5-int.h $(top_srcdir)/include/k5-platform.h \ >+@@ -461,7 +449,7 @@ toffset.so toffset.po $(OUTPRE)toffset.$(OBJEXT): $(BUILDTOP)/include/autoconf.h >+ toffset.c >+ trace.so trace.po $(OUTPRE)trace.$(OBJEXT): $(BUILDTOP)/include/autoconf.h \ >+ $(BUILDTOP)/include/krb5/krb5.h $(BUILDTOP)/include/osconf.h \ >+- $(BUILDTOP)/include/profile.h $(COM_ERR_DEPS) $(top_srcdir)/include/cm.h \ >++ $(BUILDTOP)/include/profile.h $(COM_ERR_DEPS) \ >+ $(top_srcdir)/include/k5-buf.h $(top_srcdir)/include/k5-err.h \ >+ $(top_srcdir)/include/k5-gmt_mktime.h $(top_srcdir)/include/k5-int-pkinit.h \ >+ $(top_srcdir)/include/k5-int.h $(top_srcdir)/include/k5-platform.h \ >+@@ -553,7 +541,7 @@ t_std_conf.so t_std_conf.po $(OUTPRE)t_std_conf.$(OBJEXT): \ >+ os-proto.h t_std_conf.c >+ t_trace.so t_trace.po $(OUTPRE)t_trace.$(OBJEXT): $(BUILDTOP)/include/autoconf.h \ >+ $(BUILDTOP)/include/krb5/krb5.h $(BUILDTOP)/include/osconf.h \ >+- $(BUILDTOP)/include/profile.h $(COM_ERR_DEPS) $(top_srcdir)/include/cm.h \ >++ $(BUILDTOP)/include/profile.h $(COM_ERR_DEPS) \ >+ $(top_srcdir)/include/k5-buf.h $(top_srcdir)/include/k5-err.h \ >+ $(top_srcdir)/include/k5-gmt_mktime.h $(top_srcdir)/include/k5-int-pkinit.h \ >+ $(top_srcdir)/include/k5-int.h $(top_srcdir)/include/k5-platform.h \ >+diff --git a/src/lib/krb5/os/os-proto.h b/src/lib/krb5/os/os-proto.h >+index a0fa37e..b122e80 100644 >+--- a/src/lib/krb5/os/os-proto.h >++++ b/src/lib/krb5/os/os-proto.h >+@@ -55,6 +55,19 @@ struct serverlist { >+ }; >+ #define SERVERLIST_INIT { NULL, 0 } >+ >++struct remote_address { >++ int family; >++ int type; >++ socklen_t len; >++ struct sockaddr_storage saddr; >++}; >++ >++struct sendto_callback_info { >++ int (*pfn_callback)(SOCKET fd, void *data, krb5_data *message); >++ void (*pfn_cleanup)(void *data, krb5_data *message); >++ void *data; >++}; >++ >+ krb5_error_code k5_locate_server(krb5_context, const krb5_data *realm, >+ struct serverlist *, >+ enum locate_service_type svc, int socktype); >+diff --git a/src/lib/krb5/os/sendto_kdc.c b/src/lib/krb5/os/sendto_kdc.c >+index 778ac61..f6e567d 100644 >+--- a/src/lib/krb5/os/sendto_kdc.c >++++ b/src/lib/krb5/os/sendto_kdc.c >+@@ -55,6 +55,61 @@ >+ #define DEFAULT_UDP_PREF_LIMIT 1465 >+ #define HARD_UDP_LIMIT 32700 /* could probably do 64K-epsilon ? */ >+ >++/* Select state flags. */ >++#define SSF_READ 0x01 >++#define SSF_WRITE 0x02 >++#define SSF_EXCEPTION 0x04 >++ >++/* Since fd_set is large on some platforms (8K on AIX 5.2), this probably >++ * shouldn't be allocated in automatic storage. */ >++struct select_state { >++#ifdef USE_POLL >++ struct pollfd fds[MAX_POLLFDS]; >++#else >++ int max; >++ fd_set rfds, wfds, xfds; >++#endif >++ int nfds; >++ struct timeval end_time; /* magic: tv_sec==0 => never time out */ >++}; >++ >++static const char *const state_strings[] = { >++ "INITIALIZING", "CONNECTING", "WRITING", "READING", "FAILED" >++}; >++ >++/* connection states */ >++enum conn_states { INITIALIZING, CONNECTING, WRITING, READING, FAILED }; >++struct incoming_krb5_message { >++ size_t bufsizebytes_read; >++ size_t bufsize; >++ char *buf; >++ char *pos; >++ unsigned char bufsizebytes[4]; >++ size_t n_left; >++}; >++ >++struct conn_state { >++ SOCKET fd; >++ krb5_error_code err; >++ enum conn_states state; >++ unsigned int is_udp : 1; >++ int (*service)(krb5_context context, struct conn_state *, >++ struct select_state *, int); >++ struct remote_address addr; >++ struct { >++ struct { >++ sg_buf sgbuf[2]; >++ sg_buf *sgp; >++ int sg_count; >++ unsigned char msg_len_buf[4]; >++ } out; >++ struct incoming_krb5_message in; >++ } x; >++ krb5_data callback_buffer; >++ size_t server_index; >++ struct conn_state *next; >++}; >++ >+ #undef DEBUG >+ >+ #ifdef DEBUG >+@@ -411,18 +466,6 @@ cleanup: >+ * connections already in progress >+ */ >+ >+-#include "cm.h" >+- >+-/* >+- * Currently only sendto_kdc.c knows how to use poll(); the other candidate >+- * user, lib/apputils/net-server.c, is stuck using select() for the moment >+- * since it is entangled with the RPC library. The following cm_* functions >+- * are not fully generic, are O(n^2) in the poll case, and are limited to >+- * handling 1024 connections (in order to maintain a constant-sized selstate). >+- * More rearchitecting would be appropriate before extending this support to >+- * the KDC and kadmind. >+- */ >+- >+ static void >+ cm_init_selstate(struct select_state *selstate) >+ { >+@@ -518,7 +561,7 @@ cm_select_or_poll(const struct select_state *in, struct select_state *out, >+ if (in->end_time.tv_sec == 0) >+ timeout = -1; >+ else { >+- e = k5_getcurtime(&now); >++ e = gettimeofday(&now, NULL); >+ if (e) >+ return e; >+ timeout = (in->end_time.tv_sec - now.tv_sec) * 1000 + >+@@ -528,15 +571,42 @@ cm_select_or_poll(const struct select_state *in, struct select_state *out, >+ return 0; >+ } >+ } >+- /* We don't need a separate copy of the selstate for poll, but use one >+- * anyone for consistency with the select wrapper. */ >++ /* We don't need a separate copy of the selstate for poll, but use one for >++ * consistency with how we use select. */ >+ *out = *in; >+ *sret = poll(out->fds, out->nfds, timeout); >+ e = SOCKET_ERRNO; >+ return (*sret < 0) ? e : 0; >+ #else >+- /* Use the select wrapper from cm.c. */ >+- return krb5int_cm_call_select(in, out, sret); >++ struct timeval now, *timo; >++ krb5_error_code e; >++ >++ *out = *in; >++ e = gettimeofday(&now, NULL); >++ if (e) >++ return e; >++ if (out->end_time.tv_sec == 0) { >++ timo = 0; >++ } else { >++ timo = &out->end_time; >++ out->end_time.tv_sec -= now.tv_sec; >++ out->end_time.tv_usec -= now.tv_usec; >++ if (out->end_time.tv_usec < 0) { >++ out->end_time.tv_usec += 1000000; >++ out->end_time.tv_sec--; >++ } >++ if (out->end_time.tv_sec < 0) { >++ *sret = 0; >++ return 0; >++ } >++ } >++ >++ *sret = select(out->max, &out->rfds, &out->wfds, &out->xfds, timo); >++ e = SOCKET_ERRNO; >++ >++ if (*sret < 0) >++ return e; >++ return 0; >+ #endif >+ } >+ >+@@ -820,7 +890,7 @@ start_connection(krb5_context context, struct conn_state *state, >+ */ >+ if (callback_info) { >+ >+- e = callback_info->pfn_callback(state, callback_info->context, >++ e = callback_info->pfn_callback(state->fd, callback_info->data, >+ &state->callback_buffer); >+ if (e != 0) { >+ dprint("callback failed: %m\n", e); >+@@ -1159,7 +1229,7 @@ service_fds(krb5_context context, struct select_state *selstate, int interval, >+ >+ *winner_out = NULL; >+ >+- e = k5_getcurtime(&now); >++ e = gettimeofday(&now, NULL); >+ if (e) >+ return 1; >+ selstate->end_time = now; >+@@ -1348,7 +1418,7 @@ cleanup: >+ if (state->state == READING && state->x.in.buf != udpbuf) >+ free(state->x.in.buf); >+ if (callback_info) { >+- callback_info->pfn_cleanup(callback_info->context, >++ callback_info->pfn_cleanup(callback_info->data, >+ &state->callback_buffer); >+ } >+ free(state); >+diff --git a/src/lib/krb5/os/t_trace.c b/src/lib/krb5/os/t_trace.c >+index ed53181..36044f5 100644 >+--- a/src/lib/krb5/os/t_trace.c >++++ b/src/lib/krb5/os/t_trace.c >+@@ -38,7 +38,7 @@ >+ >+ #define TEST >+ #include "k5-int.h" >+-#include "cm.h" >++#include "os-proto.h" >+ >+ const char *prog; >+ >+diff --git a/src/lib/krb5/os/trace.c b/src/lib/krb5/os/trace.c >+index 24b0f38..560befa 100644 >+--- a/src/lib/krb5/os/trace.c >++++ b/src/lib/krb5/os/trace.c >+@@ -38,7 +38,7 @@ >+ */ >+ >+ #include "k5-int.h" >+-#include "cm.h" >++#include "os-proto.h" >+ >+ #ifndef DISABLE_TRACING >+ >+-- >+1.9.3 >+ >diff --git a/krb5-1.12-Trace-log-with-a-subset-of-struct-conn_state.patch b/krb5-1.12-Trace-log-with-a-subset-of-struct-conn_state.patch >new file mode 100644 >index 0000000..e6ae3f9 >--- /dev/null >+++ b/krb5-1.12-Trace-log-with-a-subset-of-struct-conn_state.patch >@@ -0,0 +1,425 @@ >+From d30d2e435b8fb2f096d88a684aa5b3761d09d53b Mon Sep 17 00:00:00 2001 >+From: Greg Hudson <ghudson@mit.edu> >+Date: Wed, 10 Apr 2013 18:10:52 -0400 >+Subject: [PATCH 1/4] Trace log with a subset of struct conn_state >+ >+In struct conn_state, collect together the fields for the remote >+address and put them in a substructure. Pass this substructure to >+trace logging macros instead of the entire conn_state structure, so >+that trace.c doesn't have to know about the whole structure. >+--- >+ src/include/cm.h | 11 +++++---- >+ src/include/k5-trace.h | 54 +++++++++++++++++++++---------------------- >+ src/lib/krb5/os/sendto_kdc.c | 55 +++++++++++++++++++++++--------------------- >+ src/lib/krb5/os/t_trace.c | 34 +++++++++++++-------------- >+ src/lib/krb5/os/t_trace.ref | 8 +++---- >+ src/lib/krb5/os/trace.c | 18 +++++++-------- >+ 6 files changed, 93 insertions(+), 87 deletions(-) >+ >+diff --git a/src/include/cm.h b/src/include/cm.h >+index d9c23fc..837a549 100644 >+--- a/src/include/cm.h >++++ b/src/include/cm.h >+@@ -63,6 +63,12 @@ struct incoming_krb5_message { >+ unsigned char bufsizebytes[4]; >+ size_t n_left; >+ }; >++struct remote_address { >++ int family; >++ int type; >++ socklen_t len; >++ struct sockaddr_storage saddr; >++}; >+ struct conn_state { >+ SOCKET fd; >+ krb5_error_code err; >+@@ -70,10 +76,7 @@ struct conn_state { >+ unsigned int is_udp : 1; >+ int (*service)(krb5_context context, struct conn_state *, >+ struct select_state *, int); >+- int socktype; >+- int family; >+- size_t addrlen; >+- struct sockaddr_storage addr; >++ struct remote_address addr; >+ struct { >+ struct { >+ sg_buf sgbuf[2]; >+diff --git a/src/include/k5-trace.h b/src/include/k5-trace.h >+index df7159f..e925442 100644 >+--- a/src/include/k5-trace.h >++++ b/src/include/k5-trace.h >+@@ -60,7 +60,7 @@ >+ * {lenstr} size_t and const char *, as a counted string >+ * {hexlenstr} size_t and const char *, as hex bytes >+ * {hashlenstr} size_t and const char *, as four-character hex hash >+- * {connstate} struct conn_state *, show socket type, address, port >++ * {raddr} struct remote_address *, show socket type, address, port >+ * {data} krb5_data *, display as counted string >+ * {hexdata} krb5_data *, display as hex bytes >+ * {errno} int, display as number/errorstring >+@@ -301,32 +301,32 @@ void krb5int_trace(krb5_context context, const char *fmt, ...); >+ TRACE(c, "Response was{str} from master KDC", (master) ? "" : " not") >+ #define TRACE_SENDTO_KDC_RESOLVING(c, hostname) \ >+ TRACE(c, "Resolving hostname {str}", hostname) >+-#define TRACE_SENDTO_KDC_RESPONSE(c, conn) \ >+- TRACE(c, "Received answer from {connstate}", conn) >+-#define TRACE_SENDTO_KDC_TCP_CONNECT(c, conn) \ >+- TRACE(c, "Initiating TCP connection to {connstate}", conn) >+-#define TRACE_SENDTO_KDC_TCP_DISCONNECT(c, conn) \ >+- TRACE(c, "Terminating TCP connection to {connstate}", conn) >+-#define TRACE_SENDTO_KDC_TCP_ERROR_CONNECT(c, conn, err) \ >+- TRACE(c, "TCP error connecting to {connstate}: {errno}", conn, err) >+-#define TRACE_SENDTO_KDC_TCP_ERROR_RECV(c, conn, err) \ >+- TRACE(c, "TCP error receiving from {connstate}: {errno}", conn, err) >+-#define TRACE_SENDTO_KDC_TCP_ERROR_RECV_LEN(c, conn, err) \ >+- TRACE(c, "TCP error receiving from {connstate}: {errno}", conn, err) >+-#define TRACE_SENDTO_KDC_TCP_ERROR_SEND(c, conn, err) \ >+- TRACE(c, "TCP error sending to {connstate}: {errno}", conn, err) >+-#define TRACE_SENDTO_KDC_TCP_SEND(c, conn) \ >+- TRACE(c, "Sending TCP request to {connstate}", conn) >+-#define TRACE_SENDTO_KDC_UDP_ERROR_RECV(c, conn, err) \ >+- TRACE(c, "UDP error receiving from {connstate}: {errno}", conn, err) >+-#define TRACE_SENDTO_KDC_UDP_ERROR_SEND_INITIAL(c, conn, err) \ >+- TRACE(c, "UDP error sending to {connstate}: {errno}", conn, err) >+-#define TRACE_SENDTO_KDC_UDP_ERROR_SEND_RETRY(c, conn, err) \ >+- TRACE(c, "UDP error sending to {connstate}: {errno}", conn, err) >+-#define TRACE_SENDTO_KDC_UDP_SEND_INITIAL(c, conn) \ >+- TRACE(c, "Sending initial UDP request to {connstate}", conn) >+-#define TRACE_SENDTO_KDC_UDP_SEND_RETRY(c, conn) \ >+- TRACE(c, "Sending retry UDP request to {connstate}", conn) >++#define TRACE_SENDTO_KDC_RESPONSE(c, raddr) \ >++ TRACE(c, "Received answer from {raddr}", raddr) >++#define TRACE_SENDTO_KDC_TCP_CONNECT(c, raddr) \ >++ TRACE(c, "Initiating TCP connection to {raddr}", raddr) >++#define TRACE_SENDTO_KDC_TCP_DISCONNECT(c, raddr) \ >++ TRACE(c, "Terminating TCP connection to {raddr}", raddr) >++#define TRACE_SENDTO_KDC_TCP_ERROR_CONNECT(c, raddr, err) \ >++ TRACE(c, "TCP error connecting to {raddr}: {errno}", raddr, err) >++#define TRACE_SENDTO_KDC_TCP_ERROR_RECV(c, raddr, err) \ >++ TRACE(c, "TCP error receiving from {raddr}: {errno}", raddr, err) >++#define TRACE_SENDTO_KDC_TCP_ERROR_RECV_LEN(c, raddr, err) \ >++ TRACE(c, "TCP error receiving from {raddr}: {errno}", raddr, err) >++#define TRACE_SENDTO_KDC_TCP_ERROR_SEND(c, raddr, err) \ >++ TRACE(c, "TCP error sending to {raddr}: {errno}", raddr, err) >++#define TRACE_SENDTO_KDC_TCP_SEND(c, raddr) \ >++ TRACE(c, "Sending TCP request to {raddr}", raddr) >++#define TRACE_SENDTO_KDC_UDP_ERROR_RECV(c, raddr, err) \ >++ TRACE(c, "UDP error receiving from {raddr}: {errno}", raddr, err) >++#define TRACE_SENDTO_KDC_UDP_ERROR_SEND_INITIAL(c, raddr, err) \ >++ TRACE(c, "UDP error sending to {raddr}: {errno}", raddr, err) >++#define TRACE_SENDTO_KDC_UDP_ERROR_SEND_RETRY(c, raddr, err) \ >++ TRACE(c, "UDP error sending to {raddr}: {errno}", raddr, err) >++#define TRACE_SENDTO_KDC_UDP_SEND_INITIAL(c, raddr) \ >++ TRACE(c, "Sending initial UDP request to {raddr}", raddr) >++#define TRACE_SENDTO_KDC_UDP_SEND_RETRY(c, raddr) \ >++ TRACE(c, "Sending retry UDP request to {raddr}", raddr) >+ >+ #define TRACE_SEND_TGS_ETYPES(c, etypes) \ >+ TRACE(c, "etypes requested in TGS request: {etypes}", etypes) >+diff --git a/src/lib/krb5/os/sendto_kdc.c b/src/lib/krb5/os/sendto_kdc.c >+index cc7b86f..778ac61 100644 >+--- a/src/lib/krb5/os/sendto_kdc.c >++++ b/src/lib/krb5/os/sendto_kdc.c >+@@ -605,10 +605,10 @@ add_connection(struct conn_state **conns, struct addrinfo *ai, >+ state->state = INITIALIZING; >+ state->err = 0; >+ state->x.out.sgp = state->x.out.sgbuf; >+- state->socktype = ai->ai_socktype; >+- state->family = ai->ai_family; >+- state->addrlen = ai->ai_addrlen; >+- memcpy(&state->addr, ai->ai_addr, ai->ai_addrlen); >++ state->addr.type = ai->ai_socktype; >++ state->addr.family = ai->ai_family; >++ state->addr.len = ai->ai_addrlen; >++ memcpy(&state->addr.saddr, ai->ai_addr, ai->ai_addrlen); >+ state->fd = INVALID_SOCKET; >+ state->server_index = server_index; >+ SG_SET(&state->x.out.sgbuf[1], 0, 0); >+@@ -766,25 +766,27 @@ start_connection(krb5_context context, struct conn_state *state, >+ static const struct linger lopt = { 0, 0 }; >+ >+ dprint("start_connection(@%p)\ngetting %s socket in family %d...", state, >+- state->socktype == SOCK_STREAM ? "stream" : "dgram", state->family); >+- fd = socket(state->family, state->socktype, 0); >++ state->addr.type == SOCK_STREAM ? "stream" : "dgram", >++ state->addr.family); >++ fd = socket(state->addr.family, state->addr.type, 0); >+ if (fd == INVALID_SOCKET) { >+ state->err = SOCKET_ERRNO; >+- dprint("socket: %m creating with af %d\n", state->err, state->family); >++ dprint("socket: %m creating with af %d\n", state->err, >++ state->addr.family); >+ return -1; /* try other hosts */ >+ } >+ set_cloexec_fd(fd); >+ /* Make it non-blocking. */ >+ if (ioctlsocket(fd, FIONBIO, (const void *) &one)) >+ dperror("sendto_kdc: ioctl(FIONBIO)"); >+- if (state->socktype == SOCK_STREAM) { >++ if (state->addr.type == SOCK_STREAM) { >+ if (setsockopt(fd, SOL_SOCKET, SO_LINGER, &lopt, sizeof(lopt))) >+ dperror("sendto_kdc: setsockopt(SO_LINGER)"); >+- TRACE_SENDTO_KDC_TCP_CONNECT(context, state); >++ TRACE_SENDTO_KDC_TCP_CONNECT(context, &state->addr); >+ } >+ >+ /* Start connecting to KDC. */ >+- e = connect(fd, (struct sockaddr *)&state->addr, state->addrlen); >++ e = connect(fd, (struct sockaddr *)&state->addr.saddr, state->addr.len); >+ if (e != 0) { >+ /* >+ * This is the path that should be followed for non-blocking >+@@ -832,16 +834,16 @@ start_connection(krb5_context context, struct conn_state *state, >+ set_conn_state_msg_length(state, &state->callback_buffer); >+ } >+ >+- if (state->socktype == SOCK_DGRAM) { >++ if (state->addr.type == SOCK_DGRAM) { >+ /* Send it now. */ >+ ssize_t ret; >+ sg_buf *sg = &state->x.out.sgbuf[0]; >+ >+- TRACE_SENDTO_KDC_UDP_SEND_INITIAL(context, state); >++ TRACE_SENDTO_KDC_UDP_SEND_INITIAL(context, &state->addr); >+ dprint("sending %d bytes on fd %d\n", SG_LEN(sg), state->fd); >+ ret = send(state->fd, SG_BUF(sg), SG_LEN(sg), 0); >+ if (ret < 0 || (size_t) ret != SG_LEN(sg)) { >+- TRACE_SENDTO_KDC_UDP_ERROR_SEND_INITIAL(context, state, >++ TRACE_SENDTO_KDC_UDP_ERROR_SEND_INITIAL(context, &state->addr, >+ SOCKET_ERRNO); >+ dperror("sendto"); >+ (void) closesocket(state->fd); >+@@ -889,7 +891,7 @@ maybe_send(krb5_context context, struct conn_state *conn, >+ return -1; >+ } >+ >+- if (conn->socktype == SOCK_STREAM) { >++ if (conn->addr.type == SOCK_STREAM) { >+ dprint("skipping stream socket\n"); >+ /* The select callback will handle flushing any data we >+ haven't written yet, and we only write it once. */ >+@@ -898,11 +900,12 @@ maybe_send(krb5_context context, struct conn_state *conn, >+ >+ /* UDP - retransmit after a previous attempt timed out. */ >+ sg = &conn->x.out.sgbuf[0]; >+- TRACE_SENDTO_KDC_UDP_SEND_RETRY(context, conn); >++ TRACE_SENDTO_KDC_UDP_SEND_RETRY(context, &conn->addr); >+ dprint("sending %d bytes on fd %d\n", SG_LEN(sg), conn->fd); >+ ret = send(conn->fd, SG_BUF(sg), SG_LEN(sg), 0); >+ if (ret < 0 || (size_t) ret != SG_LEN(sg)) { >+- TRACE_SENDTO_KDC_UDP_ERROR_SEND_RETRY(context, conn, SOCKET_ERRNO); >++ TRACE_SENDTO_KDC_UDP_ERROR_SEND_RETRY(context, &conn->addr, >++ SOCKET_ERRNO); >+ dperror("send"); >+ /* Keep connection alive, we'll try again next pass. >+ >+@@ -965,7 +968,7 @@ service_tcp_fd(krb5_context context, struct conn_state *conn, >+ /* Bad -- the KDC shouldn't be sending to us first. */ >+ e = EINVAL /* ?? */; >+ kill_conn: >+- TRACE_SENDTO_KDC_TCP_DISCONNECT(context, conn); >++ TRACE_SENDTO_KDC_TCP_DISCONNECT(context, &conn->addr); >+ kill_conn(conn, selstate, e); >+ if (e == EINVAL) { >+ closesocket(conn->fd); >+@@ -994,7 +997,7 @@ service_tcp_fd(krb5_context context, struct conn_state *conn, >+ */ >+ e = get_so_error(conn->fd); >+ if (e) { >+- TRACE_SENDTO_KDC_TCP_ERROR_CONNECT(context, conn, e); >++ TRACE_SENDTO_KDC_TCP_ERROR_CONNECT(context, &conn->addr, e); >+ dprint("socket error on write fd: %m", e); >+ goto kill_conn; >+ } >+@@ -1016,12 +1019,12 @@ service_tcp_fd(krb5_context context, struct conn_state *conn, >+ ((conn->x.out.sg_count == 2 ? SG_LEN(&conn->x.out.sgp[1]) : 0) >+ + SG_LEN(&conn->x.out.sgp[0])), >+ conn->fd); >+- TRACE_SENDTO_KDC_TCP_SEND(context, conn); >++ TRACE_SENDTO_KDC_TCP_SEND(context, &conn->addr); >+ nwritten = SOCKET_WRITEV(conn->fd, conn->x.out.sgp, >+ conn->x.out.sg_count, tmp); >+ if (nwritten < 0) { >+ e = SOCKET_ERRNO; >+- TRACE_SENDTO_KDC_TCP_ERROR_SEND(context, conn, e); >++ TRACE_SENDTO_KDC_TCP_ERROR_SEND(context, &conn->addr, e); >+ dprint("failed: %m\n", e); >+ goto kill_conn; >+ } >+@@ -1076,7 +1079,7 @@ service_tcp_fd(krb5_context context, struct conn_state *conn, >+ e = nread ? SOCKET_ERRNO : ECONNRESET; >+ free(conn->x.in.buf); >+ conn->x.in.buf = 0; >+- TRACE_SENDTO_KDC_TCP_ERROR_RECV(context, conn, e); >++ TRACE_SENDTO_KDC_TCP_ERROR_RECV(context, &conn->addr, e); >+ goto kill_conn; >+ } >+ conn->x.in.n_left -= nread; >+@@ -1092,7 +1095,7 @@ service_tcp_fd(krb5_context context, struct conn_state *conn, >+ 4 - conn->x.in.bufsizebytes_read); >+ if (nread <= 0) { >+ e = nread ? SOCKET_ERRNO : ECONNRESET; >+- TRACE_SENDTO_KDC_TCP_ERROR_RECV_LEN(context, conn, e); >++ TRACE_SENDTO_KDC_TCP_ERROR_RECV_LEN(context, &conn->addr, e); >+ goto kill_conn; >+ } >+ conn->x.in.bufsizebytes_read += nread; >+@@ -1136,7 +1139,7 @@ service_udp_fd(krb5_context context, struct conn_state *conn, >+ >+ nread = recv(conn->fd, conn->x.in.buf, conn->x.in.bufsize, 0); >+ if (nread < 0) { >+- TRACE_SENDTO_KDC_UDP_ERROR_RECV(context, conn, SOCKET_ERRNO); >++ TRACE_SENDTO_KDC_UDP_ERROR_RECV(context, &conn->addr, SOCKET_ERRNO); >+ kill_conn(conn, selstate, SOCKET_ERRNO); >+ return 0; >+ } >+@@ -1275,7 +1278,7 @@ k5_sendto(krb5_context context, const krb5_data *message, >+ goto cleanup; >+ for (state = *tailptr; state != NULL && !done; state = state->next) { >+ /* Contact each new connection whose socktype matches socktype1. */ >+- if (state->socktype != socktype1) >++ if (state->addr.type != socktype1) >+ continue; >+ if (maybe_send(context, state, sel_state, callback_info)) >+ continue; >+@@ -1287,7 +1290,7 @@ k5_sendto(krb5_context context, const krb5_data *message, >+ /* Complete the first pass by contacting servers of the non-preferred >+ * socktype (if given), waiting 1s for an answer from each. */ >+ for (state = conns; state != NULL && !done; state = state->next) { >+- if (state->socktype != socktype2) >++ if (state->addr.type != socktype2) >+ continue; >+ if (maybe_send(context, state, sel_state, callback_info)) >+ continue; >+@@ -1327,7 +1330,7 @@ k5_sendto(krb5_context context, const krb5_data *message, >+ goto cleanup; >+ } >+ /* Success! */ >+- TRACE_SENDTO_KDC_RESPONSE(context, winner); >++ TRACE_SENDTO_KDC_RESPONSE(context, &winner->addr); >+ reply->data = winner->x.in.buf; >+ reply->length = winner->x.in.pos - winner->x.in.buf; >+ retval = 0; >+diff --git a/src/lib/krb5/os/t_trace.c b/src/lib/krb5/os/t_trace.c >+index 746dbea..ed53181 100644 >+--- a/src/lib/krb5/os/t_trace.c >++++ b/src/lib/krb5/os/t_trace.c >+@@ -61,7 +61,7 @@ main (int argc, char *argv[]) >+ char *str = "example.data"; >+ krb5_octet *oct = (krb5_octet *) str; >+ unsigned int oct_length = strlen(str); >+- struct conn_state conn; >++ struct remote_address ra; >+ struct sockaddr_in *addr_in; >+ krb5_data data; >+ struct krb5_key_st key; >+@@ -112,26 +112,26 @@ main (int argc, char *argv[]) >+ TRACE(ctx, "size_t and const char *, as four-character hex hash: " >+ "{hashlenstr}", 1, NULL); >+ >+- conn.socktype = SOCK_STREAM; >+- addr_in = (struct sockaddr_in *) &conn.addr; >++ ra.type = SOCK_STREAM; >++ addr_in = (struct sockaddr_in *)&ra.saddr; >+ addr_in->sin_family = AF_INET; >+ addr_in->sin_addr.s_addr = INADDR_ANY; >+ addr_in->sin_port = htons(88); >+- conn.addrlen = sizeof(struct sockaddr_in); >+- conn.family = AF_INET; >+- TRACE(ctx, "struct conn_state *, show socket type, address, port: " >+- "{connstate}", &conn); >+- conn.socktype = SOCK_DGRAM; >+- TRACE(ctx, "struct conn_state *, show socket type, address, port: " >+- "{connstate}", &conn); >+- conn.socktype = 1234; >++ ra.len = sizeof(struct sockaddr_in); >++ ra.family = AF_INET; >++ TRACE(ctx, "struct remote_address *, show socket type, address, port: " >++ "{raddr}", &ra); >++ ra.type = SOCK_DGRAM; >++ TRACE(ctx, "struct remote_address *, show socket type, address, port: " >++ "{raddr}", &ra); >++ ra.type = 1234; >+ addr_in->sin_family = AF_UNSPEC; >+- conn.family = AF_UNSPEC; >+- TRACE(ctx, "struct conn_state *, show socket type, address, port: " >+- "{connstate}", &conn); >+- conn.family = 5678; >+- TRACE(ctx, "struct conn_state *, show socket type, address, port: " >+- "{connstate}", &conn); >++ ra.family = AF_UNSPEC; >++ TRACE(ctx, "struct remote_address *, show socket type, address, port: " >++ "{raddr}", &ra); >++ ra.family = 5678; >++ TRACE(ctx, "struct remote_address *, show socket type, address, port: " >++ "{raddr}", &ra); >+ >+ data.magic = 0; >+ data.length = strlen(str); >+diff --git a/src/lib/krb5/os/t_trace.ref b/src/lib/krb5/os/t_trace.ref >+index 4922b89..749d9c9 100644 >+--- a/src/lib/krb5/os/t_trace.ref >++++ b/src/lib/krb5/os/t_trace.ref >+@@ -8,10 +8,10 @@ size_t and const char *, as hex bytes: 6578616D706C652E64617461 >+ size_t and const char *, as hex bytes: (null) >+ size_t and const char *, as four-character hex hash: 7B9A >+ size_t and const char *, as four-character hex hash: (null) >+-struct conn_state *, show socket type, address, port: stream 0.0.0.0:88 >+-struct conn_state *, show socket type, address, port: dgram 0.0.0.0:88 >+-struct conn_state *, show socket type, address, port: socktype1234 AF_UNSPEC >+-struct conn_state *, show socket type, address, port: socktype1234 af5678 >++struct remote_address *, show socket type, address, port: stream 0.0.0.0:88 >++struct remote_address *, show socket type, address, port: dgram 0.0.0.0:88 >++struct remote_address *, show socket type, address, port: socktype1234 AF_UNSPEC >++struct remote_address *, show socket type, address, port: socktype1234 af5678 >+ krb5_data *, display as counted string: example.data >+ krb5_data *, display as counted string: (null) >+ krb5_data *, display as hex bytes: 6578616D706C652E64617461 >+diff --git a/src/lib/krb5/os/trace.c b/src/lib/krb5/os/trace.c >+index 8f9ba04..24b0f38 100644 >+--- a/src/lib/krb5/os/trace.c >++++ b/src/lib/krb5/os/trace.c >+@@ -130,7 +130,7 @@ trace_format(krb5_context context, const char *fmt, va_list ap) >+ krb5_error_code kerr; >+ size_t len, i; >+ int err; >+- struct conn_state *cs; >++ struct remote_address *ra; >+ const krb5_data *d; >+ krb5_data data; >+ char addrbuf[NI_MAXHOST], portbuf[NI_MAXSERV], tmpbuf[200], *str; >+@@ -195,22 +195,22 @@ trace_format(krb5_context context, const char *fmt, va_list ap) >+ krb5int_buf_add(&buf, str); >+ free(str); >+ } >+- } else if (strcmp(tmpbuf, "connstate") == 0) { >+- cs = va_arg(ap, struct conn_state *); >+- if (cs->socktype == SOCK_DGRAM) >++ } else if (strcmp(tmpbuf, "raddr") == 0) { >++ ra = va_arg(ap, struct remote_address *); >++ if (ra->type == SOCK_DGRAM) >+ krb5int_buf_add(&buf, "dgram"); >+- else if (cs->socktype == SOCK_STREAM) >++ else if (ra->type == SOCK_STREAM) >+ krb5int_buf_add(&buf, "stream"); >+ else >+- krb5int_buf_add_fmt(&buf, "socktype%d", cs->socktype); >++ krb5int_buf_add_fmt(&buf, "socktype%d", ra->type); >+ >+- if (getnameinfo((struct sockaddr *)&cs->addr, cs->addrlen, >++ if (getnameinfo((struct sockaddr *)&ra->saddr, ra->len, >+ addrbuf, sizeof(addrbuf), portbuf, sizeof(portbuf), >+ NI_NUMERICHOST|NI_NUMERICSERV) != 0) { >+- if (cs->family == AF_UNSPEC) >++ if (ra->family == AF_UNSPEC) >+ krb5int_buf_add(&buf, " AF_UNSPEC"); >+ else >+- krb5int_buf_add_fmt(&buf, " af%d", cs->family); >++ krb5int_buf_add_fmt(&buf, " af%d", ra->family); >+ } else >+ krb5int_buf_add_fmt(&buf, " %s:%s", addrbuf, portbuf); >+ } else if (strcmp(tmpbuf, "data") == 0) { >+-- >+1.9.3 >+ >diff --git a/krb5-1.12-Use-millisecond-timeouts-in-sendto_kdc.c.patch b/krb5-1.12-Use-millisecond-timeouts-in-sendto_kdc.c.patch >new file mode 100644 >index 0000000..08d5972 >--- /dev/null >+++ b/krb5-1.12-Use-millisecond-timeouts-in-sendto_kdc.c.patch >@@ -0,0 +1,235 @@ >+From 863476085d37a3420f1d4d9cf6be59841525633a Mon Sep 17 00:00:00 2001 >+From: Nathaniel McCallum <npmccallum@redhat.com> >+Date: Tue, 9 Apr 2013 13:23:39 -0400 >+Subject: [PATCH 3/4] Use millisecond timeouts in sendto_kdc.c >+ >+Replace the end_time field of struct select_state with an endtime >+argument to cm_select_or_poll, expressed in milliseconds since the >+epoch. Add a helper function to get the current time in that format. >+Use a millisecond interval argument to service_fds for consistency. >+ >+[ghudson@mit.edu: fix overflow issue in get_curtime_ms; service_fds >+interval argument change; log message] >+--- >+ src/lib/krb5/os/sendto_kdc.c | 119 +++++++++++++++++++------------------------ >+ 1 file changed, 51 insertions(+), 68 deletions(-) >+ >+diff --git a/src/lib/krb5/os/sendto_kdc.c b/src/lib/krb5/os/sendto_kdc.c >+index f6e567d..ba0de65 100644 >+--- a/src/lib/krb5/os/sendto_kdc.c >++++ b/src/lib/krb5/os/sendto_kdc.c >+@@ -60,6 +60,8 @@ >+ #define SSF_WRITE 0x02 >+ #define SSF_EXCEPTION 0x04 >+ >++typedef krb5_int64 time_ms; >++ >+ /* Since fd_set is large on some platforms (8K on AIX 5.2), this probably >+ * shouldn't be allocated in automatic storage. */ >+ struct select_state { >+@@ -70,7 +72,6 @@ struct select_state { >+ fd_set rfds, wfds, xfds; >+ #endif >+ int nfds; >+- struct timeval end_time; /* magic: tv_sec==0 => never time out */ >+ }; >+ >+ static const char *const state_strings[] = { >+@@ -446,6 +447,18 @@ cleanup: >+ >+ #endif >+ >++/* Get current time in milliseconds. */ >++static krb5_error_code >++get_curtime_ms(time_ms *time_out) >++{ >++ struct timeval tv; >++ >++ if (gettimeofday(&tv, 0)) >++ return errno; >++ *time_out = (time_ms)tv.tv_sec * 1000 + tv.tv_usec / 1000; >++ return 0; >++} >++ >+ /* >+ * Notes: >+ * >+@@ -470,7 +483,6 @@ static void >+ cm_init_selstate(struct select_state *selstate) >+ { >+ selstate->nfds = 0; >+- selstate->end_time.tv_sec = selstate->end_time.tv_usec = 0; >+ #ifndef USE_POLL >+ selstate->max = 0; >+ FD_ZERO(&selstate->rfds); >+@@ -551,63 +563,33 @@ cm_unset_write(struct select_state *selstate, int fd) >+ } >+ >+ static krb5_error_code >+-cm_select_or_poll(const struct select_state *in, struct select_state *out, >+- int *sret) >++cm_select_or_poll(const struct select_state *in, time_ms endtime, >++ struct select_state *out, int *sret) >+ { >+-#ifdef USE_POLL >+- struct timeval now; >+- int e, timeout; >+- >+- if (in->end_time.tv_sec == 0) >+- timeout = -1; >+- else { >+- e = gettimeofday(&now, NULL); >+- if (e) >+- return e; >+- timeout = (in->end_time.tv_sec - now.tv_sec) * 1000 + >+- (in->end_time.tv_usec - now.tv_usec) / 1000; >+- if (timeout < 0) { >+- *sret = 0; >+- return 0; >+- } >+- } >++#ifndef USE_POLL >++ struct timeval tv; >++#endif >++ krb5_error_code retval; >++ time_ms curtime, interval; >++ >++ retval = get_curtime_ms(&curtime); >++ if (retval != 0) >++ return retval; >++ interval = (curtime < endtime) ? endtime - curtime : 0; >++ >+ /* We don't need a separate copy of the selstate for poll, but use one for >+ * consistency with how we use select. */ >+ *out = *in; >+- *sret = poll(out->fds, out->nfds, timeout); >+- e = SOCKET_ERRNO; >+- return (*sret < 0) ? e : 0; >+-#else >+- struct timeval now, *timo; >+- krb5_error_code e; >+ >+- *out = *in; >+- e = gettimeofday(&now, NULL); >+- if (e) >+- return e; >+- if (out->end_time.tv_sec == 0) { >+- timo = 0; >+- } else { >+- timo = &out->end_time; >+- out->end_time.tv_sec -= now.tv_sec; >+- out->end_time.tv_usec -= now.tv_usec; >+- if (out->end_time.tv_usec < 0) { >+- out->end_time.tv_usec += 1000000; >+- out->end_time.tv_sec--; >+- } >+- if (out->end_time.tv_sec < 0) { >+- *sret = 0; >+- return 0; >+- } >+- } >+- >+- *sret = select(out->max, &out->rfds, &out->wfds, &out->xfds, timo); >+- e = SOCKET_ERRNO; >+- >+- if (*sret < 0) >+- return e; >+- return 0; >++#ifdef USE_POLL >++ *sret = poll(out->fds, out->nfds, interval); >++#else >++ tv.tv_sec = interval / 1000; >++ tv.tv_usec = interval % 1000 * 1000; >++ *sret = select(out->max, &out->rfds, &out->wfds, &out->xfds, &tv); >+ #endif >++ >++ return (*sret < 0) ? SOCKET_ERRNO : 0; >+ } >+ >+ static unsigned int >+@@ -1218,26 +1200,26 @@ service_udp_fd(krb5_context context, struct conn_state *conn, >+ } >+ >+ static krb5_boolean >+-service_fds(krb5_context context, struct select_state *selstate, int interval, >+- struct conn_state *conns, struct select_state *seltemp, >++service_fds(krb5_context context, struct select_state *selstate, >++ time_ms interval, struct conn_state *conns, >++ struct select_state *seltemp, >+ int (*msg_handler)(krb5_context, const krb5_data *, void *), >+ void *msg_handler_data, struct conn_state **winner_out) >+ { >+ int e, selret = 0; >+- struct timeval now; >++ time_ms endtime; >+ struct conn_state *state; >+ >+ *winner_out = NULL; >+ >+- e = gettimeofday(&now, NULL); >++ e = get_curtime_ms(&endtime); >+ if (e) >+ return 1; >+- selstate->end_time = now; >+- selstate->end_time.tv_sec += interval; >++ endtime += interval; >+ >+ e = 0; >+ while (selstate->nfds > 0) { >+- e = cm_select_or_poll(selstate, seltemp, &selret); >++ e = cm_select_or_poll(selstate, endtime, seltemp, &selret); >+ if (e == EINTR) >+ continue; >+ if (e != 0) >+@@ -1316,7 +1298,8 @@ k5_sendto(krb5_context context, const krb5_data *message, >+ int (*msg_handler)(krb5_context, const krb5_data *, void *), >+ void *msg_handler_data) >+ { >+- int pass, delay; >++ int pass; >++ time_ms delay; >+ krb5_error_code retval; >+ struct conn_state *conns = NULL, *state, **tailptr, *next, *winner; >+ size_t s; >+@@ -1352,7 +1335,7 @@ k5_sendto(krb5_context context, const krb5_data *message, >+ continue; >+ if (maybe_send(context, state, sel_state, callback_info)) >+ continue; >+- done = service_fds(context, sel_state, 1, conns, seltemp, >++ done = service_fds(context, sel_state, 1000, conns, seltemp, >+ msg_handler, msg_handler_data, &winner); >+ } >+ } >+@@ -1364,23 +1347,23 @@ k5_sendto(krb5_context context, const krb5_data *message, >+ continue; >+ if (maybe_send(context, state, sel_state, callback_info)) >+ continue; >+- done = service_fds(context, sel_state, 1, conns, seltemp, msg_handler, >+- msg_handler_data, &winner); >++ done = service_fds(context, sel_state, 1000, conns, seltemp, >++ msg_handler, msg_handler_data, &winner); >+ } >+ >+ /* Wait for two seconds at the end of the first pass. */ >+ if (!done) { >+- done = service_fds(context, sel_state, 2, conns, seltemp, msg_handler, >+- msg_handler_data, &winner); >++ done = service_fds(context, sel_state, 2000, conns, seltemp, >++ msg_handler, msg_handler_data, &winner); >+ } >+ >+ /* Make remaining passes over all of the connections. */ >+- delay = 4; >++ delay = 4000; >+ for (pass = 1; pass < MAX_PASS && !done; pass++) { >+ for (state = conns; state != NULL && !done; state = state->next) { >+ if (maybe_send(context, state, sel_state, callback_info)) >+ continue; >+- done = service_fds(context, sel_state, 1, conns, seltemp, >++ done = service_fds(context, sel_state, 1000, conns, seltemp, >+ msg_handler, msg_handler_data, &winner); >+ if (sel_state->nfds == 0) >+ break; >+-- >+1.9.3 >+ >diff --git a/krb5.spec b/krb5.spec >index 19a0dac..3081fa9 100644 >--- a/krb5.spec >+++ b/krb5.spec >@@ -41,7 +41,7 @@ > Summary: The Kerberos network authentication system > Name: krb5 > Version: 1.11.5 >-Release: 11%{?dist} >+Release: 12%{?dist} > # Maybe we should explode from the now-available-to-everybody tarball instead? > # http://web.mit.edu/kerberos/dist/krb5/1.11/krb5-1.11.5-signed.tar > Source0: krb5-%{version}.tar.gz >@@ -133,6 +133,11 @@ Patch165: krb5-gssapi-spnego-deref.patch > Patch166: http://web.mit.edu/kerberos/advisories/2014-001-patch.txt > Patch167: http://web.mit.edu/kerberos/advisories/2014-001-patch.txt.asc > >+Patch168: krb5-1.12-Trace-log-with-a-subset-of-struct-conn_state.patch >+Patch169: krb5-1.12-Get-rid-of-cm.c-and-cm.h.patch >+Patch170: krb5-1.12-Use-millisecond-timeouts-in-sendto_kdc.c.patch >+Patch171: krb5-1.12-Dynamically-expand-timeout-when-TCP-connects.patch >+ > # Patches for otp plugin backport > Patch201: krb5-1.11.2-keycheck.patch > Patch202: krb5-1.11.2-otp.patch >@@ -424,6 +429,11 @@ ln -s NOTICE LICENSE > > %patch166 -p1 -b .2014-001 > >+%patch168 -p1 -b .tcp-timeout-trace >+%patch169 -p1 -b .tcp-timeout-remove-cm >+%patch170 -p1 -b .tcp-timeout-milliseconds >+%patch171 -p1 -b .tcp-timeout-dynamic-expand >+ > %patch201 -p1 -b .keycheck > %patch202 -p1 -b .otp > %patch203 -p1 -b .otp2 >@@ -1096,6 +1106,9 @@ exit 0 > %{_sbindir}/uuserver > > %changelog >+* Wed Aug 6 2014 Fraser Tweedale <ftweedal@redhat.com> - 1.11.5-12 >+- pull in upstream changes to expand timeout when TCP connects >+ > * Thu Aug 7 2014 Nalin Dahyabhai <nalin@redhat.com> - 1.11.5-11 > - incorporate fix for MITKRB5-SA-2014-001 (CVE-2014-4345) > >-- >1.9.3 >
You cannot view the attachment while viewing its details because your browser does not support IFRAMEs.
View the attachment on a separate page
.
View Attachment As Diff
View Attachment As Raw
Actions:
View
|
Diff
Attachments on
bug 1127992
: 925060 |
925299