/*
 * Copyright 2001, 2002, 2003 Adam Sampson <ats@offog.org>
 *
 * Permission to use, copy, modify, and/or distribute this software for any
 * purpose with or without fee is hereby granted, provided that the above
 * copyright notice and this permission notice appear in all copies.
 *
 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
 */

#include <unistd.h>
#include <stdlib.h>
#include <errno.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <string.h>
#include "iolib.h"
#include "freedt.h"
#include "config.h"
const char *progname = "svc";
const char *proghelp =
	"Usage: svc [OPTIONS] servicedir [servicedir ...]\n"
	"Control a running supervise.\n\n"
	"Commands sent to specified services in the order given on the command line:\n"
	"-u        Bring service up\n"
	"-d        Bring service down\n"
	"-o        Run service once\n"
	"-p        Send SIGSTOP\n"
	"-c        Send SIGCONT\n"
	"-h        Send SIGHUP\n"
	"-a        Send SIGALRM\n"
	"-i        Send SIGINT\n"
	"-t        Send SIGTERM\n"
	"-k        Send SIGKILL\n"
	"-X        Bring service down, then end supervise\n"
	"-x        End supervise when the child exits\n"
	"Normal options:\n";

int main(int argc, char **argv) {
	char *valid_cmds = "V?xXudopchaitk";
	buffer cmds = BUFFER;
	int dirfd;

	while (1) {
		int c = getopt(argc, argv, valid_cmds);

		if (c == -1)
			break;
		if (c == 'V')
			version();
		if (c == '?' || strchr(valid_cmds, c) == NULL)
			help();
		bappendc(&cmds, c);
	}

	if ((argc - optind) < 1)
		help();

	dirfd = open(".", O_RDONLY);
	if (dirfd < 0)
		die("unable to open current directory");	

	for (; optind < argc; optind++) {
		int fd = -1;
		const char *p;

		if (fchdir(dirfd) < 0)	
			die("unable to change back to original directory");

		if (chdir(argv[optind]) < 0) {
			warn2(argv[optind], "unable to chdir to service dir");
			goto nextservice;
		}
	
		fd = open("supervise/control", O_WRONLY | O_NONBLOCK);
		if (fd < 0) {
			if (errno == ENXIO) {
				warn2(argv[optind],
					"no supervise running for service");
			} else {
				warn2(argv[optind],
					"unable to open control pipe");
			}
			goto nextservice;
		}

		p = bstr(&cmds);
		while (*p != '\0') {
			if (write(fd, p++, 1) < 0) {
				warn2(argv[optind], "unable to write "
					"to control pipe");
				goto nextservice;
			}
		}

	nextservice:
		if (fd >= 0)
			close(fd);
	}

	bfree(&cmds);
	return 0;
}

