summaryrefslogtreecommitdiff
path: root/common/inotify_helpers.c
diff options
context:
space:
mode:
authorLuke Shumaker <lukeshu@sbcglobal.net>2014-11-28 16:33:57 -0500
committerLuke Shumaker <lukeshu@sbcglobal.net>2014-11-28 16:33:57 -0500
commitbc25cc045d6d4fdb6b20707cdec4da14890ee9d1 (patch)
tree76914ec4cd7af6444892b51016853b8a480f8a2e /common/inotify_helpers.c
parentd8c48a5aae8f3561cec14f7f08c35fc3619ef00a (diff)
cleanup inotify helpers
Diffstat (limited to 'common/inotify_helpers.c')
-rw-r--r--common/inotify_helpers.c140
1 files changed, 87 insertions, 53 deletions
diff --git a/common/inotify_helpers.c b/common/inotify_helpers.c
index 0aac023..781843e 100644
--- a/common/inotify_helpers.c
+++ b/common/inotify_helpers.c
@@ -1,52 +1,9 @@
-#include <stdio.h>
-#include <stdlib.h>
-
+#include <stdio.h> /* for printf(3) */
+#include <stdlib.h> /* for realloc(3), memcpy(3) */
+#include <unistd.h> /* for read(2) */
#include "inotify_helpers.h"
-static
-const char *in_bits[] = {
- /* main */
- "IN_ACCESS", // 0
- "IN_MODIFY", // 1
- "IN_ATTRIB", // 2
- "IN_CLOSE_WRITE", // 3
- "IN_CLOSE_NOWRITE", // 4
- "IN_OPEN", // 5
- "IN_MOVED_FROM", // 6
- "IN_MOVED_TO", // 7
- "IN_CREATE", // 8
- "IN_DELETE", // 9
- "IN_DELETE_SELF", // 10
- "IN_MOVE_SELF", // 11
- /* gap */
- "<invalid-12>", // 12
- /* events sent by the kernel */
- "IN_UNMOUNT", // 13
- "IN_Q_OVERFLOW", // 14
- "IN_IGNORED", // 15
- /* gap */
- "<invalid-16>", // 16
- "<invalid-17>", // 17
- "<invalid-18>", // 18
- "<invalid-19>", // 19
- "<invalid-20>", // 20
- "<invalid-21>", // 21
- "<invalid-22>", // 22
- "<invalid-23>", // 23
- /* special flags */
- "IN_ONLYDIR", // 24
- "IN_DONT_FOLLOW", // 25
- "IN_EXCL_UNLINK", // 26
- "<invalid-27>", // 27
- "<invalid-28>", // 28
- "IN_MASK_ADD", // 29
- "IN_ISDIR", // 30
- "IN_ONESHOT", // 31
-};
-
-char *inotify_mask2str(uint32 mask);
-int inotify_print_event(FILE *file, struct inotify_event *event);
-
+
struct strbuf {
char *str;
@@ -55,7 +12,8 @@ struct strbuf {
};
static
-void strbufcat(struct strbuf *a, const char *b) {
+void
+strbufcat(struct strbuf *a, const char *b) {
size_t blen = strlen(b);
while (a->cap <= (a->len + blen)) {
a->cap += 256;
@@ -65,20 +23,68 @@ void strbufcat(struct strbuf *a, const char *b) {
a->len += blen;
}
+
-char *inotify_mask2str(uint32_t mask) {
- struct strbuf out = { NULL, 0, 0 };
- for (size_t i = 0; i < sizeof(in_bits)/sizeof(in_bits[0]); i++) {
+static
+const char *in_mask_bits[] = {
+ /* main */
+ "IN_ACCESS", // 0
+ "IN_MODIFY", // 1
+ "IN_ATTRIB", // 2
+ "IN_CLOSE_WRITE", // 3
+ "IN_CLOSE_NOWRITE", // 4
+ "IN_OPEN", // 5
+ "IN_MOVED_FROM", // 6
+ "IN_MOVED_TO", // 7
+ "IN_CREATE", // 8
+ "IN_DELETE", // 9
+ "IN_DELETE_SELF", // 10
+ "IN_MOVE_SELF", // 11
+ /* gap */
+ "<invalid-12>", // 12
+ /* events sent by the kernel */
+ "IN_UNMOUNT", // 13
+ "IN_Q_OVERFLOW", // 14
+ "IN_IGNORED", // 15
+ /* gap */
+ "<invalid-16>", // 16
+ "<invalid-17>", // 17
+ "<invalid-18>", // 18
+ "<invalid-19>", // 19
+ "<invalid-20>", // 20
+ "<invalid-21>", // 21
+ "<invalid-22>", // 22
+ "<invalid-23>", // 23
+ /* special flags */
+ "IN_ONLYDIR", // 24
+ "IN_DONT_FOLLOW", // 25
+ "IN_EXCL_UNLINK", // 26
+ "<invalid-27>", // 27
+ "<invalid-28>", // 28
+ "IN_MASK_ADD", // 29
+ "IN_ISDIR", // 30
+ "IN_ONESHOT", // 31
+};
+
+char *
+inotify_mask2str(uint32_t mask) {
+ struct strbuf out = { 0 };
+ for (size_t i = 0;
+ i < sizeof(in_mask_bits)/sizeof(in_mask_bits[0]);
+ i++) {
if (mask & (1 << i)) {
if (out.len > 0)
- strbufcat(&out, ", ");
+ strbufcat(&out, " | ");
strbufcat(&out, in_bits[i]);
}
}
return out.str;
}
-int inotify_print_event(struct inotify_event *event) {
+
+
+int
+inotify_print_event(struct inotify_event *event) {
return printf("wd:%d\n"
"\tmask:[%s]\n"
"\tcookie:%u\n"
@@ -90,3 +96,31 @@ int inotify_print_event(struct inotify_event *event) {
event->len,
event->len > 0 ? event->name : "");
}
+
+
+
+#define EVENT_PTR(BUF) ((struct inotify_event *)&((BUF)->dat[(BUF)->pos]))
+#define EVENT_SIZE(BUF) (sizeof(struct inotify_event) + EVENT_PTR(BUF)->len)
+
+struct inotify_event *
+inotify_next_event_r(int fd, struct inotify_buffer *buf) {
+ if (((ssize_t)(buf->len - buf->pos - sizeof(struct inotify_event)) > 0)
+ && ((ssize_t)(buf->len - buf->pos - EVENT_SIZE(buf)) > 0)) {
+ buf->pos += EVENT_SIZE(buf);
+ } else {
+ do {
+ buf->len = read(fd, buf->dat, sizeof(buf->dat));
+ } while (buf->len == 0);
+ buf->pos = 0;
+ if (buf->len < 0) {
+ return NULL;
+ }
+ }
+ return EVENT_PTR(buf);
+}
+
+struct inotify_event *
+inotify_next_event(int fd) {
+ static struct inotify_buffer buf = { 0 };
+ return inotify_next_event_r(fd, &buf);
+}