mirror of
https://github.com/samba-team/samba.git
synced 2025-08-29 13:49:30 +03:00
Merge branch 'master' of ssh://git.samba.org/data/git/samba
This commit is contained in:
@ -13,7 +13,7 @@
|
|||||||
|
|
||||||
<refnamediv>
|
<refnamediv>
|
||||||
<refname>smbclient</refname>
|
<refname>smbclient</refname>
|
||||||
<refpurpose>ftp-like client to access SMB/CIFS resources
|
<refpurpose>ftp-like client to access SMB/CIFS resources
|
||||||
on servers</refpurpose>
|
on servers</refpurpose>
|
||||||
</refnamediv>
|
</refnamediv>
|
||||||
|
|
||||||
@ -30,6 +30,7 @@
|
|||||||
<arg choice="opt">-m maxprotocol</arg>
|
<arg choice="opt">-m maxprotocol</arg>
|
||||||
<arg choice="opt">-A authfile</arg>
|
<arg choice="opt">-A authfile</arg>
|
||||||
<arg choice="opt">-N</arg>
|
<arg choice="opt">-N</arg>
|
||||||
|
<arg choice="opt">-g</arg>
|
||||||
<arg choice="opt">-i scope</arg>
|
<arg choice="opt">-i scope</arg>
|
||||||
<arg choice="opt">-O <socket options></arg>
|
<arg choice="opt">-O <socket options></arg>
|
||||||
<arg choice="opt">-p port</arg>
|
<arg choice="opt">-p port</arg>
|
||||||
@ -39,7 +40,7 @@
|
|||||||
<arg choice="opt">-P</arg>
|
<arg choice="opt">-P</arg>
|
||||||
<arg choice="opt">-c <command></arg>
|
<arg choice="opt">-c <command></arg>
|
||||||
</cmdsynopsis>
|
</cmdsynopsis>
|
||||||
|
|
||||||
<cmdsynopsis>
|
<cmdsynopsis>
|
||||||
<command>smbclient</command>
|
<command>smbclient</command>
|
||||||
<arg choice="req">servicename</arg>
|
<arg choice="req">servicename</arg>
|
||||||
@ -54,6 +55,7 @@
|
|||||||
<arg choice="opt">-m maxprotocol</arg>
|
<arg choice="opt">-m maxprotocol</arg>
|
||||||
<arg choice="opt">-A authfile</arg>
|
<arg choice="opt">-A authfile</arg>
|
||||||
<arg choice="opt">-N</arg>
|
<arg choice="opt">-N</arg>
|
||||||
|
<arg choice="opt">-g</arg>
|
||||||
<arg choice="opt">-l log-basename</arg>
|
<arg choice="opt">-l log-basename</arg>
|
||||||
<arg choice="opt">-I destinationIP</arg>
|
<arg choice="opt">-I destinationIP</arg>
|
||||||
<arg choice="opt">-E</arg>
|
<arg choice="opt">-E</arg>
|
||||||
@ -233,7 +235,7 @@
|
|||||||
on your WfWg PCs if you want them to always be able to receive
|
on your WfWg PCs if you want them to always be able to receive
|
||||||
messages. </para></listitem>
|
messages. </para></listitem>
|
||||||
</varlistentry>
|
</varlistentry>
|
||||||
|
|
||||||
<varlistentry>
|
<varlistentry>
|
||||||
<term>-p port</term>
|
<term>-p port</term>
|
||||||
<listitem><para>This number is the TCP port number that will be used
|
<listitem><para>This number is the TCP port number that will be used
|
||||||
@ -241,19 +243,27 @@
|
|||||||
TCP port number for an SMB/CIFS server is 139, which is the
|
TCP port number for an SMB/CIFS server is 139, which is the
|
||||||
default. </para></listitem>
|
default. </para></listitem>
|
||||||
</varlistentry>
|
</varlistentry>
|
||||||
|
|
||||||
|
<varlistentry>
|
||||||
|
<term>-g</term>
|
||||||
|
<listitem><para>This parameter provides combined with
|
||||||
|
<parameter>-L</parameter> easy parseable output that allows processing
|
||||||
|
with utilities such as grep and cut.
|
||||||
|
</para></listitem>
|
||||||
|
</varlistentry>
|
||||||
|
|
||||||
<varlistentry>
|
<varlistentry>
|
||||||
<term>-P</term>
|
<term>-P</term>
|
||||||
<listitem><para>
|
<listitem><para>
|
||||||
Make queries to the external server using the machine account of the local server.
|
Make queries to the external server using the machine account of the local server.
|
||||||
</para></listitem>
|
</para></listitem>
|
||||||
</varlistentry>
|
</varlistentry>
|
||||||
|
|
||||||
&stdarg.help;
|
&stdarg.help;
|
||||||
|
|
||||||
<varlistentry>
|
<varlistentry>
|
||||||
<term>-I IP-address</term>
|
<term>-I IP-address</term>
|
||||||
<listitem><para><replaceable>IP address</replaceable> is the address of the server to connect to.
|
<listitem><para><replaceable>IP address</replaceable> is the address of the server to connect to.
|
||||||
It should be specified in standard "a.b.c.d" notation. </para>
|
It should be specified in standard "a.b.c.d" notation. </para>
|
||||||
|
|
||||||
<para>Normally the client would attempt to locate a named
|
<para>Normally the client would attempt to locate a named
|
||||||
|
@ -21,17 +21,17 @@
|
|||||||
|
|
||||||
PATH=/bin:/usr/bin:/sbin:/usr/sbin
|
PATH=/bin:/usr/bin:/sbin:/usr/sbin
|
||||||
|
|
||||||
killproc()
|
killproc()
|
||||||
{
|
{
|
||||||
pid=`ps aux | grep $1 | egrep -v '(grep|perfcountd)' | awk '{print $2}'`
|
pid=`ps aux | grep $1 | egrep -v '(grep|perfcountd)' | awk '{print $2}'`
|
||||||
if [ "$pid" != "" ]; then
|
if [ x"$pid" != "x" ]; then
|
||||||
kill $pid
|
kill $pid
|
||||||
fi
|
fi
|
||||||
}
|
}
|
||||||
|
|
||||||
# Start/stop processes
|
# Start/stop processes
|
||||||
|
|
||||||
case "$1"
|
case "$1"
|
||||||
in
|
in
|
||||||
start)
|
start)
|
||||||
/opt/samba/bin/perfcount -d -f /var/lib/samba/perfmon 2> /dev/null
|
/opt/samba/bin/perfcount -d -f /var/lib/samba/perfmon 2> /dev/null
|
||||||
@ -47,7 +47,7 @@ stop)
|
|||||||
|
|
||||||
status)
|
status)
|
||||||
pid=`ps aux | grep perfcount | egrep -v '(grep|perfcountd)' | awk '{print $2}'`
|
pid=`ps aux | grep perfcount | egrep -v '(grep|perfcountd)' | awk '{print $2}'`
|
||||||
if [ "$pid" == "" ]; then
|
if [ x"$pid" = "x" ]; then
|
||||||
echo "Dead!"
|
echo "Dead!"
|
||||||
exit 2;
|
exit 2;
|
||||||
fi
|
fi
|
||||||
|
@ -484,31 +484,4 @@ struct winbindd_response {
|
|||||||
} extra_data;
|
} extra_data;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct WINBINDD_MEMORY_CREDS {
|
|
||||||
struct WINBINDD_MEMORY_CREDS *next, *prev;
|
|
||||||
const char *username; /* lookup key. */
|
|
||||||
uid_t uid;
|
|
||||||
int ref_count;
|
|
||||||
size_t len;
|
|
||||||
uint8_t *nt_hash; /* Base pointer for the following 2 */
|
|
||||||
uint8_t *lm_hash;
|
|
||||||
char *pass;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct WINBINDD_CCACHE_ENTRY {
|
|
||||||
struct WINBINDD_CCACHE_ENTRY *next, *prev;
|
|
||||||
const char *principal_name;
|
|
||||||
const char *ccname;
|
|
||||||
const char *service;
|
|
||||||
const char *username;
|
|
||||||
const char *realm;
|
|
||||||
struct WINBINDD_MEMORY_CREDS *cred_ptr;
|
|
||||||
int ref_count;
|
|
||||||
uid_t uid;
|
|
||||||
time_t create_time;
|
|
||||||
time_t renew_until;
|
|
||||||
time_t refresh_time;
|
|
||||||
struct timed_event *event;
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
@ -359,7 +359,8 @@ LIB_OBJ = $(LIBSAMBAUTIL_OBJ) $(UTIL_OBJ) $(CRYPTO_OBJ) \
|
|||||||
lib/tallocmsg.o lib/dmallocmsg.o libsmb/smb_signing.o \
|
lib/tallocmsg.o lib/dmallocmsg.o libsmb/smb_signing.o \
|
||||||
lib/iconv.o lib/pam_errors.o intl/lang_tdb.o lib/conn_tdb.o \
|
lib/iconv.o lib/pam_errors.o intl/lang_tdb.o lib/conn_tdb.o \
|
||||||
lib/adt_tree.o lib/gencache.o \
|
lib/adt_tree.o lib/gencache.o \
|
||||||
lib/module.o lib/events.o lib/ldap_escape.o @CHARSET_STATIC@ \
|
lib/module.o lib/events.o @LIBTEVENT_OBJ0@ \
|
||||||
|
lib/ldap_escape.o @CHARSET_STATIC@ \
|
||||||
lib/secdesc.o lib/util_seaccess.o lib/secace.o lib/secacl.o \
|
lib/secdesc.o lib/util_seaccess.o lib/secace.o lib/secacl.o \
|
||||||
libads/krb5_errs.o lib/system_smbd.o lib/audit.o $(LIBNDR_OBJ) \
|
libads/krb5_errs.o lib/system_smbd.o lib/audit.o $(LIBNDR_OBJ) \
|
||||||
lib/file_id.o lib/idmap_cache.o
|
lib/file_id.o lib/idmap_cache.o
|
||||||
|
@ -1353,6 +1353,11 @@ static int cmd_mget(void)
|
|||||||
do_list(mget_mask, attribute, do_mget, false, true);
|
do_list(mget_mask, attribute, do_mget, false, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (mget_mask == NULL) {
|
||||||
|
d_printf("nothing to mget\n");
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
if (!*mget_mask) {
|
if (!*mget_mask) {
|
||||||
mget_mask = talloc_asprintf(ctx,
|
mget_mask = talloc_asprintf(ctx,
|
||||||
"%s*",
|
"%s*",
|
||||||
|
@ -31,6 +31,15 @@ for obj in ${TALLOC_OBJ}; do
|
|||||||
done
|
done
|
||||||
AC_SUBST(LIBTALLOC_OBJ0)
|
AC_SUBST(LIBTALLOC_OBJ0)
|
||||||
|
|
||||||
|
m4_include(../lib/tevent/libtevent.m4)
|
||||||
|
|
||||||
|
LIBTEVENT_OBJ0=""
|
||||||
|
for obj in ${TEVENT_OBJ}; do
|
||||||
|
LIBTEVENT_OBJ0="${LIBTEVENT_OBJ0} ${teventdir}/${obj}"
|
||||||
|
done
|
||||||
|
AC_SUBST(LIBTEVENT_OBJ0)
|
||||||
|
LIBS="${LIBS} ${TEVENT_LIBS}"
|
||||||
|
|
||||||
# TODO: These should come from m4_include(lib/tdb/libtdb.m4)
|
# TODO: These should come from m4_include(lib/tdb/libtdb.m4)
|
||||||
# but currently this fails: things have to get merged from s4.
|
# but currently this fails: things have to get merged from s4.
|
||||||
tdbdir="../lib/tdb"
|
tdbdir="../lib/tdb"
|
||||||
@ -50,6 +59,7 @@ AC_SUBST(LIBTDB_OBJ0)
|
|||||||
SAMBA_CPPFLAGS="-Iinclude -I${srcdir-.}/include -I. -I${srcdir-.}"
|
SAMBA_CPPFLAGS="-Iinclude -I${srcdir-.}/include -I. -I${srcdir-.}"
|
||||||
SAMBA_CPPFLAGS="${SAMBA_CPPFLAGS} -I${srcdir-.}/../lib/replace"
|
SAMBA_CPPFLAGS="${SAMBA_CPPFLAGS} -I${srcdir-.}/../lib/replace"
|
||||||
SAMBA_CPPFLAGS="${SAMBA_CPPFLAGS} ${TALLOC_CFLAGS}"
|
SAMBA_CPPFLAGS="${SAMBA_CPPFLAGS} ${TALLOC_CFLAGS}"
|
||||||
|
SAMBA_CPPFLAGS="${SAMBA_CPPFLAGS} ${TEVENT_CFLAGS}"
|
||||||
SAMBA_CPPFLAGS="${SAMBA_CPPFLAGS} ${TDB_CFLAGS}"
|
SAMBA_CPPFLAGS="${SAMBA_CPPFLAGS} ${TDB_CFLAGS}"
|
||||||
SAMBA_CPPFLAGS="${SAMBA_CPPFLAGS} -I${srcdir-.}/libaddns"
|
SAMBA_CPPFLAGS="${SAMBA_CPPFLAGS} -I${srcdir-.}/libaddns"
|
||||||
SAMBA_CPPFLAGS="${SAMBA_CPPFLAGS} -I${srcdir-.}/librpc"
|
SAMBA_CPPFLAGS="${SAMBA_CPPFLAGS} -I${srcdir-.}/librpc"
|
||||||
|
@ -18,7 +18,27 @@
|
|||||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/* bits for file descriptor event flags */
|
#define TEVENT_COMPAT_DEFINES
|
||||||
#define EVENT_FD_READ 1
|
#include <tevent.h>
|
||||||
#define EVENT_FD_WRITE 2
|
|
||||||
|
#undef event_context_init
|
||||||
|
#define event_context_init(mem_ctx) s3_tevent_context_init(mem_ctx)
|
||||||
|
|
||||||
|
/* The following definitions come from lib/events.c */
|
||||||
|
|
||||||
|
void event_fd_set_writeable(struct fd_event *fde);
|
||||||
|
void event_fd_set_not_writeable(struct fd_event *fde);
|
||||||
|
void event_fd_set_readable(struct fd_event *fde);
|
||||||
|
void event_fd_set_not_readable(struct fd_event *fde);
|
||||||
|
bool event_add_to_select_args(struct event_context *event_ctx,
|
||||||
|
const struct timeval *now,
|
||||||
|
fd_set *read_fds, fd_set *write_fds,
|
||||||
|
struct timeval *timeout, int *maxfd);
|
||||||
|
bool run_events(struct event_context *event_ctx,
|
||||||
|
int selrtn, fd_set *read_fds, fd_set *write_fds);
|
||||||
|
struct timeval *get_timed_events_timeout(struct event_context *event_ctx,
|
||||||
|
struct timeval *to_ret);
|
||||||
|
void event_context_reinit(struct event_context *ev);
|
||||||
|
void dump_event_list(struct event_context *event_ctx);
|
||||||
|
struct tevent_context *s3_tevent_context_init(TALLOC_CTX *mem_ctx);
|
||||||
|
|
||||||
|
@ -574,6 +574,8 @@ struct smb_iconv_convenience *lp_iconv_convenience(void *lp_ctx);
|
|||||||
|
|
||||||
#include "../talloc/talloc.h"
|
#include "../talloc/talloc.h"
|
||||||
|
|
||||||
|
#include "event.h"
|
||||||
|
|
||||||
#include "../lib/util/data_blob.h"
|
#include "../lib/util/data_blob.h"
|
||||||
#include "../lib/util/time.h"
|
#include "../lib/util/time.h"
|
||||||
#include "../lib/util/asn1.h"
|
#include "../lib/util/asn1.h"
|
||||||
@ -642,7 +644,6 @@ struct smb_iconv_convenience *lp_iconv_convenience(void *lp_ctx);
|
|||||||
#include "nsswitch/winbind_client.h"
|
#include "nsswitch/winbind_client.h"
|
||||||
#include "spnego.h"
|
#include "spnego.h"
|
||||||
#include "rpc_client.h"
|
#include "rpc_client.h"
|
||||||
#include "event.h"
|
|
||||||
#include "dbwrap.h"
|
#include "dbwrap.h"
|
||||||
#include "packet.h"
|
#include "packet.h"
|
||||||
#include "ctdbd_conn.h"
|
#include "ctdbd_conn.h"
|
||||||
|
@ -501,46 +501,6 @@ void display_set_stderr(void);
|
|||||||
NTSTATUS map_nt_error_from_unix(int unix_error);
|
NTSTATUS map_nt_error_from_unix(int unix_error);
|
||||||
int map_errno_from_nt_status(NTSTATUS status);
|
int map_errno_from_nt_status(NTSTATUS status);
|
||||||
|
|
||||||
/* The following definitions come from lib/events.c */
|
|
||||||
|
|
||||||
struct timed_event *event_add_timed(struct event_context *event_ctx,
|
|
||||||
TALLOC_CTX *mem_ctx,
|
|
||||||
struct timeval when,
|
|
||||||
const char *event_name,
|
|
||||||
void (*handler)(struct event_context *event_ctx,
|
|
||||||
struct timed_event *te,
|
|
||||||
const struct timeval *now,
|
|
||||||
void *private_data),
|
|
||||||
void *private_data);
|
|
||||||
struct fd_event *event_add_fd(struct event_context *event_ctx,
|
|
||||||
TALLOC_CTX *mem_ctx,
|
|
||||||
int fd, uint16_t flags,
|
|
||||||
void (*handler)(struct event_context *event_ctx,
|
|
||||||
struct fd_event *event,
|
|
||||||
uint16 flags,
|
|
||||||
void *private_data),
|
|
||||||
void *private_data);
|
|
||||||
void event_fd_set_writeable(struct fd_event *fde);
|
|
||||||
void event_fd_set_not_writeable(struct fd_event *fde);
|
|
||||||
void event_fd_set_readable(struct fd_event *fde);
|
|
||||||
void event_fd_set_not_readable(struct fd_event *fde);
|
|
||||||
bool event_add_to_select_args(struct event_context *event_ctx,
|
|
||||||
const struct timeval *now,
|
|
||||||
fd_set *read_fds, fd_set *write_fds,
|
|
||||||
struct timeval *timeout, int *maxfd);
|
|
||||||
bool events_pending(struct event_context *event_ctx);
|
|
||||||
bool run_events(struct event_context *event_ctx,
|
|
||||||
int selrtn, fd_set *read_fds, fd_set *write_fds);
|
|
||||||
struct timeval *get_timed_events_timeout(struct event_context *event_ctx,
|
|
||||||
struct timeval *to_ret);
|
|
||||||
int event_loop_once(struct event_context *ev);
|
|
||||||
struct event_context *event_context_init(TALLOC_CTX *mem_ctx);
|
|
||||||
int set_event_dispatch_time(struct event_context *event_ctx,
|
|
||||||
const char *event_name, struct timeval when);
|
|
||||||
int cancel_named_event(struct event_context *event_ctx,
|
|
||||||
const char *event_name);
|
|
||||||
void dump_event_list(struct event_context *event_ctx);
|
|
||||||
|
|
||||||
/* The following definitions come from lib/fault.c */
|
/* The following definitions come from lib/fault.c */
|
||||||
void fault_setup(void (*fn)(void *));
|
void fault_setup(void (*fn)(void *));
|
||||||
void dump_core_setup(const char *progname);
|
void dump_core_setup(const char *progname);
|
||||||
@ -1183,6 +1143,7 @@ int set_blocking(int fd, bool set);
|
|||||||
void smb_msleep(unsigned int t);
|
void smb_msleep(unsigned int t);
|
||||||
void become_daemon(bool Fork, bool no_process_group);
|
void become_daemon(bool Fork, bool no_process_group);
|
||||||
bool reinit_after_fork(struct messaging_context *msg_ctx,
|
bool reinit_after_fork(struct messaging_context *msg_ctx,
|
||||||
|
struct event_context *ev_ctx,
|
||||||
bool parent_longlived);
|
bool parent_longlived);
|
||||||
bool yesno(const char *p);
|
bool yesno(const char *p);
|
||||||
void *malloc_(size_t size);
|
void *malloc_(size_t size);
|
||||||
|
@ -361,9 +361,6 @@ struct fd_handle {
|
|||||||
unsigned long gen_id;
|
unsigned long gen_id;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct event_context;
|
|
||||||
struct fd_event;
|
|
||||||
struct timed_event;
|
|
||||||
struct idle_event;
|
struct idle_event;
|
||||||
struct share_mode_entry;
|
struct share_mode_entry;
|
||||||
struct uuid;
|
struct uuid;
|
||||||
|
@ -103,12 +103,12 @@ void async_req_error(struct async_req *req, NTSTATUS status)
|
|||||||
* @brief Timed event callback
|
* @brief Timed event callback
|
||||||
* @param[in] ev Event context
|
* @param[in] ev Event context
|
||||||
* @param[in] te The timed event
|
* @param[in] te The timed event
|
||||||
* @param[in] now current time
|
* @param[in] now zero time
|
||||||
* @param[in] priv The async request to be finished
|
* @param[in] priv The async request to be finished
|
||||||
*/
|
*/
|
||||||
|
|
||||||
static void async_trigger(struct event_context *ev, struct timed_event *te,
|
static void async_trigger(struct event_context *ev, struct timed_event *te,
|
||||||
const struct timeval *now, void *priv)
|
struct timeval now, void *priv)
|
||||||
{
|
{
|
||||||
struct async_req *req = talloc_get_type_abort(priv, struct async_req);
|
struct async_req *req = talloc_get_type_abort(priv, struct async_req);
|
||||||
|
|
||||||
@ -139,7 +139,7 @@ bool async_post_status(struct async_req *req, struct event_context *ev,
|
|||||||
{
|
{
|
||||||
req->status = status;
|
req->status = status;
|
||||||
|
|
||||||
if (event_add_timed(ev, req, timeval_zero(), "async_trigger",
|
if (event_add_timed(ev, req, timeval_zero(),
|
||||||
async_trigger, req) == NULL) {
|
async_trigger, req) == NULL) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@ -197,7 +197,7 @@ NTSTATUS async_req_simple_recv(struct async_req *req)
|
|||||||
|
|
||||||
static void async_req_timedout(struct event_context *ev,
|
static void async_req_timedout(struct event_context *ev,
|
||||||
struct timed_event *te,
|
struct timed_event *te,
|
||||||
const struct timeval *now,
|
struct timeval now,
|
||||||
void *priv)
|
void *priv)
|
||||||
{
|
{
|
||||||
struct async_req *req = talloc_get_type_abort(
|
struct async_req *req = talloc_get_type_abort(
|
||||||
@ -211,7 +211,7 @@ bool async_req_set_timeout(struct async_req *req, struct event_context *ev,
|
|||||||
{
|
{
|
||||||
return (event_add_timed(ev, req,
|
return (event_add_timed(ev, req,
|
||||||
timeval_current_ofs(to.tv_sec, to.tv_usec),
|
timeval_current_ofs(to.tv_sec, to.tv_usec),
|
||||||
"async_req_timedout", async_req_timedout, req)
|
async_req_timedout, req)
|
||||||
!= NULL);
|
!= NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -268,7 +268,7 @@ static int async_queue_entry_destructor(struct async_queue_entry *e)
|
|||||||
|
|
||||||
static void async_req_immediate_trigger(struct event_context *ev,
|
static void async_req_immediate_trigger(struct event_context *ev,
|
||||||
struct timed_event *te,
|
struct timed_event *te,
|
||||||
const struct timeval *now,
|
struct timeval now,
|
||||||
void *priv)
|
void *priv)
|
||||||
{
|
{
|
||||||
struct async_queue_entry *e = talloc_get_type_abort(
|
struct async_queue_entry *e = talloc_get_type_abort(
|
||||||
@ -303,7 +303,6 @@ bool async_req_enqueue(struct async_req_queue *queue, struct event_context *ev,
|
|||||||
struct timed_event *te;
|
struct timed_event *te;
|
||||||
|
|
||||||
te = event_add_timed(ev, e, timeval_zero(),
|
te = event_add_timed(ev, e, timeval_zero(),
|
||||||
"async_req_immediate_trigger",
|
|
||||||
async_req_immediate_trigger,
|
async_req_immediate_trigger,
|
||||||
e);
|
e);
|
||||||
if (te == NULL) {
|
if (te == NULL) {
|
||||||
|
@ -200,7 +200,7 @@ struct deferred_msg_state {
|
|||||||
|
|
||||||
static void deferred_message_dispatch(struct event_context *event_ctx,
|
static void deferred_message_dispatch(struct event_context *event_ctx,
|
||||||
struct timed_event *te,
|
struct timed_event *te,
|
||||||
const struct timeval *now,
|
struct timeval now,
|
||||||
void *private_data)
|
void *private_data)
|
||||||
{
|
{
|
||||||
struct deferred_msg_state *state = talloc_get_type_abort(
|
struct deferred_msg_state *state = talloc_get_type_abort(
|
||||||
@ -383,7 +383,6 @@ static NTSTATUS ctdb_read_req(struct ctdbd_connection *conn, uint32 reqid,
|
|||||||
evt = event_add_timed(conn->msg_ctx->event_ctx,
|
evt = event_add_timed(conn->msg_ctx->event_ctx,
|
||||||
conn->msg_ctx->event_ctx,
|
conn->msg_ctx->event_ctx,
|
||||||
timeval_zero(),
|
timeval_zero(),
|
||||||
"deferred_message_dispatch",
|
|
||||||
deferred_message_dispatch,
|
deferred_message_dispatch,
|
||||||
msg_state);
|
msg_state);
|
||||||
if (evt == NULL) {
|
if (evt == NULL) {
|
||||||
|
@ -19,52 +19,19 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
#include "includes.h"
|
#include "includes.h"
|
||||||
|
#include <tevent_internal.h>
|
||||||
|
|
||||||
struct timed_event {
|
struct s3_event_context {
|
||||||
struct timed_event *next, *prev;
|
struct tevent_context *ev;
|
||||||
struct event_context *event_ctx;
|
struct tevent_fd *fd_events;
|
||||||
struct timeval when;
|
|
||||||
const char *event_name;
|
|
||||||
void (*handler)(struct event_context *event_ctx,
|
|
||||||
struct timed_event *te,
|
|
||||||
const struct timeval *now,
|
|
||||||
void *private_data);
|
|
||||||
void *private_data;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
struct fd_event {
|
static int s3_event_timer_destructor(struct tevent_timer *te)
|
||||||
struct fd_event *prev, *next;
|
|
||||||
struct event_context *event_ctx;
|
|
||||||
int fd;
|
|
||||||
uint16_t flags; /* see EVENT_FD_* flags */
|
|
||||||
void (*handler)(struct event_context *event_ctx,
|
|
||||||
struct fd_event *event,
|
|
||||||
uint16 flags,
|
|
||||||
void *private_data);
|
|
||||||
void *private_data;
|
|
||||||
};
|
|
||||||
|
|
||||||
#define EVENT_FD_WRITEABLE(fde) \
|
|
||||||
event_set_fd_flags(fde, event_get_fd_flags(fde) | EVENT_FD_WRITE)
|
|
||||||
#define EVENT_FD_READABLE(fde) \
|
|
||||||
event_set_fd_flags(fde, event_get_fd_flags(fde) | EVENT_FD_READ)
|
|
||||||
|
|
||||||
#define EVENT_FD_NOT_WRITEABLE(fde) \
|
|
||||||
event_set_fd_flags(fde, event_get_fd_flags(fde) & ~EVENT_FD_WRITE)
|
|
||||||
#define EVENT_FD_NOT_READABLE(fde) \
|
|
||||||
event_set_fd_flags(fde, event_get_fd_flags(fde) & ~EVENT_FD_READ)
|
|
||||||
|
|
||||||
struct event_context {
|
|
||||||
struct timed_event *timed_events;
|
|
||||||
struct fd_event *fd_events;
|
|
||||||
};
|
|
||||||
|
|
||||||
static int timed_event_destructor(struct timed_event *te)
|
|
||||||
{
|
{
|
||||||
DEBUG(10, ("Destroying timed event %lx \"%s\"\n", (unsigned long)te,
|
DEBUG(10, ("Destroying timer event %p \"%s\"\n",
|
||||||
te->event_name));
|
te, te->handler_name));
|
||||||
if (te->event_ctx != NULL) {
|
if (te->event_ctx != NULL) {
|
||||||
DLIST_REMOVE(te->event_ctx->timed_events, te);
|
DLIST_REMOVE(te->event_ctx->timer_events, te);
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@ -73,23 +40,23 @@ static int timed_event_destructor(struct timed_event *te)
|
|||||||
Add te by time.
|
Add te by time.
|
||||||
****************************************************************************/
|
****************************************************************************/
|
||||||
|
|
||||||
static void add_event_by_time(struct timed_event *te)
|
static void add_event_by_time(struct tevent_timer *te)
|
||||||
{
|
{
|
||||||
struct event_context *ctx = te->event_ctx;
|
struct tevent_context *ctx = te->event_ctx;
|
||||||
struct timed_event *last_te, *cur_te;
|
struct tevent_timer *last_te, *cur_te;
|
||||||
|
|
||||||
/* Keep the list ordered by time. We must preserve this. */
|
/* Keep the list ordered by time. We must preserve this. */
|
||||||
last_te = NULL;
|
last_te = NULL;
|
||||||
for (cur_te = ctx->timed_events; cur_te; cur_te = cur_te->next) {
|
for (cur_te = ctx->timer_events; cur_te; cur_te = cur_te->next) {
|
||||||
/* if the new event comes before the current one break */
|
/* if the new event comes before the current one break */
|
||||||
if (!timeval_is_zero(&cur_te->when) &&
|
if (!timeval_is_zero(&cur_te->next_event) &&
|
||||||
timeval_compare(&te->when, &cur_te->when) < 0) {
|
timeval_compare(&te->next_event, &cur_te->next_event) < 0) {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
last_te = cur_te;
|
last_te = cur_te;
|
||||||
}
|
}
|
||||||
|
|
||||||
DLIST_ADD_AFTER(ctx->timed_events, te, last_te);
|
DLIST_ADD_AFTER(ctx->timer_events, te, last_te);
|
||||||
}
|
}
|
||||||
|
|
||||||
/****************************************************************************
|
/****************************************************************************
|
||||||
@ -98,115 +65,128 @@ static void add_event_by_time(struct timed_event *te)
|
|||||||
handed to it.
|
handed to it.
|
||||||
****************************************************************************/
|
****************************************************************************/
|
||||||
|
|
||||||
struct timed_event *event_add_timed(struct event_context *event_ctx,
|
static struct tevent_timer *s3_event_add_timer(struct tevent_context *event_ctx,
|
||||||
TALLOC_CTX *mem_ctx,
|
TALLOC_CTX *mem_ctx,
|
||||||
struct timeval when,
|
struct timeval when,
|
||||||
const char *event_name,
|
tevent_timer_handler_t handler,
|
||||||
void (*handler)(struct event_context *event_ctx,
|
void *private_data,
|
||||||
struct timed_event *te,
|
const char *handler_name,
|
||||||
const struct timeval *now,
|
const char *location)
|
||||||
void *private_data),
|
|
||||||
void *private_data)
|
|
||||||
{
|
{
|
||||||
struct timed_event *te;
|
struct tevent_timer *te;
|
||||||
|
|
||||||
te = TALLOC_P(mem_ctx, struct timed_event);
|
te = TALLOC_P(mem_ctx, struct tevent_timer);
|
||||||
if (te == NULL) {
|
if (te == NULL) {
|
||||||
DEBUG(0, ("talloc failed\n"));
|
DEBUG(0, ("talloc failed\n"));
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
te->event_ctx = event_ctx;
|
te->event_ctx = event_ctx;
|
||||||
te->when = when;
|
te->next_event = when;
|
||||||
te->event_name = event_name;
|
|
||||||
te->handler = handler;
|
te->handler = handler;
|
||||||
te->private_data = private_data;
|
te->private_data = private_data;
|
||||||
|
te->handler_name = handler_name;
|
||||||
|
te->location = location;
|
||||||
|
te->additional_data = NULL;
|
||||||
|
|
||||||
add_event_by_time(te);
|
add_event_by_time(te);
|
||||||
|
|
||||||
talloc_set_destructor(te, timed_event_destructor);
|
talloc_set_destructor(te, s3_event_timer_destructor);
|
||||||
|
|
||||||
DEBUG(10, ("Added timed event \"%s\": %lx\n", event_name,
|
DEBUG(10, ("Added timed event \"%s\": %p\n", handler_name, te));
|
||||||
(unsigned long)te));
|
|
||||||
return te;
|
return te;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int fd_event_destructor(struct fd_event *fde)
|
static int s3_event_fd_destructor(struct tevent_fd *fde)
|
||||||
{
|
{
|
||||||
if (fde->event_ctx != NULL) {
|
if (fde->event_ctx != NULL) {
|
||||||
DLIST_REMOVE(fde->event_ctx->fd_events, fde);
|
struct s3_event_context *ev3;
|
||||||
|
ev3 = talloc_get_type(fde->event_ctx->additional_data,
|
||||||
|
struct s3_event_context);
|
||||||
|
DLIST_REMOVE(ev3->fd_events, fde);
|
||||||
|
}
|
||||||
|
if (fde->close_fn) {
|
||||||
|
fde->close_fn(fde->event_ctx, fde, fde->fd, fde->private_data);
|
||||||
|
fde->fd = -1;
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
struct fd_event *event_add_fd(struct event_context *event_ctx,
|
static struct tevent_fd *s3_event_add_fd(struct tevent_context *ev,
|
||||||
TALLOC_CTX *mem_ctx,
|
TALLOC_CTX *mem_ctx,
|
||||||
int fd, uint16_t flags,
|
int fd,
|
||||||
void (*handler)(struct event_context *event_ctx,
|
uint16_t flags,
|
||||||
struct fd_event *event,
|
tevent_fd_handler_t handler,
|
||||||
uint16 flags,
|
void *private_data,
|
||||||
void *private_data),
|
const char *handler_name,
|
||||||
void *private_data)
|
const char *location)
|
||||||
{
|
{
|
||||||
struct fd_event *fde;
|
struct s3_event_context *ev3 = talloc_get_type(ev->additional_data,
|
||||||
|
struct s3_event_context);
|
||||||
|
struct tevent_fd *fde;
|
||||||
|
|
||||||
if (!(fde = TALLOC_P(mem_ctx, struct fd_event))) {
|
if (!(fde = TALLOC_P(mem_ctx, struct tevent_fd))) {
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
fde->event_ctx = event_ctx;
|
fde->event_ctx = ev;
|
||||||
fde->fd = fd;
|
fde->fd = fd;
|
||||||
fde->flags = flags;
|
fde->flags = flags;
|
||||||
fde->handler = handler;
|
fde->handler = handler;
|
||||||
|
fde->close_fn = NULL;
|
||||||
fde->private_data = private_data;
|
fde->private_data = private_data;
|
||||||
|
fde->handler_name = handler_name;
|
||||||
|
fde->location = location;
|
||||||
|
|
||||||
DLIST_ADD(event_ctx->fd_events, fde);
|
DLIST_ADD(ev3->fd_events, fde);
|
||||||
|
|
||||||
talloc_set_destructor(fde, fd_event_destructor);
|
talloc_set_destructor(fde, s3_event_fd_destructor);
|
||||||
return fde;
|
return fde;
|
||||||
}
|
}
|
||||||
|
|
||||||
void event_fd_set_writeable(struct fd_event *fde)
|
void event_fd_set_writeable(struct tevent_fd *fde)
|
||||||
{
|
{
|
||||||
fde->flags |= EVENT_FD_WRITE;
|
TEVENT_FD_WRITEABLE(fde);
|
||||||
}
|
}
|
||||||
|
|
||||||
void event_fd_set_not_writeable(struct fd_event *fde)
|
void event_fd_set_not_writeable(struct tevent_fd *fde)
|
||||||
{
|
{
|
||||||
fde->flags &= ~EVENT_FD_WRITE;
|
TEVENT_FD_NOT_WRITEABLE(fde);
|
||||||
}
|
}
|
||||||
|
|
||||||
void event_fd_set_readable(struct fd_event *fde)
|
void event_fd_set_readable(struct tevent_fd *fde)
|
||||||
{
|
{
|
||||||
fde->flags |= EVENT_FD_READ;
|
TEVENT_FD_READABLE(fde);
|
||||||
}
|
}
|
||||||
|
|
||||||
void event_fd_set_not_readable(struct fd_event *fde)
|
void event_fd_set_not_readable(struct tevent_fd *fde)
|
||||||
{
|
{
|
||||||
fde->flags &= ~EVENT_FD_READ;
|
TEVENT_FD_NOT_READABLE(fde);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Return if there's something in the queue
|
* Return if there's something in the queue
|
||||||
*/
|
*/
|
||||||
|
|
||||||
bool event_add_to_select_args(struct event_context *event_ctx,
|
bool event_add_to_select_args(struct tevent_context *ev,
|
||||||
const struct timeval *now,
|
const struct timeval *now,
|
||||||
fd_set *read_fds, fd_set *write_fds,
|
fd_set *read_fds, fd_set *write_fds,
|
||||||
struct timeval *timeout, int *maxfd)
|
struct timeval *timeout, int *maxfd)
|
||||||
{
|
{
|
||||||
struct fd_event *fde;
|
struct s3_event_context *ev3 = talloc_get_type(ev->additional_data,
|
||||||
|
struct s3_event_context);
|
||||||
|
struct tevent_fd *fde;
|
||||||
struct timeval diff;
|
struct timeval diff;
|
||||||
bool ret = False;
|
bool ret = false;
|
||||||
|
|
||||||
for (fde = event_ctx->fd_events; fde; fde = fde->next) {
|
for (fde = ev3->fd_events; fde; fde = fde->next) {
|
||||||
if (fde->flags & EVENT_FD_READ) {
|
if (fde->flags & EVENT_FD_READ) {
|
||||||
FD_SET(fde->fd, read_fds);
|
FD_SET(fde->fd, read_fds);
|
||||||
ret = True;
|
ret = true;
|
||||||
}
|
}
|
||||||
if (fde->flags & EVENT_FD_WRITE) {
|
if (fde->flags & EVENT_FD_WRITE) {
|
||||||
FD_SET(fde->fd, write_fds);
|
FD_SET(fde->fd, write_fds);
|
||||||
ret = True;
|
ret = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ((fde->flags & (EVENT_FD_READ|EVENT_FD_WRITE))
|
if ((fde->flags & (EVENT_FD_READ|EVENT_FD_WRITE))
|
||||||
@ -215,61 +195,48 @@ bool event_add_to_select_args(struct event_context *event_ctx,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (event_ctx->timed_events == NULL) {
|
if (ev->timer_events == NULL) {
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
diff = timeval_until(now, &event_ctx->timed_events->when);
|
diff = timeval_until(now, &ev->timer_events->next_event);
|
||||||
*timeout = timeval_min(timeout, &diff);
|
*timeout = timeval_min(timeout, &diff);
|
||||||
|
|
||||||
return True;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool events_pending(struct event_context *event_ctx)
|
bool run_events(struct tevent_context *ev,
|
||||||
{
|
|
||||||
struct fd_event *fde;
|
|
||||||
|
|
||||||
if (event_ctx->timed_events != NULL) {
|
|
||||||
return True;
|
|
||||||
}
|
|
||||||
for (fde = event_ctx->fd_events; fde; fde = fde->next) {
|
|
||||||
if (fde->flags & (EVENT_FD_READ|EVENT_FD_WRITE)) {
|
|
||||||
return True;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return False;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool run_events(struct event_context *event_ctx,
|
|
||||||
int selrtn, fd_set *read_fds, fd_set *write_fds)
|
int selrtn, fd_set *read_fds, fd_set *write_fds)
|
||||||
{
|
{
|
||||||
bool fired = False;
|
struct s3_event_context *ev3 = talloc_get_type(ev->additional_data,
|
||||||
struct fd_event *fde, *next;
|
struct s3_event_context);
|
||||||
|
bool fired = false;
|
||||||
|
struct tevent_fd *fde, *next;
|
||||||
|
|
||||||
/* Run all events that are pending, not just one (as we
|
/* Run all events that are pending, not just one (as we
|
||||||
did previously. */
|
did previously. */
|
||||||
|
|
||||||
while (event_ctx->timed_events) {
|
while (ev->timer_events) {
|
||||||
struct timeval now;
|
struct timeval now;
|
||||||
GetTimeOfDay(&now);
|
GetTimeOfDay(&now);
|
||||||
|
|
||||||
if (timeval_compare(
|
if (timeval_compare(
|
||||||
&now, &event_ctx->timed_events->when) < 0) {
|
&now, &ev->timer_events->next_event) < 0) {
|
||||||
/* Nothing to do yet */
|
/* Nothing to do yet */
|
||||||
DEBUG(11, ("run_events: Nothing to do\n"));
|
DEBUG(11, ("run_events: Nothing to do\n"));
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
DEBUG(10, ("Running event \"%s\" %lx\n",
|
DEBUG(10, ("Running event \"%s\" %p\n",
|
||||||
event_ctx->timed_events->event_name,
|
ev->timer_events->handler_name,
|
||||||
(unsigned long)event_ctx->timed_events));
|
ev->timer_events));
|
||||||
|
|
||||||
event_ctx->timed_events->handler(
|
ev->timer_events->handler(
|
||||||
event_ctx,
|
ev,
|
||||||
event_ctx->timed_events, &now,
|
ev->timer_events, now,
|
||||||
event_ctx->timed_events->private_data);
|
ev->timer_events->private_data);
|
||||||
|
|
||||||
fired = True;
|
fired = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (fired) {
|
if (fired) {
|
||||||
@ -277,7 +244,7 @@ bool run_events(struct event_context *event_ctx,
|
|||||||
* We might have changed the socket status during the timed
|
* We might have changed the socket status during the timed
|
||||||
* events, return to run select again.
|
* events, return to run select again.
|
||||||
*/
|
*/
|
||||||
return True;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (selrtn == 0) {
|
if (selrtn == 0) {
|
||||||
@ -287,7 +254,7 @@ bool run_events(struct event_context *event_ctx,
|
|||||||
return fired;
|
return fired;
|
||||||
}
|
}
|
||||||
|
|
||||||
for (fde = event_ctx->fd_events; fde; fde = next) {
|
for (fde = ev3->fd_events; fde; fde = next) {
|
||||||
uint16 flags = 0;
|
uint16 flags = 0;
|
||||||
|
|
||||||
next = fde->next;
|
next = fde->next;
|
||||||
@ -295,8 +262,8 @@ bool run_events(struct event_context *event_ctx,
|
|||||||
if (FD_ISSET(fde->fd, write_fds)) flags |= EVENT_FD_WRITE;
|
if (FD_ISSET(fde->fd, write_fds)) flags |= EVENT_FD_WRITE;
|
||||||
|
|
||||||
if (flags & fde->flags) {
|
if (flags & fde->flags) {
|
||||||
fde->handler(event_ctx, fde, flags, fde->private_data);
|
fde->handler(ev, fde, flags, fde->private_data);
|
||||||
fired = True;
|
fired = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -304,17 +271,17 @@ bool run_events(struct event_context *event_ctx,
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
struct timeval *get_timed_events_timeout(struct event_context *event_ctx,
|
struct timeval *get_timed_events_timeout(struct tevent_context *ev,
|
||||||
struct timeval *to_ret)
|
struct timeval *to_ret)
|
||||||
{
|
{
|
||||||
struct timeval now;
|
struct timeval now;
|
||||||
|
|
||||||
if (event_ctx->timed_events == NULL) {
|
if (ev->timer_events == NULL) {
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
now = timeval_current();
|
now = timeval_current();
|
||||||
*to_ret = timeval_until(&now, &event_ctx->timed_events->when);
|
*to_ret = timeval_until(&now, &ev->timer_events->next_event);
|
||||||
|
|
||||||
DEBUG(10, ("timed_events_timeout: %d/%d\n", (int)to_ret->tv_sec,
|
DEBUG(10, ("timed_events_timeout: %d/%d\n", (int)to_ret->tv_sec,
|
||||||
(int)to_ret->tv_usec));
|
(int)to_ret->tv_usec));
|
||||||
@ -322,7 +289,7 @@ struct timeval *get_timed_events_timeout(struct event_context *event_ctx,
|
|||||||
return to_ret;
|
return to_ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
int event_loop_once(struct event_context *ev)
|
static int s3_event_loop_once(struct tevent_context *ev)
|
||||||
{
|
{
|
||||||
struct timeval now, to;
|
struct timeval now, to;
|
||||||
fd_set r_fds, w_fds;
|
fd_set r_fds, w_fds;
|
||||||
@ -356,71 +323,60 @@ int event_loop_once(struct event_context *ev)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int event_context_destructor(struct event_context *ev)
|
static int s3_event_loop_wait(struct tevent_context *ev)
|
||||||
{
|
{
|
||||||
while (ev->fd_events != NULL) {
|
int ret = 0;
|
||||||
ev->fd_events->event_ctx = NULL;
|
|
||||||
DLIST_REMOVE(ev->fd_events, ev->fd_events);
|
while (ret == 0) {
|
||||||
|
ret = s3_event_loop_once(ev);
|
||||||
}
|
}
|
||||||
while (ev->timed_events != NULL) {
|
|
||||||
ev->timed_events->event_ctx = NULL;
|
return ret;
|
||||||
DLIST_REMOVE(ev->timed_events, ev->timed_events);
|
}
|
||||||
|
|
||||||
|
static int s3_event_context_destructor(struct tevent_context *ev)
|
||||||
|
{
|
||||||
|
struct s3_event_context *ev3 = talloc_get_type(ev->additional_data,
|
||||||
|
struct s3_event_context);
|
||||||
|
while (ev3->fd_events != NULL) {
|
||||||
|
ev3->fd_events->event_ctx = NULL;
|
||||||
|
DLIST_REMOVE(ev3->fd_events, ev3->fd_events);
|
||||||
|
}
|
||||||
|
while (ev->timer_events != NULL) {
|
||||||
|
ev->timer_events->event_ctx = NULL;
|
||||||
|
DLIST_REMOVE(ev->timer_events, ev3->ev->timer_events);
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
struct event_context *event_context_init(TALLOC_CTX *mem_ctx)
|
void event_context_reinit(struct tevent_context *ev)
|
||||||
{
|
{
|
||||||
struct event_context *result;
|
s3_event_context_destructor(ev);
|
||||||
|
return;
|
||||||
result = TALLOC_ZERO_P(mem_ctx, struct event_context);
|
|
||||||
if (result == NULL) {
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
talloc_set_destructor(result, event_context_destructor);
|
|
||||||
return result;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
int set_event_dispatch_time(struct event_context *event_ctx,
|
static int s3_event_context_init(struct tevent_context *ev)
|
||||||
const char *event_name, struct timeval when)
|
|
||||||
{
|
{
|
||||||
struct timed_event *te;
|
struct s3_event_context *ev3;
|
||||||
|
|
||||||
for (te = event_ctx->timed_events; te; te = te->next) {
|
ev3 = talloc_zero(ev, struct s3_event_context);
|
||||||
if (strcmp(event_name, te->event_name) == 0) {
|
if (!ev3) return -1;
|
||||||
DLIST_REMOVE(event_ctx->timed_events, te);
|
ev3->ev = ev;
|
||||||
te->when = when;
|
|
||||||
add_event_by_time(te);
|
ev->additional_data = ev3;
|
||||||
return 1;
|
talloc_set_destructor(ev, s3_event_context_destructor);
|
||||||
}
|
|
||||||
}
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Returns 1 if event was found and cancelled, 0 otherwise. */
|
void dump_event_list(struct tevent_context *ev)
|
||||||
|
|
||||||
int cancel_named_event(struct event_context *event_ctx,
|
|
||||||
const char *event_name)
|
|
||||||
{
|
{
|
||||||
struct timed_event *te;
|
struct s3_event_context *ev3 = talloc_get_type(ev->additional_data,
|
||||||
|
struct s3_event_context);
|
||||||
for (te = event_ctx->timed_events; te; te = te->next) {
|
struct tevent_timer *te;
|
||||||
if (strcmp(event_name, te->event_name) == 0) {
|
struct tevent_fd *fe;
|
||||||
TALLOC_FREE(te);
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
void dump_event_list(struct event_context *event_ctx)
|
|
||||||
{
|
|
||||||
struct timed_event *te;
|
|
||||||
struct fd_event *fe;
|
|
||||||
struct timeval evt, now;
|
struct timeval evt, now;
|
||||||
|
|
||||||
if (!event_ctx) {
|
if (!ev) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -428,22 +384,50 @@ void dump_event_list(struct event_context *event_ctx)
|
|||||||
|
|
||||||
DEBUG(10,("dump_event_list:\n"));
|
DEBUG(10,("dump_event_list:\n"));
|
||||||
|
|
||||||
for (te = event_ctx->timed_events; te; te = te->next) {
|
for (te = ev->timer_events; te; te = te->next) {
|
||||||
|
|
||||||
evt = timeval_until(&now, &te->when);
|
evt = timeval_until(&now, &te->next_event);
|
||||||
|
|
||||||
DEBUGADD(10,("Timed Event \"%s\" %lx handled in %d seconds (at %s)\n",
|
DEBUGADD(10,("Timed Event \"%s\" %p handled in %d seconds (at %s)\n",
|
||||||
te->event_name,
|
te->handler_name,
|
||||||
(unsigned long)te,
|
te,
|
||||||
(int)evt.tv_sec,
|
(int)evt.tv_sec,
|
||||||
http_timestring(talloc_tos(), te->when.tv_sec)));
|
http_timestring(talloc_tos(), te->next_event.tv_sec)));
|
||||||
}
|
}
|
||||||
|
|
||||||
for (fe = event_ctx->fd_events; fe; fe = fe->next) {
|
for (fe = ev3->fd_events; fe; fe = fe->next) {
|
||||||
|
|
||||||
DEBUGADD(10,("FD Event %d %lx, flags: 0x%04x\n",
|
DEBUGADD(10,("FD Event %d %p, flags: 0x%04x\n",
|
||||||
fe->fd,
|
fe->fd,
|
||||||
(unsigned long)fe,
|
fe,
|
||||||
fe->flags));
|
fe->flags));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static const struct tevent_ops s3_event_ops = {
|
||||||
|
.context_init = s3_event_context_init,
|
||||||
|
.add_fd = s3_event_add_fd,
|
||||||
|
.set_fd_close_fn= tevent_common_fd_set_close_fn,
|
||||||
|
.get_fd_flags = tevent_common_fd_get_flags,
|
||||||
|
.set_fd_flags = tevent_common_fd_set_flags,
|
||||||
|
.add_timer = s3_event_add_timer,
|
||||||
|
.loop_once = s3_event_loop_once,
|
||||||
|
.loop_wait = s3_event_loop_wait,
|
||||||
|
};
|
||||||
|
|
||||||
|
static bool s3_tevent_init(void)
|
||||||
|
{
|
||||||
|
static bool initialized;
|
||||||
|
if (initialized) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
initialized = tevent_register_backend("s3", &s3_event_ops);
|
||||||
|
tevent_set_default_backend("s3");
|
||||||
|
return initialized;
|
||||||
|
}
|
||||||
|
|
||||||
|
struct tevent_context *s3_tevent_context_init(TALLOC_CTX *mem_ctx)
|
||||||
|
{
|
||||||
|
s3_tevent_init();
|
||||||
|
return tevent_context_init_byname(mem_ctx, "s3");
|
||||||
|
}
|
||||||
|
@ -1014,7 +1014,7 @@ static int smbldap_connect_system(struct smbldap_state *ldap_state, LDAP * ldap_
|
|||||||
|
|
||||||
static void smbldap_idle_fn(struct event_context *event_ctx,
|
static void smbldap_idle_fn(struct event_context *event_ctx,
|
||||||
struct timed_event *te,
|
struct timed_event *te,
|
||||||
const struct timeval *now,
|
struct timeval now,
|
||||||
void *private_data);
|
void *private_data);
|
||||||
|
|
||||||
/**********************************************************************
|
/**********************************************************************
|
||||||
@ -1079,7 +1079,7 @@ static int smbldap_open(struct smbldap_state *ldap_state)
|
|||||||
ldap_state->idle_event = event_add_timed(
|
ldap_state->idle_event = event_add_timed(
|
||||||
ldap_state->event_context, NULL,
|
ldap_state->event_context, NULL,
|
||||||
timeval_current_ofs(SMBLDAP_IDLE_TIME, 0),
|
timeval_current_ofs(SMBLDAP_IDLE_TIME, 0),
|
||||||
"smbldap_idle_fn", smbldap_idle_fn, ldap_state);
|
smbldap_idle_fn, ldap_state);
|
||||||
}
|
}
|
||||||
|
|
||||||
DEBUG(4,("The LDAP server is successfully connected\n"));
|
DEBUG(4,("The LDAP server is successfully connected\n"));
|
||||||
@ -1572,7 +1572,7 @@ int smbldap_search_suffix (struct smbldap_state *ldap_state,
|
|||||||
|
|
||||||
static void smbldap_idle_fn(struct event_context *event_ctx,
|
static void smbldap_idle_fn(struct event_context *event_ctx,
|
||||||
struct timed_event *te,
|
struct timed_event *te,
|
||||||
const struct timeval *now,
|
struct timeval now,
|
||||||
void *private_data)
|
void *private_data)
|
||||||
{
|
{
|
||||||
struct smbldap_state *state = (struct smbldap_state *)private_data;
|
struct smbldap_state *state = (struct smbldap_state *)private_data;
|
||||||
@ -1584,13 +1584,13 @@ static void smbldap_idle_fn(struct event_context *event_ctx,
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ((state->last_use+SMBLDAP_IDLE_TIME) > now->tv_sec) {
|
if ((state->last_use+SMBLDAP_IDLE_TIME) > now.tv_sec) {
|
||||||
DEBUG(10,("ldap connection not idle...\n"));
|
DEBUG(10,("ldap connection not idle...\n"));
|
||||||
|
|
||||||
state->idle_event = event_add_timed(
|
state->idle_event = event_add_timed(
|
||||||
event_ctx, NULL,
|
event_ctx, NULL,
|
||||||
timeval_add(now, SMBLDAP_IDLE_TIME, 0),
|
timeval_add(&now, SMBLDAP_IDLE_TIME, 0),
|
||||||
"smbldap_idle_fn", smbldap_idle_fn,
|
smbldap_idle_fn,
|
||||||
private_data);
|
private_data);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -949,6 +949,7 @@ void become_daemon(bool Fork, bool no_process_group)
|
|||||||
}
|
}
|
||||||
|
|
||||||
bool reinit_after_fork(struct messaging_context *msg_ctx,
|
bool reinit_after_fork(struct messaging_context *msg_ctx,
|
||||||
|
struct event_context *ev_ctx,
|
||||||
bool parent_longlived)
|
bool parent_longlived)
|
||||||
{
|
{
|
||||||
NTSTATUS status;
|
NTSTATUS status;
|
||||||
@ -976,6 +977,8 @@ bool reinit_after_fork(struct messaging_context *msg_ctx,
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
event_context_reinit(ev_ctx);
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -216,7 +216,7 @@ static ssize_t write_fd(int fd, void *ptr, size_t nbytes, int sendfd)
|
|||||||
|
|
||||||
static void aio_child_cleanup(struct event_context *event_ctx,
|
static void aio_child_cleanup(struct event_context *event_ctx,
|
||||||
struct timed_event *te,
|
struct timed_event *te,
|
||||||
const struct timeval *now,
|
struct timeval now,
|
||||||
void *private_data)
|
void *private_data)
|
||||||
{
|
{
|
||||||
struct aio_child_list *list = talloc_get_type_abort(
|
struct aio_child_list *list = talloc_get_type_abort(
|
||||||
@ -252,8 +252,7 @@ static void aio_child_cleanup(struct event_context *event_ctx,
|
|||||||
* Re-schedule the next cleanup round
|
* Re-schedule the next cleanup round
|
||||||
*/
|
*/
|
||||||
list->cleanup_event = event_add_timed(smbd_event_context(), list,
|
list->cleanup_event = event_add_timed(smbd_event_context(), list,
|
||||||
timeval_add(now, 30, 0),
|
timeval_add(&now, 30, 0),
|
||||||
"aio_child_cleanup",
|
|
||||||
aio_child_cleanup, list);
|
aio_child_cleanup, list);
|
||||||
|
|
||||||
}
|
}
|
||||||
@ -284,7 +283,6 @@ static struct aio_child_list *init_aio_children(struct vfs_handle_struct *handle
|
|||||||
if (data->cleanup_event == NULL) {
|
if (data->cleanup_event == NULL) {
|
||||||
data->cleanup_event = event_add_timed(smbd_event_context(), data,
|
data->cleanup_event = event_add_timed(smbd_event_context(), data,
|
||||||
timeval_current_ofs(30, 0),
|
timeval_current_ofs(30, 0),
|
||||||
"aio_child_cleanup",
|
|
||||||
aio_child_cleanup, data);
|
aio_child_cleanup, data);
|
||||||
if (data->cleanup_event == NULL) {
|
if (data->cleanup_event == NULL) {
|
||||||
TALLOC_FREE(data);
|
TALLOC_FREE(data);
|
||||||
|
@ -164,7 +164,8 @@ void start_async_dns(void)
|
|||||||
CatchSignal(SIGHUP, SIG_IGN);
|
CatchSignal(SIGHUP, SIG_IGN);
|
||||||
CatchSignal(SIGTERM, SIGNAL_CAST sig_term );
|
CatchSignal(SIGTERM, SIGNAL_CAST sig_term );
|
||||||
|
|
||||||
if (!reinit_after_fork(nmbd_messaging_context(), true)) {
|
if (!reinit_after_fork(nmbd_messaging_context(),
|
||||||
|
nmbd_event_context(), true)) {
|
||||||
DEBUG(0,("reinit_after_fork() failed\n"));
|
DEBUG(0,("reinit_after_fork() failed\n"));
|
||||||
smb_panic("reinit_after_fork() failed");
|
smb_panic("reinit_after_fork() failed");
|
||||||
}
|
}
|
||||||
|
@ -911,7 +911,8 @@ static bool open_sockets(bool isdaemon, int port)
|
|||||||
|
|
||||||
pidfile_create("nmbd");
|
pidfile_create("nmbd");
|
||||||
|
|
||||||
if (!reinit_after_fork(nmbd_messaging_context(), false)) {
|
if (!reinit_after_fork(nmbd_messaging_context(),
|
||||||
|
nmbd_event_context(), false)) {
|
||||||
DEBUG(0,("reinit_after_fork() failed\n"));
|
DEBUG(0,("reinit_after_fork() failed\n"));
|
||||||
exit(1);
|
exit(1);
|
||||||
}
|
}
|
||||||
|
@ -52,7 +52,7 @@ static bool delay_logon(const char *peer_name, const char *peer_addr)
|
|||||||
|
|
||||||
static void delayed_init_logon_handler(struct event_context *event_ctx,
|
static void delayed_init_logon_handler(struct event_context *event_ctx,
|
||||||
struct timed_event *te,
|
struct timed_event *te,
|
||||||
const struct timeval *now,
|
struct timeval now,
|
||||||
void *private_data)
|
void *private_data)
|
||||||
{
|
{
|
||||||
struct packet_struct *p = (struct packet_struct *)private_data;
|
struct packet_struct *p = (struct packet_struct *)private_data;
|
||||||
@ -657,7 +657,6 @@ reporting %s domain %s 0x%x ntversion=%x lm_nt token=%x lm_20 token=%x\n",
|
|||||||
event_add_timed(nmbd_event_context(),
|
event_add_timed(nmbd_event_context(),
|
||||||
NULL,
|
NULL,
|
||||||
when,
|
when,
|
||||||
"delayed_init_logon",
|
|
||||||
delayed_init_logon_handler,
|
delayed_init_logon_handler,
|
||||||
p);
|
p);
|
||||||
} else {
|
} else {
|
||||||
|
@ -221,7 +221,7 @@ void print_notify_send_messages(struct messaging_context *msg_ctx,
|
|||||||
|
|
||||||
static void print_notify_event_send_messages(struct event_context *event_ctx,
|
static void print_notify_event_send_messages(struct event_context *event_ctx,
|
||||||
struct timed_event *te,
|
struct timed_event *te,
|
||||||
const struct timeval *now,
|
struct timeval now,
|
||||||
void *private_data)
|
void *private_data)
|
||||||
{
|
{
|
||||||
/* Remove this timed event handler. */
|
/* Remove this timed event handler. */
|
||||||
@ -326,7 +326,6 @@ to notify_queue_head\n", msg->type, msg->field, msg->printer));
|
|||||||
/* Add an event for 1 second's time to send this queue. */
|
/* Add an event for 1 second's time to send this queue. */
|
||||||
notify_event = event_add_timed(smbd_event_context(), NULL,
|
notify_event = event_add_timed(smbd_event_context(), NULL,
|
||||||
timeval_current_ofs(1,0),
|
timeval_current_ofs(1,0),
|
||||||
"print_notify",
|
|
||||||
print_notify_event_send_messages, NULL);
|
print_notify_event_send_messages, NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -425,7 +425,8 @@ static bool cups_pcap_load_async(int *pfd)
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* Child. */
|
/* Child. */
|
||||||
if (!reinit_after_fork(smbd_messaging_context(), true)) {
|
if (!reinit_after_fork(smbd_messaging_context(),
|
||||||
|
smbd_event_context(), true)) {
|
||||||
DEBUG(0,("cups_pcap_load_async: reinit_after_fork() failed\n"));
|
DEBUG(0,("cups_pcap_load_async: reinit_after_fork() failed\n"));
|
||||||
smb_panic("cups_pcap_load_async: reinit_after_fork() failed");
|
smb_panic("cups_pcap_load_async: reinit_after_fork() failed");
|
||||||
}
|
}
|
||||||
|
@ -1421,7 +1421,8 @@ void start_background_queue(void)
|
|||||||
close(pause_pipe[0]);
|
close(pause_pipe[0]);
|
||||||
pause_pipe[0] = -1;
|
pause_pipe[0] = -1;
|
||||||
|
|
||||||
if (!reinit_after_fork(smbd_messaging_context(), true)) {
|
if (!reinit_after_fork(smbd_messaging_context(),
|
||||||
|
smbd_event_context(), true)) {
|
||||||
DEBUG(0,("reinit_after_fork() failed\n"));
|
DEBUG(0,("reinit_after_fork() failed\n"));
|
||||||
smb_panic("reinit_after_fork() failed");
|
smb_panic("reinit_after_fork() failed");
|
||||||
}
|
}
|
||||||
|
@ -457,7 +457,7 @@ static void free_samr_info(void *ptr)
|
|||||||
|
|
||||||
static void disp_info_cache_idle_timeout_handler(struct event_context *ev_ctx,
|
static void disp_info_cache_idle_timeout_handler(struct event_context *ev_ctx,
|
||||||
struct timed_event *te,
|
struct timed_event *te,
|
||||||
const struct timeval *now,
|
struct timeval now,
|
||||||
void *private_data)
|
void *private_data)
|
||||||
{
|
{
|
||||||
DISP_INFO *disp_info = (DISP_INFO *)private_data;
|
DISP_INFO *disp_info = (DISP_INFO *)private_data;
|
||||||
@ -486,7 +486,6 @@ static void set_disp_info_cache_timeout(DISP_INFO *disp_info, time_t secs_fromno
|
|||||||
disp_info->cache_timeout_event = event_add_timed(
|
disp_info->cache_timeout_event = event_add_timed(
|
||||||
smbd_event_context(), NULL,
|
smbd_event_context(), NULL,
|
||||||
timeval_current_ofs(secs_fromnow, 0),
|
timeval_current_ofs(secs_fromnow, 0),
|
||||||
"disp_info_cache_idle_timeout_handler",
|
|
||||||
disp_info_cache_idle_timeout_handler, (void *)disp_info);
|
disp_info_cache_idle_timeout_handler, (void *)disp_info);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -68,7 +68,7 @@ static void process_blocking_lock_queue(void);
|
|||||||
|
|
||||||
static void brl_timeout_fn(struct event_context *event_ctx,
|
static void brl_timeout_fn(struct event_context *event_ctx,
|
||||||
struct timed_event *te,
|
struct timed_event *te,
|
||||||
const struct timeval *now,
|
struct timeval now,
|
||||||
void *private_data)
|
void *private_data)
|
||||||
{
|
{
|
||||||
SMB_ASSERT(brl_timeout == te);
|
SMB_ASSERT(brl_timeout == te);
|
||||||
@ -123,7 +123,7 @@ static bool recalc_brl_timeout(void)
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (!(brl_timeout = event_add_timed(smbd_event_context(), NULL,
|
if (!(brl_timeout = event_add_timed(smbd_event_context(), NULL,
|
||||||
next_timeout, "brl_timeout",
|
next_timeout,
|
||||||
brl_timeout_fn, NULL))) {
|
brl_timeout_fn, NULL))) {
|
||||||
return False;
|
return False;
|
||||||
}
|
}
|
||||||
|
@ -85,7 +85,6 @@ static void schedule_dns_register_smbd_retry(struct dns_reg_state *dns_state,
|
|||||||
event= event_add_timed(smbd_event_context(),
|
event= event_add_timed(smbd_event_context(),
|
||||||
NULL,
|
NULL,
|
||||||
timeval_current_ofs(DNS_REG_RETRY_INTERVAL, 0),
|
timeval_current_ofs(DNS_REG_RETRY_INTERVAL, 0),
|
||||||
"DNS registration handler",
|
|
||||||
dns_register_smbd_retry,
|
dns_register_smbd_retry,
|
||||||
dns_state);
|
dns_state);
|
||||||
|
|
||||||
|
@ -173,7 +173,7 @@ static int wcp_file_size_change(files_struct *fsp)
|
|||||||
|
|
||||||
static void update_write_time_handler(struct event_context *ctx,
|
static void update_write_time_handler(struct event_context *ctx,
|
||||||
struct timed_event *te,
|
struct timed_event *te,
|
||||||
const struct timeval *now,
|
struct timeval now,
|
||||||
void *private_data)
|
void *private_data)
|
||||||
{
|
{
|
||||||
files_struct *fsp = (files_struct *)private_data;
|
files_struct *fsp = (files_struct *)private_data;
|
||||||
@ -221,7 +221,6 @@ void trigger_write_time_update(struct files_struct *fsp)
|
|||||||
fsp->update_write_time_event =
|
fsp->update_write_time_event =
|
||||||
event_add_timed(smbd_event_context(), NULL,
|
event_add_timed(smbd_event_context(), NULL,
|
||||||
timeval_current_ofs(0, delay),
|
timeval_current_ofs(0, delay),
|
||||||
"update_write_time_handler",
|
|
||||||
update_write_time_handler, fsp);
|
update_write_time_handler, fsp);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -346,7 +346,7 @@ static files_struct *initial_break_processing(struct file_id id, unsigned long f
|
|||||||
|
|
||||||
static void oplock_timeout_handler(struct event_context *ctx,
|
static void oplock_timeout_handler(struct event_context *ctx,
|
||||||
struct timed_event *te,
|
struct timed_event *te,
|
||||||
const struct timeval *now,
|
struct timeval now,
|
||||||
void *private_data)
|
void *private_data)
|
||||||
{
|
{
|
||||||
files_struct *fsp = (files_struct *)private_data;
|
files_struct *fsp = (files_struct *)private_data;
|
||||||
@ -373,7 +373,6 @@ static void add_oplock_timeout_handler(files_struct *fsp)
|
|||||||
fsp->oplock_timeout =
|
fsp->oplock_timeout =
|
||||||
event_add_timed(smbd_event_context(), NULL,
|
event_add_timed(smbd_event_context(), NULL,
|
||||||
timeval_current_ofs(OPLOCK_BREAK_TIMEOUT, 0),
|
timeval_current_ofs(OPLOCK_BREAK_TIMEOUT, 0),
|
||||||
"oplock_timeout_handler",
|
|
||||||
oplock_timeout_handler, fsp);
|
oplock_timeout_handler, fsp);
|
||||||
|
|
||||||
if (fsp->oplock_timeout == NULL) {
|
if (fsp->oplock_timeout == NULL) {
|
||||||
|
@ -583,26 +583,33 @@ struct idle_event {
|
|||||||
void *private_data;
|
void *private_data;
|
||||||
};
|
};
|
||||||
|
|
||||||
static void idle_event_handler(struct event_context *ctx,
|
static void smbd_idle_event_handler(struct event_context *ctx,
|
||||||
struct timed_event *te,
|
struct timed_event *te,
|
||||||
const struct timeval *now,
|
struct timeval now,
|
||||||
void *private_data)
|
void *private_data)
|
||||||
{
|
{
|
||||||
struct idle_event *event =
|
struct idle_event *event =
|
||||||
talloc_get_type_abort(private_data, struct idle_event);
|
talloc_get_type_abort(private_data, struct idle_event);
|
||||||
|
|
||||||
TALLOC_FREE(event->te);
|
TALLOC_FREE(event->te);
|
||||||
|
|
||||||
if (!event->handler(now, event->private_data)) {
|
DEBUG(10,("smbd_idle_event_handler: %s %p called\n",
|
||||||
|
event->name, event->te));
|
||||||
|
|
||||||
|
if (!event->handler(&now, event->private_data)) {
|
||||||
|
DEBUG(10,("smbd_idle_event_handler: %s %p stopped\n",
|
||||||
|
event->name, event->te));
|
||||||
/* Don't repeat, delete ourselves */
|
/* Don't repeat, delete ourselves */
|
||||||
TALLOC_FREE(event);
|
TALLOC_FREE(event);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
DEBUG(10,("smbd_idle_event_handler: %s %p rescheduled\n",
|
||||||
|
event->name, event->te));
|
||||||
|
|
||||||
event->te = event_add_timed(ctx, event,
|
event->te = event_add_timed(ctx, event,
|
||||||
timeval_sum(now, &event->interval),
|
timeval_sum(&now, &event->interval),
|
||||||
event->name,
|
smbd_idle_event_handler, event);
|
||||||
idle_event_handler, event);
|
|
||||||
|
|
||||||
/* We can't do much but fail here. */
|
/* We can't do much but fail here. */
|
||||||
SMB_ASSERT(event->te != NULL);
|
SMB_ASSERT(event->te != NULL);
|
||||||
@ -637,14 +644,14 @@ struct idle_event *event_add_idle(struct event_context *event_ctx,
|
|||||||
|
|
||||||
result->te = event_add_timed(event_ctx, result,
|
result->te = event_add_timed(event_ctx, result,
|
||||||
timeval_sum(&now, &interval),
|
timeval_sum(&now, &interval),
|
||||||
result->name,
|
smbd_idle_event_handler, result);
|
||||||
idle_event_handler, result);
|
|
||||||
if (result->te == NULL) {
|
if (result->te == NULL) {
|
||||||
DEBUG(0, ("event_add_timed failed\n"));
|
DEBUG(0, ("event_add_timed failed\n"));
|
||||||
TALLOC_FREE(result);
|
TALLOC_FREE(result);
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
DEBUG(10,("event_add_idle: %s %p\n", result->name, result->te));
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -753,7 +753,9 @@ static bool open_sockets_smbd(bool is_daemon, bool interactive, const char *smb_
|
|||||||
false);
|
false);
|
||||||
|
|
||||||
if (!reinit_after_fork(
|
if (!reinit_after_fork(
|
||||||
smbd_messaging_context(), true)) {
|
smbd_messaging_context(),
|
||||||
|
smbd_event_context(),
|
||||||
|
true)) {
|
||||||
DEBUG(0,("reinit_after_fork() failed\n"));
|
DEBUG(0,("reinit_after_fork() failed\n"));
|
||||||
smb_panic("reinit_after_fork() failed");
|
smb_panic("reinit_after_fork() failed");
|
||||||
}
|
}
|
||||||
@ -1327,7 +1329,8 @@ extern void build_options(bool screen);
|
|||||||
if (is_daemon)
|
if (is_daemon)
|
||||||
pidfile_create("smbd");
|
pidfile_create("smbd");
|
||||||
|
|
||||||
if (!reinit_after_fork(smbd_messaging_context(), false)) {
|
if (!reinit_after_fork(smbd_messaging_context(),
|
||||||
|
smbd_event_context(), false)) {
|
||||||
DEBUG(0,("reinit_after_fork() failed\n"));
|
DEBUG(0,("reinit_after_fork() failed\n"));
|
||||||
exit(1);
|
exit(1);
|
||||||
}
|
}
|
||||||
|
@ -248,7 +248,7 @@ static int evt_userdata_tostring(lua_State *L) {
|
|||||||
|
|
||||||
static void evt_userdata_sleep_done(struct event_context *event_ctx,
|
static void evt_userdata_sleep_done(struct event_context *event_ctx,
|
||||||
struct timed_event *te,
|
struct timed_event *te,
|
||||||
const struct timeval *now,
|
struct timeval now,
|
||||||
void *priv)
|
void *priv)
|
||||||
{
|
{
|
||||||
struct thread_reference *ref = talloc_get_type_abort(
|
struct thread_reference *ref = talloc_get_type_abort(
|
||||||
@ -279,7 +279,7 @@ static int evt_userdata_sleep(lua_State *L)
|
|||||||
}
|
}
|
||||||
|
|
||||||
te = event_add_timed(p->ev, ref, timeval_current_ofs(0, usecs),
|
te = event_add_timed(p->ev, ref, timeval_current_ofs(0, usecs),
|
||||||
"evt_userdata_sleep", evt_userdata_sleep_done,
|
evt_userdata_sleep_done,
|
||||||
ref);
|
ref);
|
||||||
|
|
||||||
if (te == NULL) {
|
if (te == NULL) {
|
||||||
|
@ -65,9 +65,9 @@ static bool send_message(struct messaging_context *msg_ctx,
|
|||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void timeout_handler(struct event_context *event_ctx,
|
static void smbcontrol_timeout(struct event_context *event_ctx,
|
||||||
struct timed_event *te,
|
struct timed_event *te,
|
||||||
const struct timeval *now,
|
struct timeval now,
|
||||||
void *private_data)
|
void *private_data)
|
||||||
{
|
{
|
||||||
bool *timed_out = (bool *)private_data;
|
bool *timed_out = (bool *)private_data;
|
||||||
@ -85,8 +85,7 @@ static void wait_replies(struct messaging_context *msg_ctx,
|
|||||||
|
|
||||||
if (!(te = event_add_timed(messaging_event_context(msg_ctx), NULL,
|
if (!(te = event_add_timed(messaging_event_context(msg_ctx), NULL,
|
||||||
timeval_current_ofs(timeout, 0),
|
timeval_current_ofs(timeout, 0),
|
||||||
"smbcontrol_timeout",
|
smbcontrol_timeout, (void *)&timed_out))) {
|
||||||
timeout_handler, (void *)&timed_out))) {
|
|
||||||
DEBUG(0, ("event_add_timed failed\n"));
|
DEBUG(0, ("event_add_timed failed\n"));
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -415,16 +415,16 @@ static void process_request(struct winbindd_cli_state *state)
|
|||||||
|
|
||||||
/*
|
/*
|
||||||
* A list of file descriptors being monitored by select in the main processing
|
* A list of file descriptors being monitored by select in the main processing
|
||||||
* loop. fd_event->handler is called whenever the socket is readable/writable.
|
* loop. winbindd_fd_event->handler is called whenever the socket is readable/writable.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
static struct fd_event *fd_events = NULL;
|
static struct winbindd_fd_event *fd_events = NULL;
|
||||||
|
|
||||||
void add_fd_event(struct fd_event *ev)
|
void add_fd_event(struct winbindd_fd_event *ev)
|
||||||
{
|
{
|
||||||
struct fd_event *match;
|
struct winbindd_fd_event *match;
|
||||||
|
|
||||||
/* only add unique fd_event structs */
|
/* only add unique winbindd_fd_event structs */
|
||||||
|
|
||||||
for (match=fd_events; match; match=match->next ) {
|
for (match=fd_events; match; match=match->next ) {
|
||||||
#ifdef DEVELOPER
|
#ifdef DEVELOPER
|
||||||
@ -438,17 +438,17 @@ void add_fd_event(struct fd_event *ev)
|
|||||||
DLIST_ADD(fd_events, ev);
|
DLIST_ADD(fd_events, ev);
|
||||||
}
|
}
|
||||||
|
|
||||||
void remove_fd_event(struct fd_event *ev)
|
void remove_fd_event(struct winbindd_fd_event *ev)
|
||||||
{
|
{
|
||||||
DLIST_REMOVE(fd_events, ev);
|
DLIST_REMOVE(fd_events, ev);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Handler for fd_events to complete a read/write request, set up by
|
* Handler for winbindd_fd_events to complete a read/write request, set up by
|
||||||
* setup_async_read/setup_async_write.
|
* setup_async_read/setup_async_write.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
static void rw_callback(struct fd_event *event, int flags)
|
static void rw_callback(struct winbindd_fd_event *event, int flags)
|
||||||
{
|
{
|
||||||
size_t todo;
|
size_t todo;
|
||||||
ssize_t done = 0;
|
ssize_t done = 0;
|
||||||
@ -489,11 +489,11 @@ static void rw_callback(struct fd_event *event, int flags)
|
|||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Request an async read/write on a fd_event structure. (*finished) is called
|
* Request an async read/write on a winbindd_fd_event structure. (*finished) is called
|
||||||
* when the request is completed or an error had occurred.
|
* when the request is completed or an error had occurred.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
void setup_async_read(struct fd_event *event, void *data, size_t length,
|
void setup_async_read(struct winbindd_fd_event *event, void *data, size_t length,
|
||||||
void (*finished)(void *private_data, bool success),
|
void (*finished)(void *private_data, bool success),
|
||||||
void *private_data)
|
void *private_data)
|
||||||
{
|
{
|
||||||
@ -507,7 +507,7 @@ void setup_async_read(struct fd_event *event, void *data, size_t length,
|
|||||||
event->flags = EVENT_FD_READ;
|
event->flags = EVENT_FD_READ;
|
||||||
}
|
}
|
||||||
|
|
||||||
void setup_async_write(struct fd_event *event, void *data, size_t length,
|
void setup_async_write(struct winbindd_fd_event *event, void *data, size_t length,
|
||||||
void (*finished)(void *private_data, bool success),
|
void (*finished)(void *private_data, bool success),
|
||||||
void *private_data)
|
void *private_data)
|
||||||
{
|
{
|
||||||
@ -826,7 +826,7 @@ void winbind_check_sigterm(bool is_parent)
|
|||||||
static void process_loop(void)
|
static void process_loop(void)
|
||||||
{
|
{
|
||||||
struct winbindd_cli_state *state;
|
struct winbindd_cli_state *state;
|
||||||
struct fd_event *ev;
|
struct winbindd_fd_event *ev;
|
||||||
fd_set r_fds, w_fds;
|
fd_set r_fds, w_fds;
|
||||||
int maxfd, listen_sock, listen_priv_sock, selret;
|
int maxfd, listen_sock, listen_priv_sock, selret;
|
||||||
struct timeval timeout, ev_timeout;
|
struct timeval timeout, ev_timeout;
|
||||||
@ -865,6 +865,13 @@ static void process_loop(void)
|
|||||||
timeout.tv_usec = 0;
|
timeout.tv_usec = 0;
|
||||||
|
|
||||||
/* Check for any event timeouts. */
|
/* Check for any event timeouts. */
|
||||||
|
{
|
||||||
|
struct timeval now;
|
||||||
|
GetTimeOfDay(&now);
|
||||||
|
|
||||||
|
event_add_to_select_args(winbind_event_context(), &now,
|
||||||
|
&r_fds, &w_fds, &ev_timeout, &maxfd);
|
||||||
|
}
|
||||||
if (get_timed_events_timeout(winbind_event_context(), &ev_timeout)) {
|
if (get_timed_events_timeout(winbind_event_context(), &ev_timeout)) {
|
||||||
timeout = timeval_min(&timeout, &ev_timeout);
|
timeout = timeval_min(&timeout, &ev_timeout);
|
||||||
}
|
}
|
||||||
@ -918,9 +925,11 @@ static void process_loop(void)
|
|||||||
|
|
||||||
/* selret > 0 */
|
/* selret > 0 */
|
||||||
|
|
||||||
|
run_events(winbind_event_context(), selret, &r_fds, &w_fds);
|
||||||
|
|
||||||
ev = fd_events;
|
ev = fd_events;
|
||||||
while (ev != NULL) {
|
while (ev != NULL) {
|
||||||
struct fd_event *next = ev->next;
|
struct winbindd_fd_event *next = ev->next;
|
||||||
int flags = 0;
|
int flags = 0;
|
||||||
if (FD_ISSET(ev->fd, &r_fds))
|
if (FD_ISSET(ev->fd, &r_fds))
|
||||||
flags |= EVENT_FD_READ;
|
flags |= EVENT_FD_READ;
|
||||||
@ -1191,7 +1200,8 @@ int main(int argc, char **argv, char **envp)
|
|||||||
|
|
||||||
TimeInit();
|
TimeInit();
|
||||||
|
|
||||||
if (!reinit_after_fork(winbind_messaging_context(), false)) {
|
if (!reinit_after_fork(winbind_messaging_context(),
|
||||||
|
winbind_event_context(), false)) {
|
||||||
DEBUG(0,("reinit_after_fork() failed\n"));
|
DEBUG(0,("reinit_after_fork() failed\n"));
|
||||||
exit(1);
|
exit(1);
|
||||||
}
|
}
|
||||||
|
@ -39,15 +39,11 @@
|
|||||||
|
|
||||||
#define WB_REPLACE_CHAR '_'
|
#define WB_REPLACE_CHAR '_'
|
||||||
|
|
||||||
/* bits for fd_event.flags */
|
struct winbindd_fd_event {
|
||||||
#define EVENT_FD_READ 1
|
struct winbindd_fd_event *next, *prev;
|
||||||
#define EVENT_FD_WRITE 2
|
|
||||||
|
|
||||||
struct fd_event {
|
|
||||||
struct fd_event *next, *prev;
|
|
||||||
int fd;
|
int fd;
|
||||||
int flags; /* see EVENT_FD_* flags */
|
int flags; /* see EVENT_FD_* flags */
|
||||||
void (*handler)(struct fd_event *fde, int flags);
|
void (*handler)(struct winbindd_fd_event *fde, int flags);
|
||||||
void *data;
|
void *data;
|
||||||
size_t length, done;
|
size_t length, done;
|
||||||
void (*finished)(void *private_data, bool success);
|
void (*finished)(void *private_data, bool success);
|
||||||
@ -65,7 +61,7 @@ struct sid_ctr {
|
|||||||
struct winbindd_cli_state {
|
struct winbindd_cli_state {
|
||||||
struct winbindd_cli_state *prev, *next; /* Linked list pointers */
|
struct winbindd_cli_state *prev, *next; /* Linked list pointers */
|
||||||
int sock; /* Open socket from client */
|
int sock; /* Open socket from client */
|
||||||
struct fd_event fd_event;
|
struct winbindd_fd_event fd_event;
|
||||||
pid_t pid; /* pid of client */
|
pid_t pid; /* pid of client */
|
||||||
bool finished; /* Can delete from list */
|
bool finished; /* Can delete from list */
|
||||||
bool write_extra_data; /* Write extra_data field */
|
bool write_extra_data; /* Write extra_data field */
|
||||||
@ -151,7 +147,7 @@ struct winbindd_child {
|
|||||||
struct winbindd_domain *domain;
|
struct winbindd_domain *domain;
|
||||||
char *logfilename;
|
char *logfilename;
|
||||||
|
|
||||||
struct fd_event event;
|
struct winbindd_fd_event event;
|
||||||
struct timed_event *lockout_policy_event;
|
struct timed_event *lockout_policy_event;
|
||||||
struct timed_event *machine_password_change_event;
|
struct timed_event *machine_password_change_event;
|
||||||
struct winbindd_async_request *requests;
|
struct winbindd_async_request *requests;
|
||||||
@ -377,7 +373,34 @@ enum ent_type {
|
|||||||
LIST_USERS = 0,
|
LIST_USERS = 0,
|
||||||
LIST_GROUPS,
|
LIST_GROUPS,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
struct WINBINDD_MEMORY_CREDS {
|
||||||
|
struct WINBINDD_MEMORY_CREDS *next, *prev;
|
||||||
|
const char *username; /* lookup key. */
|
||||||
|
uid_t uid;
|
||||||
|
int ref_count;
|
||||||
|
size_t len;
|
||||||
|
uint8_t *nt_hash; /* Base pointer for the following 2 */
|
||||||
|
uint8_t *lm_hash;
|
||||||
|
char *pass;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct WINBINDD_CCACHE_ENTRY {
|
||||||
|
struct WINBINDD_CCACHE_ENTRY *next, *prev;
|
||||||
|
const char *principal_name;
|
||||||
|
const char *ccname;
|
||||||
|
const char *service;
|
||||||
|
const char *username;
|
||||||
|
const char *realm;
|
||||||
|
struct WINBINDD_MEMORY_CREDS *cred_ptr;
|
||||||
|
int ref_count;
|
||||||
|
uid_t uid;
|
||||||
|
time_t create_time;
|
||||||
|
time_t renew_until;
|
||||||
|
time_t refresh_time;
|
||||||
|
struct timed_event *event;
|
||||||
|
};
|
||||||
|
|
||||||
#include "winbindd/winbindd_proto.h"
|
#include "winbindd/winbindd_proto.h"
|
||||||
|
|
||||||
#define WINBINDD_ESTABLISH_LOOP 30
|
#define WINBINDD_ESTABLISH_LOOP 30
|
||||||
|
@ -212,7 +212,8 @@ static bool fork_child_dc_connect(struct winbindd_domain *domain)
|
|||||||
|
|
||||||
/* Leave messages blocked - we will never process one. */
|
/* Leave messages blocked - we will never process one. */
|
||||||
|
|
||||||
if (!reinit_after_fork(winbind_messaging_context(), true)) {
|
if (!reinit_after_fork(winbind_messaging_context(),
|
||||||
|
winbind_event_context(), true)) {
|
||||||
DEBUG(0,("reinit_after_fork() failed\n"));
|
DEBUG(0,("reinit_after_fork() failed\n"));
|
||||||
messaging_send_buf(winbind_messaging_context(),
|
messaging_send_buf(winbind_messaging_context(),
|
||||||
pid_to_procid(parent_pid),
|
pid_to_procid(parent_pid),
|
||||||
@ -271,7 +272,7 @@ static bool fork_child_dc_connect(struct winbindd_domain *domain)
|
|||||||
|
|
||||||
static void check_domain_online_handler(struct event_context *ctx,
|
static void check_domain_online_handler(struct event_context *ctx,
|
||||||
struct timed_event *te,
|
struct timed_event *te,
|
||||||
const struct timeval *now,
|
struct timeval now,
|
||||||
void *private_data)
|
void *private_data)
|
||||||
{
|
{
|
||||||
struct winbindd_domain *domain =
|
struct winbindd_domain *domain =
|
||||||
@ -285,7 +286,7 @@ static void check_domain_online_handler(struct event_context *ctx,
|
|||||||
|
|
||||||
/* Are we still in "startup" mode ? */
|
/* Are we still in "startup" mode ? */
|
||||||
|
|
||||||
if (domain->startup && (now->tv_sec > domain->startup_time + 30)) {
|
if (domain->startup && (now.tv_sec > domain->startup_time + 30)) {
|
||||||
/* No longer in "startup" mode. */
|
/* No longer in "startup" mode. */
|
||||||
DEBUG(10,("check_domain_online_handler: domain %s no longer in 'startup' mode.\n",
|
DEBUG(10,("check_domain_online_handler: domain %s no longer in 'startup' mode.\n",
|
||||||
domain->name ));
|
domain->name ));
|
||||||
@ -366,7 +367,6 @@ void set_domain_offline(struct winbindd_domain *domain)
|
|||||||
domain->check_online_event = event_add_timed(winbind_event_context(),
|
domain->check_online_event = event_add_timed(winbind_event_context(),
|
||||||
NULL,
|
NULL,
|
||||||
timeval_current_ofs(domain->check_online_timeout,0),
|
timeval_current_ofs(domain->check_online_timeout,0),
|
||||||
"check_domain_online_handler",
|
|
||||||
check_domain_online_handler,
|
check_domain_online_handler,
|
||||||
domain);
|
domain);
|
||||||
|
|
||||||
@ -402,8 +402,6 @@ void set_domain_offline(struct winbindd_domain *domain)
|
|||||||
|
|
||||||
static void set_domain_online(struct winbindd_domain *domain)
|
static void set_domain_online(struct winbindd_domain *domain)
|
||||||
{
|
{
|
||||||
struct timeval now;
|
|
||||||
|
|
||||||
DEBUG(10,("set_domain_online: called for domain %s\n",
|
DEBUG(10,("set_domain_online: called for domain %s\n",
|
||||||
domain->name ));
|
domain->name ));
|
||||||
|
|
||||||
@ -422,9 +420,7 @@ static void set_domain_online(struct winbindd_domain *domain)
|
|||||||
winbindd_set_locator_kdc_envs(domain);
|
winbindd_set_locator_kdc_envs(domain);
|
||||||
|
|
||||||
/* If we are waiting to get a krb5 ticket, trigger immediately. */
|
/* If we are waiting to get a krb5 ticket, trigger immediately. */
|
||||||
GetTimeOfDay(&now);
|
ccache_regain_all_now();
|
||||||
set_event_dispatch_time(winbind_event_context(),
|
|
||||||
"krb5_ticket_gain_handler", now);
|
|
||||||
|
|
||||||
/* Ok, we're out of any startup mode now... */
|
/* Ok, we're out of any startup mode now... */
|
||||||
domain->startup = False;
|
domain->startup = False;
|
||||||
@ -497,27 +493,6 @@ void set_domain_online_request(struct winbindd_domain *domain)
|
|||||||
because network manager seems to lie.
|
because network manager seems to lie.
|
||||||
Wait at least 5 seconds. Heuristics suck... */
|
Wait at least 5 seconds. Heuristics suck... */
|
||||||
|
|
||||||
if (!domain->check_online_event) {
|
|
||||||
/* If we've come from being globally offline we
|
|
||||||
don't have a check online event handler set.
|
|
||||||
We need to add one now we're trying to go
|
|
||||||
back online. */
|
|
||||||
|
|
||||||
DEBUG(10,("set_domain_online_request: domain %s was globally offline.\n",
|
|
||||||
domain->name ));
|
|
||||||
|
|
||||||
domain->check_online_event = event_add_timed(winbind_event_context(),
|
|
||||||
NULL,
|
|
||||||
timeval_current_ofs(5, 0),
|
|
||||||
"check_domain_online_handler",
|
|
||||||
check_domain_online_handler,
|
|
||||||
domain);
|
|
||||||
|
|
||||||
/* The above *has* to succeed for winbindd to work. */
|
|
||||||
if (!domain->check_online_event) {
|
|
||||||
smb_panic("set_domain_online_request: failed to add online handler");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
GetTimeOfDay(&tev);
|
GetTimeOfDay(&tev);
|
||||||
|
|
||||||
@ -527,7 +502,28 @@ void set_domain_online_request(struct winbindd_domain *domain)
|
|||||||
|
|
||||||
tev.tv_sec += 5;
|
tev.tv_sec += 5;
|
||||||
|
|
||||||
set_event_dispatch_time(winbind_event_context(), "check_domain_online_handler", tev);
|
if (!domain->check_online_event) {
|
||||||
|
/* If we've come from being globally offline we
|
||||||
|
don't have a check online event handler set.
|
||||||
|
We need to add one now we're trying to go
|
||||||
|
back online. */
|
||||||
|
|
||||||
|
DEBUG(10,("set_domain_online_request: domain %s was globally offline.\n",
|
||||||
|
domain->name ));
|
||||||
|
}
|
||||||
|
|
||||||
|
TALLOC_FREE(domain->check_online_event);
|
||||||
|
|
||||||
|
domain->check_online_event = event_add_timed(winbind_event_context(),
|
||||||
|
NULL,
|
||||||
|
tev,
|
||||||
|
check_domain_online_handler,
|
||||||
|
domain);
|
||||||
|
|
||||||
|
/* The above *has* to succeed for winbindd to work. */
|
||||||
|
if (!domain->check_online_event) {
|
||||||
|
smb_panic("set_domain_online_request: failed to add online handler");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/****************************************************************
|
/****************************************************************
|
||||||
|
@ -34,6 +34,10 @@
|
|||||||
#define MAX_CCACHES 100
|
#define MAX_CCACHES 100
|
||||||
|
|
||||||
static struct WINBINDD_CCACHE_ENTRY *ccache_list;
|
static struct WINBINDD_CCACHE_ENTRY *ccache_list;
|
||||||
|
static void krb5_ticket_gain_handler(struct event_context *,
|
||||||
|
struct timed_event *,
|
||||||
|
struct timeval,
|
||||||
|
void *);
|
||||||
|
|
||||||
/* The Krb5 ticket refresh handler should be scheduled
|
/* The Krb5 ticket refresh handler should be scheduled
|
||||||
at one-half of the period from now till the tkt
|
at one-half of the period from now till the tkt
|
||||||
@ -71,13 +75,27 @@ static int ccache_entry_count(void)
|
|||||||
return i;
|
return i;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void ccache_remove_all_after_fork(void)
|
||||||
|
{
|
||||||
|
struct WINBINDD_CCACHE_ENTRY *cur, *next;
|
||||||
|
|
||||||
|
for (cur = ccache_list; cur; cur = next) {
|
||||||
|
next = cur->next;
|
||||||
|
DLIST_REMOVE(ccache_list, cur);
|
||||||
|
TALLOC_FREE(cur->event);
|
||||||
|
TALLOC_FREE(cur);
|
||||||
|
}
|
||||||
|
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
/****************************************************************
|
/****************************************************************
|
||||||
Do the work of refreshing the ticket.
|
Do the work of refreshing the ticket.
|
||||||
****************************************************************/
|
****************************************************************/
|
||||||
|
|
||||||
static void krb5_ticket_refresh_handler(struct event_context *event_ctx,
|
static void krb5_ticket_refresh_handler(struct event_context *event_ctx,
|
||||||
struct timed_event *te,
|
struct timed_event *te,
|
||||||
const struct timeval *now,
|
struct timeval now,
|
||||||
void *private_data)
|
void *private_data)
|
||||||
{
|
{
|
||||||
struct WINBINDD_CCACHE_ENTRY *entry =
|
struct WINBINDD_CCACHE_ENTRY *entry =
|
||||||
@ -85,6 +103,7 @@ static void krb5_ticket_refresh_handler(struct event_context *event_ctx,
|
|||||||
#ifdef HAVE_KRB5
|
#ifdef HAVE_KRB5
|
||||||
int ret;
|
int ret;
|
||||||
time_t new_start;
|
time_t new_start;
|
||||||
|
time_t expire_time = 0;
|
||||||
struct WINBINDD_MEMORY_CREDS *cred_ptr = entry->cred_ptr;
|
struct WINBINDD_MEMORY_CREDS *cred_ptr = entry->cred_ptr;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@ -97,44 +116,83 @@ static void krb5_ticket_refresh_handler(struct event_context *event_ctx,
|
|||||||
#ifdef HAVE_KRB5
|
#ifdef HAVE_KRB5
|
||||||
|
|
||||||
/* Kinit again if we have the user password and we can't renew the old
|
/* Kinit again if we have the user password and we can't renew the old
|
||||||
* tgt anymore */
|
* tgt anymore
|
||||||
|
* NB
|
||||||
|
* This happens when machine are put to sleep for a very long time. */
|
||||||
|
|
||||||
if ((entry->renew_until < time(NULL)) && cred_ptr && cred_ptr->pass) {
|
if (entry->renew_until < time(NULL)) {
|
||||||
|
rekinit:
|
||||||
|
if (cred_ptr && cred_ptr->pass) {
|
||||||
|
|
||||||
set_effective_uid(entry->uid);
|
set_effective_uid(entry->uid);
|
||||||
|
|
||||||
ret = kerberos_kinit_password_ext(entry->principal_name,
|
ret = kerberos_kinit_password_ext(entry->principal_name,
|
||||||
cred_ptr->pass,
|
cred_ptr->pass,
|
||||||
0, /* hm, can we do time correction here ? */
|
0, /* hm, can we do time correction here ? */
|
||||||
&entry->refresh_time,
|
&entry->refresh_time,
|
||||||
&entry->renew_until,
|
&entry->renew_until,
|
||||||
entry->ccname,
|
entry->ccname,
|
||||||
False, /* no PAC required anymore */
|
False, /* no PAC required anymore */
|
||||||
True,
|
True,
|
||||||
WINBINDD_PAM_AUTH_KRB5_RENEW_TIME,
|
WINBINDD_PAM_AUTH_KRB5_RENEW_TIME,
|
||||||
NULL);
|
NULL);
|
||||||
gain_root_privilege();
|
gain_root_privilege();
|
||||||
|
|
||||||
if (ret) {
|
if (ret) {
|
||||||
DEBUG(3,("krb5_ticket_refresh_handler: "
|
DEBUG(3,("krb5_ticket_refresh_handler: "
|
||||||
"could not re-kinit: %s\n",
|
"could not re-kinit: %s\n",
|
||||||
error_message(ret)));
|
error_message(ret)));
|
||||||
TALLOC_FREE(entry->event);
|
/* destroy the ticket because we cannot rekinit
|
||||||
return;
|
* it, ignore error here */
|
||||||
}
|
ads_kdestroy(entry->ccname);
|
||||||
|
|
||||||
DEBUG(10,("krb5_ticket_refresh_handler: successful re-kinit "
|
/* Don't break the ticket refresh chain: retry
|
||||||
"for: %s in ccache: %s\n",
|
* refreshing ticket sometime later when KDC is
|
||||||
entry->principal_name, entry->ccname));
|
* unreachable -- BoYang
|
||||||
|
* */
|
||||||
|
|
||||||
|
if ((ret == KRB5_KDC_UNREACH)
|
||||||
|
|| (ret == KRB5_REALM_CANT_RESOLVE)) {
|
||||||
|
#if defined(DEBUG_KRB5_TKT_RENEWAL)
|
||||||
|
new_start = time(NULL) + 30;
|
||||||
|
#else
|
||||||
|
new_start = time(NULL) +
|
||||||
|
MAX(30, lp_winbind_cache_time());
|
||||||
|
#endif
|
||||||
|
/* try to regain ticket here */
|
||||||
|
entry->event = event_add_timed(winbind_event_context(),
|
||||||
|
entry,
|
||||||
|
timeval_set(new_start, 0),
|
||||||
|
krb5_ticket_gain_handler,
|
||||||
|
entry);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
TALLOC_FREE(entry->event);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
DEBUG(10,("krb5_ticket_refresh_handler: successful re-kinit "
|
||||||
|
"for: %s in ccache: %s\n",
|
||||||
|
entry->principal_name, entry->ccname));
|
||||||
|
|
||||||
#if defined(DEBUG_KRB5_TKT_RENEWAL)
|
#if defined(DEBUG_KRB5_TKT_RENEWAL)
|
||||||
new_start = time(NULL) + 30;
|
new_start = time(NULL) + 30;
|
||||||
#else
|
#else
|
||||||
/* The tkt should be refreshed at one-half the period
|
/* The tkt should be refreshed at one-half the period
|
||||||
from now to the expiration time */
|
from now to the expiration time */
|
||||||
new_start = KRB5_EVENT_REFRESH_TIME(entry->refresh_time);
|
expire_time = entry->refresh_time;
|
||||||
|
new_start = KRB5_EVENT_REFRESH_TIME(entry->refresh_time);
|
||||||
#endif
|
#endif
|
||||||
goto done;
|
goto done;
|
||||||
|
} else {
|
||||||
|
/* can this happen?
|
||||||
|
* No cached credentials
|
||||||
|
* destroy ticket and refresh chain
|
||||||
|
* */
|
||||||
|
ads_kdestroy(entry->ccname);
|
||||||
|
TALLOC_FREE(entry->event);
|
||||||
|
return;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
set_effective_uid(entry->uid);
|
set_effective_uid(entry->uid);
|
||||||
@ -146,6 +204,7 @@ static void krb5_ticket_refresh_handler(struct event_context *event_ctx,
|
|||||||
#if defined(DEBUG_KRB5_TKT_RENEWAL)
|
#if defined(DEBUG_KRB5_TKT_RENEWAL)
|
||||||
new_start = time(NULL) + 30;
|
new_start = time(NULL) + 30;
|
||||||
#else
|
#else
|
||||||
|
expire_time = new_start;
|
||||||
new_start = KRB5_EVENT_REFRESH_TIME(new_start);
|
new_start = KRB5_EVENT_REFRESH_TIME(new_start);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@ -157,24 +216,73 @@ static void krb5_ticket_refresh_handler(struct event_context *event_ctx,
|
|||||||
error_message(ret)));
|
error_message(ret)));
|
||||||
/* maybe we are beyond the renewing window */
|
/* maybe we are beyond the renewing window */
|
||||||
|
|
||||||
|
/* evil rises here, we refresh ticket failed,
|
||||||
|
* but the ticket might be expired. Therefore,
|
||||||
|
* When we refresh ticket failed, destory the
|
||||||
|
* ticket */
|
||||||
|
|
||||||
|
ads_kdestroy(entry->ccname);
|
||||||
|
|
||||||
/* avoid breaking the renewal chain: retry in
|
/* avoid breaking the renewal chain: retry in
|
||||||
* lp_winbind_cache_time() seconds when the KDC was not
|
* lp_winbind_cache_time() seconds when the KDC was not
|
||||||
* available right now. */
|
* available right now.
|
||||||
|
* the return code can be KRB5_REALM_CANT_RESOLVE*/
|
||||||
|
|
||||||
if (ret == KRB5_KDC_UNREACH) {
|
if ((ret == KRB5_KDC_UNREACH)
|
||||||
|
|| (ret == KRB5_REALM_CANT_RESOLVE)) {
|
||||||
|
#if defined(DEBUG_KRB5_TKT_RENEWAL)
|
||||||
|
new_start = time(NULL) + 30;
|
||||||
|
#else
|
||||||
new_start = time(NULL) +
|
new_start = time(NULL) +
|
||||||
MAX(30, lp_winbind_cache_time());
|
MAX(30, lp_winbind_cache_time());
|
||||||
goto done;
|
#endif
|
||||||
|
/* ticket is destroyed here, we have to regain it
|
||||||
|
* if it is possible */
|
||||||
|
entry->event = event_add_timed(winbind_event_context(),
|
||||||
|
entry,
|
||||||
|
timeval_set(new_start, 0),
|
||||||
|
krb5_ticket_gain_handler,
|
||||||
|
entry);
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* This is evil, if the ticket was already expired.
|
||||||
|
* renew ticket function returns KRB5KRB_AP_ERR_TKT_EXPIRED.
|
||||||
|
* But there is still a chance that we can rekinit it.
|
||||||
|
*
|
||||||
|
* This happens when user login in online mode, and then network
|
||||||
|
* down or something cause winbind goes offline for a very long time,
|
||||||
|
* and then goes online again. ticket expired, renew failed.
|
||||||
|
* This happens when machine are put to sleep for a long time,
|
||||||
|
* but shorter than entry->renew_util.
|
||||||
|
* NB
|
||||||
|
* Looks like the KDC is reachable, we want to rekinit as soon as
|
||||||
|
* possible instead of waiting some time later. */
|
||||||
|
if ((ret == KRB5KRB_AP_ERR_TKT_EXPIRED)
|
||||||
|
|| (ret == KRB5_FCC_NOFILE)) goto rekinit;
|
||||||
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
done:
|
done:
|
||||||
|
/* in cases that ticket will be unrenewable soon, we don't try to renew ticket
|
||||||
|
* but try to regain ticket if it is possible */
|
||||||
|
if (entry->renew_until && expire_time
|
||||||
|
&& (entry->renew_until <= expire_time)) {
|
||||||
|
/* try to regain ticket 10 seconds beforre expiration */
|
||||||
|
expire_time -= 10;
|
||||||
|
entry->event = event_add_timed(winbind_event_context(), entry,
|
||||||
|
timeval_set(expire_time, 0),
|
||||||
|
krb5_ticket_gain_handler,
|
||||||
|
entry);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (entry->refresh_time == 0) {
|
||||||
|
entry->refresh_time = new_start;
|
||||||
|
}
|
||||||
entry->event = event_add_timed(winbind_event_context(), entry,
|
entry->event = event_add_timed(winbind_event_context(), entry,
|
||||||
timeval_set(new_start, 0),
|
timeval_set(new_start, 0),
|
||||||
"krb5_ticket_refresh_handler",
|
|
||||||
krb5_ticket_refresh_handler,
|
krb5_ticket_refresh_handler,
|
||||||
entry);
|
entry);
|
||||||
|
|
||||||
@ -187,7 +295,7 @@ done:
|
|||||||
|
|
||||||
static void krb5_ticket_gain_handler(struct event_context *event_ctx,
|
static void krb5_ticket_gain_handler(struct event_context *event_ctx,
|
||||||
struct timed_event *te,
|
struct timed_event *te,
|
||||||
const struct timeval *now,
|
struct timeval now,
|
||||||
void *private_data)
|
void *private_data)
|
||||||
{
|
{
|
||||||
struct WINBINDD_CCACHE_ENTRY *entry =
|
struct WINBINDD_CCACHE_ENTRY *entry =
|
||||||
@ -239,6 +347,9 @@ static void krb5_ticket_gain_handler(struct event_context *event_ctx,
|
|||||||
DEBUG(3,("krb5_ticket_gain_handler: "
|
DEBUG(3,("krb5_ticket_gain_handler: "
|
||||||
"could not kinit: %s\n",
|
"could not kinit: %s\n",
|
||||||
error_message(ret)));
|
error_message(ret)));
|
||||||
|
/* evil. If we cannot do it, destroy any the __maybe__
|
||||||
|
* __existing__ ticket */
|
||||||
|
ads_kdestroy(entry->ccname);
|
||||||
goto retry_later;
|
goto retry_later;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -249,13 +360,17 @@ static void krb5_ticket_gain_handler(struct event_context *event_ctx,
|
|||||||
goto got_ticket;
|
goto got_ticket;
|
||||||
|
|
||||||
retry_later:
|
retry_later:
|
||||||
|
|
||||||
|
#if defined(DEBUG_KRB5_TKT_REGAIN)
|
||||||
|
t = timeval_set(time(NULL) + 30, 0);
|
||||||
|
#else
|
||||||
t = timeval_current_ofs(MAX(30, lp_winbind_cache_time()), 0);
|
t = timeval_current_ofs(MAX(30, lp_winbind_cache_time()), 0);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
entry->refresh_time = 0;
|
||||||
entry->event = event_add_timed(winbind_event_context(),
|
entry->event = event_add_timed(winbind_event_context(),
|
||||||
entry,
|
entry,
|
||||||
t,
|
t,
|
||||||
"krb5_ticket_gain_handler",
|
|
||||||
krb5_ticket_gain_handler,
|
krb5_ticket_gain_handler,
|
||||||
entry);
|
entry);
|
||||||
|
|
||||||
@ -269,10 +384,12 @@ static void krb5_ticket_gain_handler(struct event_context *event_ctx,
|
|||||||
t = timeval_set(KRB5_EVENT_REFRESH_TIME(entry->refresh_time), 0);
|
t = timeval_set(KRB5_EVENT_REFRESH_TIME(entry->refresh_time), 0);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
if (entry->refresh_time == 0) {
|
||||||
|
entry->refresh_time = t.tv_sec;
|
||||||
|
}
|
||||||
entry->event = event_add_timed(winbind_event_context(),
|
entry->event = event_add_timed(winbind_event_context(),
|
||||||
entry,
|
entry,
|
||||||
t,
|
t,
|
||||||
"krb5_ticket_refresh_handler",
|
|
||||||
krb5_ticket_refresh_handler,
|
krb5_ticket_refresh_handler,
|
||||||
entry);
|
entry);
|
||||||
|
|
||||||
@ -280,6 +397,43 @@ static void krb5_ticket_gain_handler(struct event_context *event_ctx,
|
|||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void ccache_regain_all_now(void)
|
||||||
|
{
|
||||||
|
struct WINBINDD_CCACHE_ENTRY *cur;
|
||||||
|
struct timeval t = timeval_current();
|
||||||
|
|
||||||
|
for (cur = ccache_list; cur; cur = cur->next) {
|
||||||
|
struct timed_event *new_event;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* if refresh_time is 0, we know that the
|
||||||
|
* the event has the krb5_ticket_gain_handler
|
||||||
|
*/
|
||||||
|
if (cur->refresh_time == 0) {
|
||||||
|
new_event = event_add_timed(winbind_event_context(),
|
||||||
|
cur,
|
||||||
|
t,
|
||||||
|
krb5_ticket_gain_handler,
|
||||||
|
cur);
|
||||||
|
} else {
|
||||||
|
new_event = event_add_timed(winbind_event_context(),
|
||||||
|
cur,
|
||||||
|
t,
|
||||||
|
krb5_ticket_refresh_handler,
|
||||||
|
cur);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!new_event) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
TALLOC_FREE(cur->event);
|
||||||
|
cur->event = new_event;
|
||||||
|
}
|
||||||
|
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
/****************************************************************
|
/****************************************************************
|
||||||
Check if an ccache entry exists.
|
Check if an ccache entry exists.
|
||||||
****************************************************************/
|
****************************************************************/
|
||||||
@ -331,6 +485,10 @@ NTSTATUS add_ccache_to_list(const char *princ_name,
|
|||||||
{
|
{
|
||||||
struct WINBINDD_CCACHE_ENTRY *entry = NULL;
|
struct WINBINDD_CCACHE_ENTRY *entry = NULL;
|
||||||
struct timeval t;
|
struct timeval t;
|
||||||
|
NTSTATUS ntret;
|
||||||
|
#ifdef HAVE_KRB5
|
||||||
|
int ret;
|
||||||
|
#endif
|
||||||
|
|
||||||
if ((username == NULL && princ_name == NULL) ||
|
if ((username == NULL && princ_name == NULL) ||
|
||||||
ccname == NULL || uid < 0) {
|
ccname == NULL || uid < 0) {
|
||||||
@ -343,6 +501,28 @@ NTSTATUS add_ccache_to_list(const char *princ_name,
|
|||||||
return NT_STATUS_NO_MORE_ENTRIES;
|
return NT_STATUS_NO_MORE_ENTRIES;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* If it is cached login, destroy krb5 ticket
|
||||||
|
* to avoid surprise. */
|
||||||
|
#ifdef HAVE_KRB5
|
||||||
|
if (postponed_request) {
|
||||||
|
/* ignore KRB5_FCC_NOFILE error here */
|
||||||
|
ret = ads_kdestroy(ccname);
|
||||||
|
if (ret == KRB5_FCC_NOFILE) {
|
||||||
|
ret = 0;
|
||||||
|
}
|
||||||
|
if (ret) {
|
||||||
|
DEBUG(0, ("add_ccache_to_list: failed to destroy "
|
||||||
|
"user krb5 ccache %s with %s\n", ccname,
|
||||||
|
error_message(ret)));
|
||||||
|
return krb5_to_nt_status(ret);
|
||||||
|
} else {
|
||||||
|
DEBUG(10, ("add_ccache_to_list: successfully destroyed "
|
||||||
|
"krb5 ccache %s for user %s\n", ccname,
|
||||||
|
username));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
/* Reference count old entries */
|
/* Reference count old entries */
|
||||||
entry = get_ccache_by_username(username);
|
entry = get_ccache_by_username(username);
|
||||||
if (entry) {
|
if (entry) {
|
||||||
@ -355,7 +535,51 @@ NTSTATUS add_ccache_to_list(const char *princ_name,
|
|||||||
"ref count on entry %s is now %d\n",
|
"ref count on entry %s is now %d\n",
|
||||||
username, entry->ref_count));
|
username, entry->ref_count));
|
||||||
/* FIXME: in this case we still might want to have a krb5 cred
|
/* FIXME: in this case we still might want to have a krb5 cred
|
||||||
* event handler created - gd*/
|
* event handler created - gd
|
||||||
|
* Add ticket refresh handler here */
|
||||||
|
|
||||||
|
if (!lp_winbind_refresh_tickets() || renew_until <= 0) {
|
||||||
|
return NT_STATUS_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!entry->event) {
|
||||||
|
if (postponed_request) {
|
||||||
|
t = timeval_current_ofs(MAX(30, lp_winbind_cache_time()), 0);
|
||||||
|
entry->event = event_add_timed(winbind_event_context(),
|
||||||
|
entry,
|
||||||
|
t,
|
||||||
|
krb5_ticket_gain_handler,
|
||||||
|
entry);
|
||||||
|
} else {
|
||||||
|
/* Renew at 1/2 the ticket expiration time */
|
||||||
|
#if defined(DEBUG_KRB5_TKT_RENEWAL)
|
||||||
|
t = timeval_set(time(NULL)+30, 0);
|
||||||
|
#else
|
||||||
|
t = timeval_set(KRB5_EVENT_REFRESH_TIME(ticket_end), 0);
|
||||||
|
#endif
|
||||||
|
entry->event = event_add_timed(winbind_event_context(),
|
||||||
|
entry,
|
||||||
|
t,
|
||||||
|
krb5_ticket_refresh_handler,
|
||||||
|
entry);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!entry->event) {
|
||||||
|
ntret = remove_ccache(username);
|
||||||
|
if (!NT_STATUS_IS_OK(ntret)) {
|
||||||
|
DEBUG(0, ("add_ccache_to_list: Failed to remove krb5 "
|
||||||
|
"ccache %s for user %s\n", entry->ccname,
|
||||||
|
entry->username));
|
||||||
|
DEBUG(0, ("add_ccache_to_list: error is %s\n",
|
||||||
|
nt_errstr(ntret)));
|
||||||
|
return ntret;
|
||||||
|
}
|
||||||
|
return NT_STATUS_NO_MEMORY;
|
||||||
|
}
|
||||||
|
|
||||||
|
DEBUG(10,("add_ccache_to_list: added krb5_ticket handler\n"));
|
||||||
|
}
|
||||||
|
|
||||||
return NT_STATUS_OK;
|
return NT_STATUS_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -406,10 +630,10 @@ NTSTATUS add_ccache_to_list(const char *princ_name,
|
|||||||
|
|
||||||
if (postponed_request) {
|
if (postponed_request) {
|
||||||
t = timeval_current_ofs(MAX(30, lp_winbind_cache_time()), 0);
|
t = timeval_current_ofs(MAX(30, lp_winbind_cache_time()), 0);
|
||||||
|
entry->refresh_time = 0;
|
||||||
entry->event = event_add_timed(winbind_event_context(),
|
entry->event = event_add_timed(winbind_event_context(),
|
||||||
entry,
|
entry,
|
||||||
t,
|
t,
|
||||||
"krb5_ticket_gain_handler",
|
|
||||||
krb5_ticket_gain_handler,
|
krb5_ticket_gain_handler,
|
||||||
entry);
|
entry);
|
||||||
} else {
|
} else {
|
||||||
@ -419,10 +643,12 @@ NTSTATUS add_ccache_to_list(const char *princ_name,
|
|||||||
#else
|
#else
|
||||||
t = timeval_set(KRB5_EVENT_REFRESH_TIME(ticket_end), 0);
|
t = timeval_set(KRB5_EVENT_REFRESH_TIME(ticket_end), 0);
|
||||||
#endif
|
#endif
|
||||||
|
if (entry->refresh_time == 0) {
|
||||||
|
entry->refresh_time = t.tv_sec;
|
||||||
|
}
|
||||||
entry->event = event_add_timed(winbind_event_context(),
|
entry->event = event_add_timed(winbind_event_context(),
|
||||||
entry,
|
entry,
|
||||||
t,
|
t,
|
||||||
"krb5_ticket_refresh_handler",
|
|
||||||
krb5_ticket_refresh_handler,
|
krb5_ticket_refresh_handler,
|
||||||
entry);
|
entry);
|
||||||
}
|
}
|
||||||
|
@ -175,7 +175,7 @@ static void async_main_request_sent(void *private_data, bool success)
|
|||||||
|
|
||||||
static void async_request_timeout_handler(struct event_context *ctx,
|
static void async_request_timeout_handler(struct event_context *ctx,
|
||||||
struct timed_event *te,
|
struct timed_event *te,
|
||||||
const struct timeval *now,
|
struct timeval now,
|
||||||
void *private_data)
|
void *private_data)
|
||||||
{
|
{
|
||||||
struct winbindd_async_request *state =
|
struct winbindd_async_request *state =
|
||||||
@ -247,7 +247,6 @@ static void async_request_sent(void *private_data_data, bool success)
|
|||||||
state->reply_timeout_event = event_add_timed(winbind_event_context(),
|
state->reply_timeout_event = event_add_timed(winbind_event_context(),
|
||||||
NULL,
|
NULL,
|
||||||
timeval_current_ofs(300,0),
|
timeval_current_ofs(300,0),
|
||||||
"async_request_timeout",
|
|
||||||
async_request_timeout_handler,
|
async_request_timeout_handler,
|
||||||
state);
|
state);
|
||||||
if (!state->reply_timeout_event) {
|
if (!state->reply_timeout_event) {
|
||||||
@ -827,7 +826,7 @@ void winbind_msg_dump_domain_list(struct messaging_context *msg_ctx,
|
|||||||
|
|
||||||
static void account_lockout_policy_handler(struct event_context *ctx,
|
static void account_lockout_policy_handler(struct event_context *ctx,
|
||||||
struct timed_event *te,
|
struct timed_event *te,
|
||||||
const struct timeval *now,
|
struct timeval now,
|
||||||
void *private_data)
|
void *private_data)
|
||||||
{
|
{
|
||||||
struct winbindd_child *child =
|
struct winbindd_child *child =
|
||||||
@ -866,7 +865,6 @@ static void account_lockout_policy_handler(struct event_context *ctx,
|
|||||||
|
|
||||||
child->lockout_policy_event = event_add_timed(winbind_event_context(), NULL,
|
child->lockout_policy_event = event_add_timed(winbind_event_context(), NULL,
|
||||||
timeval_current_ofs(3600, 0),
|
timeval_current_ofs(3600, 0),
|
||||||
"account_lockout_policy_handler",
|
|
||||||
account_lockout_policy_handler,
|
account_lockout_policy_handler,
|
||||||
child);
|
child);
|
||||||
}
|
}
|
||||||
@ -919,7 +917,7 @@ static bool calculate_next_machine_pwd_change(const char *domain,
|
|||||||
|
|
||||||
static void machine_password_change_handler(struct event_context *ctx,
|
static void machine_password_change_handler(struct event_context *ctx,
|
||||||
struct timed_event *te,
|
struct timed_event *te,
|
||||||
const struct timeval *now,
|
struct timeval now,
|
||||||
void *private_data)
|
void *private_data)
|
||||||
{
|
{
|
||||||
struct winbindd_child *child =
|
struct winbindd_child *child =
|
||||||
@ -971,7 +969,6 @@ static void machine_password_change_handler(struct event_context *ctx,
|
|||||||
|
|
||||||
child->machine_password_change_event = event_add_timed(winbind_event_context(), NULL,
|
child->machine_password_change_event = event_add_timed(winbind_event_context(), NULL,
|
||||||
next_change,
|
next_change,
|
||||||
"machine_password_change_handler",
|
|
||||||
machine_password_change_handler,
|
machine_password_change_handler,
|
||||||
child);
|
child);
|
||||||
}
|
}
|
||||||
@ -985,6 +982,7 @@ static void child_msg_offline(struct messaging_context *msg,
|
|||||||
DATA_BLOB *data)
|
DATA_BLOB *data)
|
||||||
{
|
{
|
||||||
struct winbindd_domain *domain;
|
struct winbindd_domain *domain;
|
||||||
|
struct winbindd_domain *primary_domain = NULL;
|
||||||
const char *domainname = (const char *)data->data;
|
const char *domainname = (const char *)data->data;
|
||||||
|
|
||||||
if (data->data == NULL || data->length == 0) {
|
if (data->data == NULL || data->length == 0) {
|
||||||
@ -998,6 +996,8 @@ static void child_msg_offline(struct messaging_context *msg,
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
primary_domain = find_our_domain();
|
||||||
|
|
||||||
/* Mark the requested domain offline. */
|
/* Mark the requested domain offline. */
|
||||||
|
|
||||||
for (domain = domain_list(); domain; domain = domain->next) {
|
for (domain = domain_list(); domain; domain = domain->next) {
|
||||||
@ -1007,6 +1007,11 @@ static void child_msg_offline(struct messaging_context *msg,
|
|||||||
if (strequal(domain->name, domainname)) {
|
if (strequal(domain->name, domainname)) {
|
||||||
DEBUG(5,("child_msg_offline: marking %s offline.\n", domain->name));
|
DEBUG(5,("child_msg_offline: marking %s offline.\n", domain->name));
|
||||||
set_domain_offline(domain);
|
set_domain_offline(domain);
|
||||||
|
/* we are in the trusted domain, set the primary domain
|
||||||
|
* offline too */
|
||||||
|
if (domain != primary_domain) {
|
||||||
|
set_domain_offline(primary_domain);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1020,6 +1025,7 @@ static void child_msg_online(struct messaging_context *msg,
|
|||||||
DATA_BLOB *data)
|
DATA_BLOB *data)
|
||||||
{
|
{
|
||||||
struct winbindd_domain *domain;
|
struct winbindd_domain *domain;
|
||||||
|
struct winbindd_domain *primary_domain = NULL;
|
||||||
const char *domainname = (const char *)data->data;
|
const char *domainname = (const char *)data->data;
|
||||||
|
|
||||||
if (data->data == NULL || data->length == 0) {
|
if (data->data == NULL || data->length == 0) {
|
||||||
@ -1033,6 +1039,8 @@ static void child_msg_online(struct messaging_context *msg,
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
primary_domain = find_our_domain();
|
||||||
|
|
||||||
/* Set our global state as online. */
|
/* Set our global state as online. */
|
||||||
set_global_winbindd_state_online();
|
set_global_winbindd_state_online();
|
||||||
|
|
||||||
@ -1047,6 +1055,16 @@ static void child_msg_online(struct messaging_context *msg,
|
|||||||
DEBUG(5,("child_msg_online: requesting %s to go online.\n", domain->name));
|
DEBUG(5,("child_msg_online: requesting %s to go online.\n", domain->name));
|
||||||
winbindd_flush_negative_conn_cache(domain);
|
winbindd_flush_negative_conn_cache(domain);
|
||||||
set_domain_online_request(domain);
|
set_domain_online_request(domain);
|
||||||
|
|
||||||
|
/* we can be in trusted domain, which will contact primary domain
|
||||||
|
* we have to bring primary domain online in trusted domain process
|
||||||
|
* see, winbindd_dual_pam_auth() --> winbindd_dual_pam_auth_samlogon()
|
||||||
|
* --> contact_domain = find_our_domain()
|
||||||
|
* */
|
||||||
|
if (domain != primary_domain) {
|
||||||
|
winbindd_flush_negative_conn_cache(primary_domain);
|
||||||
|
set_domain_online_request(primary_domain);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1177,13 +1195,18 @@ static bool fork_domain_child(struct winbindd_child *child)
|
|||||||
state.sock = fdpair[0];
|
state.sock = fdpair[0];
|
||||||
close(fdpair[1]);
|
close(fdpair[1]);
|
||||||
|
|
||||||
if (!reinit_after_fork(winbind_messaging_context(), true)) {
|
if (!reinit_after_fork(winbind_messaging_context(),
|
||||||
|
winbind_event_context(), true)) {
|
||||||
DEBUG(0,("reinit_after_fork() failed\n"));
|
DEBUG(0,("reinit_after_fork() failed\n"));
|
||||||
_exit(0);
|
_exit(0);
|
||||||
}
|
}
|
||||||
|
|
||||||
close_conns_after_fork();
|
close_conns_after_fork();
|
||||||
|
|
||||||
|
/* Ensure we're not handling an event inherited from
|
||||||
|
our parent. */
|
||||||
|
ccache_remove_all_after_fork();
|
||||||
|
|
||||||
if (!override_logfile) {
|
if (!override_logfile) {
|
||||||
lp_set_logfile(child->logfilename);
|
lp_set_logfile(child->logfilename);
|
||||||
reopen_logs();
|
reopen_logs();
|
||||||
@ -1219,32 +1242,33 @@ static bool fork_domain_child(struct winbindd_child *child)
|
|||||||
messaging_register(winbind_messaging_context(), NULL,
|
messaging_register(winbind_messaging_context(), NULL,
|
||||||
MSG_DEBUG, debug_message);
|
MSG_DEBUG, debug_message);
|
||||||
|
|
||||||
if ( child->domain ) {
|
primary_domain = find_our_domain();
|
||||||
child->domain->startup = True;
|
|
||||||
child->domain->startup_time = time(NULL);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Ensure we have no pending check_online events other
|
|
||||||
than one for this domain or the primary domain. */
|
|
||||||
|
|
||||||
for (domain = domain_list(); domain; domain = domain->next) {
|
|
||||||
if (domain->primary) {
|
|
||||||
primary_domain = domain;
|
|
||||||
}
|
|
||||||
if ((domain != child->domain) && !domain->primary) {
|
|
||||||
TALLOC_FREE(domain->check_online_event);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (primary_domain == NULL) {
|
if (primary_domain == NULL) {
|
||||||
smb_panic("no primary domain found");
|
smb_panic("no primary domain found");
|
||||||
}
|
}
|
||||||
|
/* we have destroy all time event in reinit_after_fork()
|
||||||
/* Ensure we're not handling an event inherited from
|
* set check_online_event to NULL */
|
||||||
our parent. */
|
for (domain = domain_list(); domain; domain = domain->next) {
|
||||||
|
domain->check_online_event = NULL;
|
||||||
cancel_named_event(winbind_event_context(),
|
}
|
||||||
"krb5_ticket_refresh_handler");
|
/* It doesn't matter if we allow cache login,
|
||||||
|
* try to bring domain online after fork. */
|
||||||
|
if ( child->domain ) {
|
||||||
|
child->domain->startup = True;
|
||||||
|
child->domain->startup_time = time(NULL);
|
||||||
|
/* we can be in primary domain or in trusted domain
|
||||||
|
* If we are in trusted domain, set the primary domain
|
||||||
|
* in start-up mode */
|
||||||
|
if (!(child->domain->internal)) {
|
||||||
|
set_domain_online_request(child->domain);
|
||||||
|
if (!(child->domain->primary)) {
|
||||||
|
primary_domain->startup = True;
|
||||||
|
primary_domain->startup_time = time(NULL);
|
||||||
|
set_domain_online_request(primary_domain);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/* We might be in the idmap child...*/
|
/* We might be in the idmap child...*/
|
||||||
if (child->domain && !(child->domain->internal) &&
|
if (child->domain && !(child->domain->internal) &&
|
||||||
@ -1266,7 +1290,6 @@ static bool fork_domain_child(struct winbindd_child *child)
|
|||||||
|
|
||||||
child->lockout_policy_event = event_add_timed(
|
child->lockout_policy_event = event_add_timed(
|
||||||
winbind_event_context(), NULL, timeval_zero(),
|
winbind_event_context(), NULL, timeval_zero(),
|
||||||
"account_lockout_policy_handler",
|
|
||||||
account_lockout_policy_handler,
|
account_lockout_policy_handler,
|
||||||
child);
|
child);
|
||||||
}
|
}
|
||||||
@ -1281,7 +1304,6 @@ static bool fork_domain_child(struct winbindd_child *child)
|
|||||||
&next_change)) {
|
&next_change)) {
|
||||||
child->machine_password_change_event = event_add_timed(
|
child->machine_password_change_event = event_add_timed(
|
||||||
winbind_event_context(), NULL, next_change,
|
winbind_event_context(), NULL, next_change,
|
||||||
"machine_password_change_handler",
|
|
||||||
machine_password_change_handler,
|
machine_password_change_handler,
|
||||||
child);
|
child);
|
||||||
}
|
}
|
||||||
|
@ -53,12 +53,12 @@ bool register_message_flags(bool doreg, uint32 msg_flags);
|
|||||||
|
|
||||||
struct event_context *winbind_event_context(void);
|
struct event_context *winbind_event_context(void);
|
||||||
struct messaging_context *winbind_messaging_context(void);
|
struct messaging_context *winbind_messaging_context(void);
|
||||||
void add_fd_event(struct fd_event *ev);
|
void add_fd_event(struct winbindd_fd_event *ev);
|
||||||
void remove_fd_event(struct fd_event *ev);
|
void remove_fd_event(struct winbindd_fd_event *ev);
|
||||||
void setup_async_read(struct fd_event *event, void *data, size_t length,
|
void setup_async_read(struct winbindd_fd_event *event, void *data, size_t length,
|
||||||
void (*finished)(void *private_data, bool success),
|
void (*finished)(void *private_data, bool success),
|
||||||
void *private_data);
|
void *private_data);
|
||||||
void setup_async_write(struct fd_event *event, void *data, size_t length,
|
void setup_async_write(struct winbindd_fd_event *event, void *data, size_t length,
|
||||||
void (*finished)(void *private_data, bool success),
|
void (*finished)(void *private_data, bool success),
|
||||||
void *private_data);
|
void *private_data);
|
||||||
void request_error(struct winbindd_cli_state *state);
|
void request_error(struct winbindd_cli_state *state);
|
||||||
@ -243,6 +243,8 @@ bool ccache_entry_exists(const char *username);
|
|||||||
bool ccache_entry_identical(const char *username,
|
bool ccache_entry_identical(const char *username,
|
||||||
uid_t uid,
|
uid_t uid,
|
||||||
const char *ccname);
|
const char *ccname);
|
||||||
|
void ccache_remove_all_after_fork(void);
|
||||||
|
void ccache_regain_all_now(void);
|
||||||
NTSTATUS add_ccache_to_list(const char *princ_name,
|
NTSTATUS add_ccache_to_list(const char *princ_name,
|
||||||
const char *ccname,
|
const char *ccname,
|
||||||
const char *service,
|
const char *service,
|
||||||
|
Reference in New Issue
Block a user