/* vi: set sw=4 ts=4: */
/*
 * simple ACPI events listener
 *
 * Copyright (C) 2008 by Vladimir Dronnikov <dronnikov@gmail.com>
 *
 * Licensed under GPLv2, see file LICENSE in this tarball for details.
 */
#include "libbb.h"

#include <linux/input.h>
#ifndef SW_RFKILL_ALL
# define SW_RFKILL_ALL 3
#endif

/*
 * acpid listens to ACPI events coming either in textual form
 * from /proc/acpi/event (though it is marked deprecated,
 * it is still widely used and _is_ a standard) or in binary form
 * from specified evdevs (just use /dev/input/event*).
 * It parses the event to retrieve ACTION and a possible PARAMETER.
 * It then spawns /etc/acpi/<ACTION>[/<PARAMETER>] either via run-parts
 * (if the resulting path is a directory) or directly.
 * If the resulting path does not exist it logs it via perror
 * and continues listening.
 */

static void process_event(const char *event)
{
	struct stat st;
	char *handler = xasprintf("./%s", event);
	const char *args[] = { "run-parts", handler, NULL };

	// debug info
	if (option_mask32 & 8) { // -d
		bb_error_msg("%s", event);
	}

	// spawn handler
	// N.B. run-parts would require scripts to have #!/bin/sh
	// handler is directory? -> use run-parts
	// handler is file? -> run it directly
	if (0 == stat(event, &st))
		spawn((char **)args + (0==(st.st_mode & S_IFDIR)));
	else
		bb_simple_perror_msg(event);
	free(handler);
}

/*
 * acpid [-c conf_dir] [-l log_file] [-e proc_event_file] [evdev_event_file...]
*/

int acpid_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE;
int acpid_main(int argc, char **argv)
{
	struct pollfd *pfd;
	int i, nfd;
	const char *opt_conf = "/etc/acpi";
	const char *opt_input = "/proc/acpi/event";
	const char *opt_logfile = "/var/log/acpid.log";

	getopt32(argv, "c:e:l:d"
		IF_FEATURE_ACPID_COMPAT("g:m:s:S:v"),
		&opt_conf, &opt_input, &opt_logfile
		IF_FEATURE_ACPID_COMPAT(, NULL, NULL, NULL, NULL, NULL)
	);

	// daemonize unless -d given
	if (!(option_mask32 & 8)) { // ! -d
		bb_daemonize_or_rexec(0, argv);
		close(2);
		xopen(opt_logfile, O_WRONLY | O_CREAT | O_TRUNC);
	}

	argv += optind;

	// goto configuration directory
	xchdir(opt_conf);

	// prevent zombies
	signal(SIGCHLD, SIG_IGN);

	// no explicit evdev files given? -> use proc event interface
	if (!*argv) {
		// proc_event file is just a "config" :)
		char *token[4];
		parser_t *parser = config_open(opt_input);

		// dispatch events
		while (config_read(parser, token, 4, 4, "\0 ", PARSE_NORMAL)) {
			char *event = xasprintf("%s/%s", token[1], token[2]);
			process_event(event);
			free(event);
		}

		if (ENABLE_FEATURE_CLEAN_UP)
			config_close(parser);
		return EXIT_SUCCESS;
	}

	// evdev files given, use evdev interface

	// open event devices
	pfd = xzalloc(sizeof(*pfd) * (argc - optind));
	nfd = 0;
	while (*argv) {
		pfd[nfd].fd = open_or_warn(*argv++, O_RDONLY | O_NONBLOCK);
		if (pfd[nfd].fd >= 0)
			pfd[nfd++].events = POLLIN;
	}

	// dispatch events
	while (/* !bb_got_signal && */ poll(pfd, nfd, -1) > 0) {
		for (i = 0; i < nfd; i++) {
			const char *event;
			struct input_event ev;

			if (!(pfd[i].revents & POLLIN))
				continue;

			if (sizeof(ev) != full_read(pfd[i].fd, &ev, sizeof(ev)))
				continue;
//bb_info_msg("%d: %d %d %4d", i, ev.type, ev.code, ev.value);

			// filter out unneeded events
			if (ev.value != 1)
				continue;

			event = NULL;

			// N.B. we will conform to /proc/acpi/event
			// naming convention when assigning event names

			// TODO: do we want other events?

			// power and sleep buttons delivered as keys pressed
			if (EV_KEY == ev.type) {
				if (KEY_POWER == ev.code)
					event = "PWRF/00000080";
				else if (KEY_SLEEP == ev.code)
					event = "SLPB/00000080";
			}
			// switches
			else if (EV_SW == ev.type) {
				if (SW_LID == ev.code)
					event = "LID/00000080";
				else if (SW_RFKILL_ALL == ev.code)
					event = "RFKILL";
			}
			// filter out unneeded events
			if (!event)
				continue;

			// spawn event handler
			process_event(event);
		}
	}

	if (ENABLE_FEATURE_CLEAN_UP) {
		for (i = 0; i < nfd; i++)
			close(pfd[i].fd);
		free(pfd);
	}

	return EXIT_SUCCESS;
}
