summaryrefslogtreecommitdiff
path: root/source3/smbd/notify.c
diff options
context:
space:
mode:
authorVolker Lendecke <vlendec@samba.org>2007-01-31 14:42:56 +0000
committerGerald (Jerry) Carter <jerry@samba.org>2007-10-10 12:17:36 -0500
commit2852ecc67ebded7758a07d8fb72eef53bfa1c63a (patch)
tree4c69630521ef333be31379e0433fb53fad37919a /source3/smbd/notify.c
parentaccbfaa4c3ffe669cc29aac8a85c4144ad234e43 (diff)
downloadsamba-2852ecc67ebded7758a07d8fb72eef53bfa1c63a.tar.gz
samba-2852ecc67ebded7758a07d8fb72eef53bfa1c63a.tar.bz2
samba-2852ecc67ebded7758a07d8fb72eef53bfa1c63a.zip
r21092: Ok, that's the one that activates the Samba4 notify backend.
Now to clean up / fix lots of stuff. Volker (This used to be commit 9e7443fa1417c01be903b15073825dc4def78d99)
Diffstat (limited to 'source3/smbd/notify.c')
-rw-r--r--source3/smbd/notify.c97
1 files changed, 57 insertions, 40 deletions
diff --git a/source3/smbd/notify.c b/source3/smbd/notify.c
index 49219bcca5..93a6357d0c 100644
--- a/source3/smbd/notify.c
+++ b/source3/smbd/notify.c
@@ -159,7 +159,8 @@ void change_notify_reply(const char *request_buf, uint32 max_param_count,
}
NTSTATUS change_notify_add_request(const char *inbuf, uint32 max_param_count,
- uint32 filter, struct files_struct *fsp)
+ uint32 filter, BOOL recursive,
+ struct files_struct *fsp)
{
struct notify_change_request *request = NULL;
struct notify_mid_map *map = NULL;
@@ -177,9 +178,7 @@ NTSTATUS change_notify_add_request(const char *inbuf, uint32 max_param_count,
request->max_param_count = max_param_count;
request->filter = filter;
request->fsp = fsp;
-
- request->backend_data = cnotify->notify_add(NULL, smbd_event_context(),
- fsp, &request->filter);
+ request->backend_data = NULL;
DLIST_ADD_END(fsp->notify->requests, request,
struct notify_change_request *);
@@ -343,6 +342,18 @@ void notify_action(connection_struct *conn, const char *parent,
return;
}
+ {
+ char *fullpath;
+
+ if (asprintf(&fullpath, "%s/%s/%s", conn->connectpath,
+ parent, name) != -1) {
+ notify_trigger(conn->notify_ctx, action, filter,
+ fullpath);
+ SAFE_FREE(fullpath);
+ }
+ return;
+ }
+
if (!(lck = get_share_mode_lock(NULL, sbuf.st_dev, sbuf.st_ino,
NULL, NULL))) {
return;
@@ -405,20 +416,21 @@ void notify_action(connection_struct *conn, const char *parent,
void notify_fname(connection_struct *conn, uint32 action, uint32 filter,
const char *path)
{
- char *parent;
- const char *name;
+ char *fullpath;
- if (!parent_dirname_talloc(tmp_talloc_ctx(), path, &parent, &name)) {
+ if (asprintf(&fullpath, "%s/%s", conn->connectpath, path) == -1) {
+ DEBUG(0, ("asprintf failed\n"));
return;
}
- notify_action(conn, parent, name, filter, action);
- TALLOC_FREE(parent);
+ notify_trigger(conn->notify_ctx, action, filter, fullpath);
+ SAFE_FREE(fullpath);
}
-void notify_fsp(files_struct *fsp, uint32 action, char *name)
+void notify_fsp(files_struct *fsp, uint32 action, const char *name)
{
struct notify_change *change, *changes;
+ char *name2;
if (fsp->notify == NULL) {
/*
@@ -427,35 +439,12 @@ void notify_fsp(files_struct *fsp, uint32 action, char *name)
return;
}
- if (fsp->notify->requests != NULL) {
- /*
- * Someone is waiting for the change, trigger the reply
- * immediately.
- *
- * TODO: do we have to walk the lists of requests pending?
- */
-
- struct notify_change_request *req = fsp->notify->requests;
- struct notify_change onechange;
-
- if (name == NULL) {
- /*
- * Catch-all change, possibly from notify_hash.c
- */
- change_notify_reply(req->request_buf,
- req->max_param_count,
- -1, NULL);
+ if (!(name2 = talloc_strdup(fsp->notify, name))) {
+ DEBUG(0, ("talloc_strdup failed\n"));
return;
}
- onechange.action = action;
- onechange.name = name;
-
- change_notify_reply(req->request_buf, req->max_param_count,
- 1, &onechange);
- change_notify_remove_request(req);
- return;
- }
+ string_replace(name2, '/', '\\');
/*
* Someone has triggered a notify previously, queue the change for
@@ -468,6 +457,7 @@ void notify_fsp(files_struct *fsp, uint32 action, char *name)
* W2k3 seems to store at most 30 changes.
*/
TALLOC_FREE(fsp->notify->changes);
+ TALLOC_FREE(name2);
fsp->notify->num_changes = -1;
return;
}
@@ -480,6 +470,7 @@ void notify_fsp(files_struct *fsp, uint32 action, char *name)
fsp->notify, fsp->notify->changes,
struct notify_change, fsp->notify->num_changes+1))) {
DEBUG(0, ("talloc_realloc failed\n"));
+ TALLOC_FREE(name2);
return;
}
@@ -487,14 +478,40 @@ void notify_fsp(files_struct *fsp, uint32 action, char *name)
change = &(fsp->notify->changes[fsp->notify->num_changes]);
- if (!(change->name = talloc_strdup(changes, name))) {
- DEBUG(0, ("talloc_strdup failed\n"));
- return;
- }
+ change->name = talloc_move(changes, &name2);
change->action = action;
fsp->notify->num_changes += 1;
+ if (fsp->notify->requests == NULL) {
+ /*
+ * Nobody is waiting, so don't send anything. The ot
+ */
+ return;
+ }
+
+ if (action == NOTIFY_ACTION_OLD_NAME) {
+ /*
+ * We have to send the two rename events in one reply. So hold
+ * the first part back.
+ */
return;
+ }
+
+ /*
+ * Someone is waiting for the change, trigger the reply immediately.
+ *
+ * TODO: do we have to walk the lists of requests pending?
+ */
+
+ change_notify_reply(fsp->notify->requests->request_buf,
+ fsp->notify->requests->max_param_count,
+ fsp->notify->num_changes,
+ fsp->notify->changes);
+
+ change_notify_remove_request(fsp->notify->requests);
+
+ TALLOC_FREE(fsp->notify->changes);
+ fsp->notify->num_changes = 0;
}
static void notify_message_callback(int msgtype, struct process_id pid,