/** * Detect and notify about the changes in the watched directory. * * This function is top-level and it operates with other specific routines * to notify about different sets of events in a different conditions. * * @param[in] wrk A pointer to #worker. * @param[in] w A pointer to #watch. * @param[in] event A pointer to the received kqueue event. **/ void produce_directory_diff (worker *wrk, watch *w, struct kevent *event) { assert (wrk != NULL); assert (w != NULL); assert (event != NULL); assert (w->type == WATCH_USER); assert (w->is_directory); dep_list *was = NULL, *now = NULL; was = dl_shallow_copy (w->deps); now = dl_listing (w->filename); if (now == NULL && errno != ENOENT) { /* Why do I skip ENOENT? Because the directory could be deleted at this * point */ perror_msg ("Failed to create a listing for directory %s", w->filename); dl_shallow_free (was); return; } dl_shallow_free (w->deps); w->deps = now; bulk_events be; memset (&be, 0, sizeof (be)); handle_context ctx; memset (&ctx, 0, sizeof (ctx)); ctx.wrk = wrk; ctx.w = w; ctx.be = &be; dl_calculate (was, now, &cbs, &ctx); if (be.memory) { safe_write (wrk->io[KQUEUE_FD], be.memory, be.size); free (be.memory); } dl_free (was); }
void _kh_dir_diff (kqueue_sub *sub, GFileMonitorSource *source) { dep_list *was; handle_ctx ctx; g_assert (sub != NULL); g_assert (source != NULL); memset (&ctx, 0, sizeof (handle_ctx)); ctx.sub = sub; ctx.source = source; was = sub->deps; sub->deps = dl_listing (sub->filename); dl_calculate (was, sub->deps, &cbs, &ctx); dl_free (was); }