summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--source3/Makefile.in2
-rw-r--r--source3/include/nt_status.h5
-rw-r--r--source3/include/smb.h5
-rw-r--r--source3/lib/util.c13
-rw-r--r--source3/smbd/notify.c27
-rw-r--r--source3/smbd/notify_inotify.c60
-rw-r--r--source3/smbd/notify_internal.c30
7 files changed, 98 insertions, 44 deletions
diff --git a/source3/Makefile.in b/source3/Makefile.in
index c21cea0aec..5c1ff7c695 100644
--- a/source3/Makefile.in
+++ b/source3/Makefile.in
@@ -409,7 +409,7 @@ PROFILES_OBJ = utils/profiles.o \
OPLOCK_OBJ = smbd/oplock.o smbd/oplock_irix.o smbd/oplock_linux.o
NOTIFY_OBJ = smbd/notify.o smbd/notify_hash.o smbd/notify_kernel.o \
- smbd/notify_fam.o
+ smbd/notify_fam.o smbd/notify_inotify.o smbd/notify_internal.o
VFS_DEFAULT_OBJ = modules/vfs_default.o
VFS_AUDIT_OBJ = modules/vfs_audit.o
diff --git a/source3/include/nt_status.h b/source3/include/nt_status.h
index 968657ca44..471ac47927 100644
--- a/source3/include/nt_status.h
+++ b/source3/include/nt_status.h
@@ -66,6 +66,11 @@ typedef uint32 WERROR;
}\
} while (0)
+#define NT_STATUS_NOT_OK_RETURN(x) do { \
+ if (!NT_STATUS_IS_OK(x)) {\
+ return x;\
+ }\
+} while (0)
/* The top byte in an NTSTATUS code is used as a type field.
* Windows only uses value 0xC0 as an indicator for an NT error
diff --git a/source3/include/smb.h b/source3/include/smb.h
index 3af3dd63dc..0fe5a44e3c 100644
--- a/source3/include/smb.h
+++ b/source3/include/smb.h
@@ -446,6 +446,11 @@ struct notify_change {
};
struct notify_mid_map;
+struct sys_notify_backend;
+struct sys_notify_context {
+ struct event_context *ev;
+ void *private_data;
+};
struct notify_change_request {
struct notify_change_request *prev, *next;
diff --git a/source3/lib/util.c b/source3/lib/util.c
index 5e2588e5b9..b416907c41 100644
--- a/source3/lib/util.c
+++ b/source3/lib/util.c
@@ -3007,11 +3007,24 @@ struct process_id procid_self(void)
return pid_to_procid(sys_getpid());
}
+struct server_id server_id_self(void)
+{
+ struct server_id id;
+ id.id = procid_self();
+ return id;
+}
+
BOOL procid_equal(const struct process_id *p1, const struct process_id *p2)
{
return (p1->pid == p2->pid);
}
+BOOL cluster_id_equal(const struct server_id *id1,
+ const struct server_id *id2)
+{
+ return procid_equal(&id1->id, &id2->id);
+}
+
BOOL procid_is_me(const struct process_id *pid)
{
return (pid->pid == sys_getpid());
diff --git a/source3/smbd/notify.c b/source3/smbd/notify.c
index 4c82b9fca8..97192d6e63 100644
--- a/source3/smbd/notify.c
+++ b/source3/smbd/notify.c
@@ -548,3 +548,30 @@ BOOL init_change_notify(void)
return True;
}
+
+struct sys_notify_context *sys_notify_context_create(struct share_params *scfg,
+ TALLOC_CTX *mem_ctx,
+ struct event_context *ev)
+{
+ struct sys_notify_context *ctx;
+
+ if (!(ctx = TALLOC_P(mem_ctx, struct sys_notify_context))) {
+ DEBUG(0, ("talloc failed\n"));
+ return NULL;
+ }
+
+ ctx->ev = ev;
+ ctx->private_data = NULL;
+ return ctx;
+}
+
+NTSTATUS sys_notify_watch(struct sys_notify_context *ctx,
+ struct notify_entry *e,
+ void (*callback)(struct sys_notify_context *ctx,
+ void *private_data,
+ struct notify_event *ev),
+ void *private_data, void *handle)
+{
+ return inotify_watch(ctx, e, callback, private_data, handle);
+}
+
diff --git a/source3/smbd/notify_inotify.c b/source3/smbd/notify_inotify.c
index 8bb0096dcc..39dc7e53e7 100644
--- a/source3/smbd/notify_inotify.c
+++ b/source3/smbd/notify_inotify.c
@@ -23,11 +23,8 @@
*/
#include "includes.h"
-#include "system/filesys.h"
-#include "ntvfs/sysdep/sys_notify.h"
-#include "lib/events/events.h"
-#include "lib/util/dlinklist.h"
-#include "libcli/raw/smb.h"
+
+#ifdef HAVE_INOTIFY
#include <linux/inotify.h>
#include <asm/unistd.h>
@@ -71,7 +68,9 @@ struct watch_context {
struct watch_context *next, *prev;
struct inotify_private *in;
int wd;
- sys_notify_callback_t callback;
+ void (*callback)(struct sys_notify_context *ctx,
+ void *private_data,
+ struct notify_event *ev);
void *private_data;
uint32_t mask; /* the inotify mask */
uint32_t filter; /* the windows completion filter */
@@ -95,6 +94,9 @@ static int inotify_destructor(struct inotify_private *in)
*/
static BOOL filter_match(struct watch_context *w, struct inotify_event *e)
{
+ DEBUG(10, ("filter_match: e->mask=%x, w->mask=%x, w->filter=%x\n",
+ e->mask, w->mask, w->filter));
+
if ((e->mask & w->mask) == 0) {
/* this happens because inotify_add_watch() coalesces watches on the same
path, oring their masks together */
@@ -142,6 +144,9 @@ static void inotify_dispatch(struct inotify_private *in,
struct watch_context *w, *next;
struct notify_event ne;
+ DEBUG(10, ("inotify_dispatch called with mask=%x, name=[%s]\n",
+ e->mask, e->len ? e->name : ""));
+
/* ignore extraneous events, such as unmount and IN_IGNORED events */
if ((e->mask & (IN_ATTRIB|IN_MODIFY|IN_CREATE|IN_DELETE|
IN_MOVED_FROM|IN_MOVED_TO)) == 0) {
@@ -171,6 +176,9 @@ static void inotify_dispatch(struct inotify_private *in,
}
ne.path = e->name;
+ DEBUG(10, ("inotify_dispatch: ne.action = %d, ne.path = %s\n",
+ ne.action, ne.path));
+
/* find any watches that have this watch descriptor */
for (w=in->watches;w;w=next) {
next = w->next;
@@ -222,7 +230,7 @@ static void inotify_handler(struct event_context *ev, struct fd_event *fde,
return;
}
- e0 = e = talloc_size(in, bufsize);
+ e0 = e = (struct inotify_event *)talloc_size(in, bufsize);
if (e == NULL) return;
if (read(in->fd, e0, bufsize) != bufsize) {
@@ -323,7 +331,12 @@ static int watch_destructor(struct watch_context *w)
if (w->wd == wd) break;
}
if (w == NULL) {
- inotify_rm_watch(in->fd, wd);
+ DEBUG(10, ("Deleting inotify watch %d\n", wd));
+ if (inotify_rm_watch(in->fd, wd) == -1) {
+ DEBUG(1, ("inotify_rm_watch returned %s\n",
+ strerror(errno)));
+ }
+
}
return 0;
}
@@ -333,11 +346,13 @@ static int watch_destructor(struct watch_context *w)
add a watch. The watch is removed when the caller calls
talloc_free() on *handle
*/
-static NTSTATUS inotify_watch(struct sys_notify_context *ctx,
- struct notify_entry *e,
- sys_notify_callback_t callback,
- void *private_data,
- void *handle_p)
+NTSTATUS inotify_watch(struct sys_notify_context *ctx,
+ struct notify_entry *e,
+ void (*callback)(struct sys_notify_context *ctx,
+ void *private_data,
+ struct notify_event *ev),
+ void *private_data,
+ void *handle_p)
{
struct inotify_private *in;
int wd;
@@ -369,9 +384,13 @@ static NTSTATUS inotify_watch(struct sys_notify_context *ctx,
wd = inotify_add_watch(in->fd, e->path, mask);
if (wd == -1) {
e->filter = filter;
+ DEBUG(1, ("inotify_add_watch returned %s\n", strerror(errno)));
return map_nt_error_from_unix(errno);
}
+ DEBUG(10, ("inotify_add_watch for %s mask %x returned wd %d\n",
+ e->path, mask, wd));
+
w = talloc(in, struct watch_context);
if (w == NULL) {
inotify_rm_watch(in->fd, wd);
@@ -402,17 +421,4 @@ static NTSTATUS inotify_watch(struct sys_notify_context *ctx,
return NT_STATUS_OK;
}
-
-static struct sys_notify_backend inotify = {
- .name = "inotify",
- .notify_watch = inotify_watch
-};
-
-/*
- initialialise the inotify module
- */
-NTSTATUS sys_notify_inotify_init(void)
-{
- /* register ourselves as a system inotify module */
- return sys_notify_register(&inotify);
-}
+#endif
diff --git a/source3/smbd/notify_internal.c b/source3/smbd/notify_internal.c
index 91fa8a1d78..6d77ba4df6 100644
--- a/source3/smbd/notify_internal.c
+++ b/source3/smbd/notify_internal.c
@@ -25,17 +25,7 @@
*/
#include "includes.h"
-#include "system/filesys.h"
-#include "lib/tdb/include/tdb.h"
-#include "lib/util/util_tdb.h"
-#include "messaging/messaging.h"
-#include "db_wrap.h"
-#include "lib/messaging/irpc.h"
#include "librpc/gen_ndr/ndr_notify.h"
-#include "lib/util/dlinklist.h"
-#include "ntvfs/common/ntvfs_common.h"
-#include "ntvfs/sysdep/sys_notify.h"
-#include "cluster/cluster.h"
struct notify_context {
struct tdb_wrap *w;
@@ -83,11 +73,11 @@ static int notify_destructor(struct notify_context *notify)
struct notify_context *notify_init(TALLOC_CTX *mem_ctx, struct server_id server,
struct messaging_context *messaging_ctx,
struct event_context *ev,
- struct share_config *scfg)
+ struct share_params *scfg)
{
struct notify_context *notify;
- if (share_bool_option(scfg, NOTIFY_ENABLE, NOTIFY_ENABLE_DEFAULT) != True) {
+ if (!lp_parm_bool(scfg->service, "notify", "enable", True)) {
return NULL;
}
@@ -96,7 +86,9 @@ struct notify_context *notify_init(TALLOC_CTX *mem_ctx, struct server_id server,
return NULL;
}
- notify->w = cluster_tdb_tmp_open(notify, "notify.tdb", TDB_SEQNUM);
+ notify->w = tdb_wrap_open(notify, lock_path("notify.tdb"),
+ 0, TDB_SEQNUM|TDB_CLEAR_IF_FIRST,
+ O_RDWR|O_CREAT, 0644);
if (notify->w == NULL) {
talloc_free(notify);
return NULL;
@@ -167,7 +159,7 @@ static NTSTATUS notify_load(struct notify_context *notify)
return NT_STATUS_OK;
}
- blob.data = dbuf.dptr;
+ blob.data = (uint8 *)dbuf.dptr;
blob.length = dbuf.dsize;
status = ndr_pull_struct_blob(&blob, notify->array, notify->array,
@@ -182,7 +174,8 @@ static NTSTATUS notify_load(struct notify_context *notify)
*/
static int notify_compare(const void *p1, const void *p2)
{
- const struct notify_entry *e1 = p1, *e2 = p2;
+ const struct notify_entry *e1 = (const struct notify_entry *)p1;
+ const struct notify_entry *e2 = (const struct notify_entry *)p2;
return strcmp(e1->path, e2->path);
}
@@ -222,7 +215,7 @@ static NTSTATUS notify_save(struct notify_context *notify)
return status;
}
- dbuf.dptr = blob.data;
+ dbuf.dptr = (char *)blob.data;
dbuf.dsize = blob.length;
ret = tdb_store_bystring(notify->w->tdb, NOTIFY_KEY, dbuf, TDB_REPLACE);
@@ -276,6 +269,8 @@ static void sys_notify_callback(struct sys_notify_context *ctx,
{
struct notify_list *listel = talloc_get_type(ptr, struct notify_list);
ev->private_data = listel;
+ DEBUG(10, ("sys_notify_callback called with action=%d, for %s\n",
+ ev->action, ev->path));
listel->callback(listel->private_data, ev);
}
@@ -576,6 +571,9 @@ void notify_trigger(struct notify_context *notify,
int depth;
const char *p, *next_p;
+ DEBUG(10, ("notify_trigger called action=0x%x, filter=0x%x, "
+ "path=%s\n", (unsigned)action, (unsigned)filter, path));
+
/* see if change notify is enabled at all */
if (notify == NULL) {
return;