示例#1
0
int
main(int ac, char **av)
{
	int	x;
	char	*file = (char *)NULL;
	pid_t	pid = 0;
	int	uucpstyle = FALSE;	/* indicating UUCP style locks */
	int	only_check = TRUE;	/* don't make a lock */

	Pname = ((Pname = strrchr(av[0], '/')) ? Pname + 1 : av[0]);

	for(x = 1; x < ac; x++) {
		if (av[x][0] == '-') {
			switch(av[x][1]) {
			case 'u':
				uucpstyle = TRUE;
				break;
			case 'd':
				Debug = TRUE;
				break;
			case 'p':
				if (strlen(av[x]) > 2) {
					pid = atoi(&av[x][2]);
				} else {
					if (++x >= ac) {
						bad_usage();
					}
					pid = atoi(av[x]);
				}
				only_check = FALSE;	/* wants one */
				break;
			case 'f':
				if (strlen(av[x]) > 2) {
					file = &av[x][2];
				} else {
					if (++x >= ac) {
						bad_usage();
					}
					file = av[x];
				}
				break;
			default:
				bad_usage();
			}
		}
	}

	if (file == (char *)NULL || (!only_check && pid <= 0)) {
		bad_usage();
	}

	if (only_check) {
		exit(cklock(file, uucpstyle) ? LOCK_GOOD : LOCK_BAD);
	}

	exit(mklock(file, pid, uucpstyle) ? LOCK_SET : LOCK_FAIL);
}
示例#2
0
/*
 * Open a file, locking using the lock types specified. Returns EAGAIN if lock
 * failed.
 */
int
openlock(const char *path, int flags, u_int locks)
{
	int	fd, saved_errno;

	if (mklock(locks, path) != 0)
		return (-1);
	if ((fd = open(path, flags, 0)) == -1)
		goto error;
	if (lockfd(locks, fd) != 0)
		goto error;

	return (fd);

error:
	saved_errno = errno;
	close(fd);
	rmlock(locks, path);
	errno = saved_errno;
	return (-1);
}
示例#3
0
/* Create a locked file. */
int
createlock(
    const char *path, int flags, uid_t uid, gid_t gid, mode_t mode, u_int locks)
{
	int	fd, saved_errno;

	if (mklock(locks, path) != 0)
		return (-1);
	if ((fd = xcreate(path, flags, uid, gid, mode)) == -1)
		goto error;
	if (lockfd(locks, fd) != 0)
		goto error;

	return (fd);

error:
	saved_errno = errno;
	close(fd);
	rmlock(locks, path);
	errno = saved_errno;
	return (-1);
}
示例#4
0
文件: cron.c 项目: 99years/plan9
static int
mklock(char *file)
{
	int fd, try;
	Dir *dir;

	fd = openlock(file);
	if (fd >= 0) {
		/* make it a lock file if it wasn't */
		dir = dirfstat(fd);
		if (dir == nil)
			error("%s vanished: %r", file);
		dir->mode |= DMEXCL;
		dir->qid.type |= QTEXCL;
		dirfwstat(fd, dir);
		free(dir);

		/* reopen in case it wasn't a lock file at last open */
		close(fd);
	}
	for (try = 0; try < 65 && (fd = openlock(file)) < 0; try++)
		sleep(10*1000);
	return fd;
}

