예제 #1
0
파일: test.c 프로젝트: kspaans/CS499
__attribute__((unused)) static void task_reclamation_test(void) {
	for(int i=0; i<1000; ++i) {
		printf("%05x ", spawn(1, null_task, 0));
		printf("%05x ", spawn(1, null_task, 0));
		printf("%05x\n", spawn(3, null_task, 0));
	}
	xspawn(4, task_reclamation_2, 0);
}
예제 #2
0
int inotifyd_main(int argc UNUSED_PARAM, char **argv)
{
	int n;
	unsigned mask = IN_ALL_EVENTS; // assume we want all events
	struct pollfd pfd;
	char **watched = ++argv; // watched name list
	const char *args[] = { *argv, NULL, NULL, NULL, NULL };

	// sanity check: agent and at least one watch must be given
	if (!argv[1])
		bb_show_usage();

	// open inotify
	pfd.fd = inotify_init();
	if (pfd.fd < 0)
		bb_perror_msg_and_die("no kernel support");

	// setup watched
	while (*++argv) {
		char *path = *argv;
		char *masks = strchr(path, ':');
		// if mask is specified ->
		if (masks) {
			*masks = '\0'; // split path and mask
			// convert mask names to mask bitset
			mask = 0;
			while (*++masks) {
				int i = strchr(mask_names, *masks) - mask_names;
				if (i >= 0) {
					mask |= (1 << i);
				}
			}
		}
		// add watch
		n = inotify_add_watch(pfd.fd, path, mask);
		if (n < 0)
			bb_perror_msg_and_die("add watch (%s) failed", path);
		//bb_error_msg("added %d [%s]:%4X", n, path, mask);
	}

	// setup signals
	bb_signals(BB_FATAL_SIGS, record_signo);

	// do watch
	pfd.events = POLLIN;
	while (1) {
		ssize_t len;
		void *buf;
		struct inotify_event *ie;

 again:
		if (bb_got_signal)
			break;
		n = poll(&pfd, 1, -1);
		/* Signal interrupted us? */
		if (n < 0 && errno == EINTR)
			goto again;
		// Under Linux, above if() is not necessary.
		// Non-fatal signals, e.g. SIGCHLD, when set to SIG_DFL,
		// are not interrupting poll().
		// Thus we can just break if n <= 0 (see below),
		// because EINTR will happen only on SIGTERM et al.
		// But this might be not true under other Unixes,
		// and is generally way too subtle to depend on.
		if (n <= 0) // strange error?
			break;

		// read out all pending events
		xioctl(pfd.fd, FIONREAD, &len);
#define eventbuf bb_common_bufsiz1
		ie = buf = (len <= sizeof(eventbuf)) ? eventbuf : xmalloc(len);
		len = full_read(pfd.fd, buf, len);
		// process events. N.B. events may vary in length
		while (len > 0) {
			int i;
			char events[sizeof(mask_names)];
			char *s = events;
			unsigned m = ie->mask;

			for (i = 0; i < sizeof(mask_names)-1; ++i, m >>= 1) {
				if (m & 1)
					*s++ = mask_names[i];
			}
			*s = '\0';
			//bb_error_msg("exec %s %08X\t%s\t%s\t%s", agent,
			// ie->mask, events, watched[ie->wd], ie->len ? ie->name : "");
			args[1] = events;
			args[2] = watched[ie->wd];
			args[3] = ie->len ? ie->name : NULL;
			wait4pid(xspawn((char **)args));
			// next event
			i = sizeof(struct inotify_event) + ie->len;
			len -= i;
			ie = (void*)((char*)ie + i);
		}
		if (eventbuf != buf)
			free(buf);
	}

	return EXIT_SUCCESS;
}