void
main(int argc, char *argv[])
{
	Job *j;
	Tm tm;
	Time t;
	ulong now, last;		/* in seconds */
	int i, lock;

	debug = 0;
	ARGBEGIN{
	case 'c':
		createuser();
		exits(0);
	case 'd':
		debug = 1;
		break;
	default:
		usage();
	}ARGEND

	if(debug){
		readalljobs();
		printjobs();
		exits(0);
	}

	initcap();		/* do this early, before cpurc removes it */

	switch(fork()){
	case -1:
		fatal("can't fork: %r");
	case 0:
		break;
	default:
		exits(0);
	}

	/*
	 * it can take a few minutes before the file server notices that
	 * we've rebooted and gives up the lock.
	 */
	lock = mklock("/cron/lock");
	if (lock < 0)
		fatal("cron already running: %r");

	argv0 = "cron";
	srand(getpid()*time(0));
	last = time(0);
	for(;;){
		readalljobs();
		/*
		 * the system's notion of time may have jumped forward or
		 * backward an arbitrary amount since the last call to time().
		 */
		now = time(0);
		/*
		 * if time has jumped backward, just note it and adapt.
		 * if time has jumped forward more than a day,
		 * just execute one day's jobs.
		 */
		if (now < last) {
			clog("time went backward");
			last = now;
		} else if (now - last > Day) {
			clog("time advanced more than a day");
			last = now - Day;
		}
		now = minute(now);
		for(last = minute(last); last <= now; last += Minute){
			tm = *localtime(last);
			t.min = 1ULL << tm.min;
			t.hour = 1 << tm.hour;
			t.wday = 1 << tm.wday;
			t.mday = 1 << tm.mday;
			t.mon =  1 << (tm.mon + 1);
			for(i = 0; i < nuser; i++)
				for(j = users[i].jobs; j; j = j->next)
					if(j->time.min & t.min
					&& j->time.hour & t.hour
					&& j->time.wday & t.wday
					&& j->time.mday & t.mday
					&& j->time.mon & t.mon)
						rexec(&users[i], j);
		}
		seek(lock, 0, 0);
		write(lock, "x", 1);	/* keep the lock alive */
		/*
		 * if we're not at next minute yet, sleep until a second past
		 * (to allow for sleep intervals being approximate),
		 * which synchronises with minute roll-over as a side-effect.
		 */
		sleepuntil(now + Minute + 1);
	}
	/* not reached */
}
示例#5
0
/*
 * get next conversation sequence number
 *	rmtname	-> name of remote system
 * returns:
 *	0	-> no entery
 *	1	-> 0 sequence number
 */
int
gnxseq(char *rmtname)
{
	register FILE *fp0, *fp1;
	register struct tm *tp;
	int count = 0, ct, ret;
	char buf[BUFSIZ], name[NAMESIZE];
	time_t clock;

	if (access(SQFILE, 0) != 0)
		return (0);

	{
		int i;
		for (i = 0; i < 5; i++)
			if ((ret = mklock(SQLOCK)) == SUCCESS)
				break;
		sleep(5);
	}
	if (ret != SUCCESS) {
		logent("CAN'T LOCK", SQLOCK);
		DEBUG(4, "can't lock %s\n", SQLOCK);
		return (0);
	}
	if ((fp0 = fopen(SQFILE, "r")) == NULL)
		return (0);
	if ((fp1 = fopen(SQTMP, "w")) == NULL) {
		fclose(fp0);
		return (0);
	}
	chmod(SQTMP, DFILEMODE);

	while (fgets(buf, BUFSIZ, fp0) != NULL) {
		ret = sscanf(buf, "%s%d", name, &ct);
		if (ret < 2)
			ct = 0;
		name[7] = '\0';
		if (ct > 9998)
			ct = 0;
		if (strncmp(rmtname, name, SYSNSIZE) != SAME) {
			fputs(buf, fp1);
			continue;
		}

		/*
		 * found name
		 */
		count = ++ct;
		time(&clock);
		tp = localtime(&clock);
		fprintf(fp1, "%s %d %d/%d-%d:%2.2d\n", name, ct,
		    tp->tm_mon + 1, tp->tm_mday, tp->tm_hour,
		    tp->tm_min);

		/*
		 * write should be checked
		 */
		while (fgets(buf, BUFSIZ, fp0) != NULL)
			fputs(buf, fp1);
	}
	fclose(fp0);
	fclose(fp1);
	if (count == 0) {
		rmlock(SQLOCK);
		unlink(SQTMP);
	}
	return (count);
}