V10/cmd/backup.old/bpush.c

Compare this file to the similar file:
Show the results in this format:

#include	<fio.h>
#include	<ipc.h>
#include	<pwd.h>
#include	<grp.h>
#include	<errno.h>
#include	"backup.h"
#include	<string.h>
#include	<signal.h>

struct backfile h;
extern int errno;
int ofd;
char *fname;
unsigned short csum;

main(argc, argv)
	char **argv;
{
	char *s, *ss, buf[FNAMELEN];
	char *mach;
	int ifd;
	int retry = 0;
	extern long atol();

	signal(SIGPIPE, SIG_IGN);/**/
	chdir("/tmp");
	backupdir(buf);
	mach = strchr(buf, 0)+1;
	if(rx(mach, "bkprcv", (char *)0, "heavy", &ifd, &ofd))
		exit(1);
	if(*++argv == 0)
		*--argv = "??";
	write(ofd, *argv, strlen(*argv)+1);
	while(s = Frdline(0)){
		if((ss = strrchr(s, ' ')) == 0){
			exit(2);
		}
		*ss++ = 0;
		fname = s;
		while(*s)
			if((s[0] == '/') && (s[1] == '/')){
				*s = 0;
				break;
			} else
				s++;
		while(do1(fname, atol(ss))){
			if(!retry)
				goto done;
			h.version = -1;
			WRITE((char *)&h, sizeof h);
			close(ifd);
			close(ofd);
			sleep(20);
			fprint(2, "retrying: ");
			if(rx(mach, "bkprcv", (char *)0, "heavy", &ifd, &ofd))
				exit(1);
			write(ofd, *argv, strlen(*argv)+1);
		}
	}
done:
	h.version = -1;
	WRITE((char *)&h, sizeof h);
	Finit(ifd, (char *)0);
	s = Frdline(ifd);
	if(argc > 2){
		if(s)
			fprint(2, "file transfer: %s\n", s);
		else
			fprint(2, "uh oh! i didn't get the transmission statistics!\n");
	}
	exit(0);
}

do1(file, size)
	char *file;
	long size;
{
	register ifd, n;
	char buf[512];
	struct passwd *p;
	struct group *g;
	int ret = 0;

	if((ifd = open(file, 0)) < 0){
		if(errno != ENOENT)	/* don't bitch about missing files */
			perror(file);
		return(ret);
	}
	memset((char *)&h, 0, sizeof h);
	h.version = CURVERSION;
	h.checksum = 0;		 /* done later */
	if(getflab(file, &h.lab) < 0){
		perror(file);
		exit(9);
	}
	if(lstat(file, &h.sbuf) < 0){
		perror(file);
		exit(4);
	}
	if(size > sizeof h + h.sbuf.st_size)
		size = sizeof h + h.sbuf.st_size;
	else if(size < sizeof h + h.sbuf.st_size)
		h.sbuf.st_size = size - sizeof h;
	if(p = getpwuid(h.sbuf.st_uid))
		strcpy(h.uname, p->pw_name);
	else
		sprint(h.uname, "#%d", h.sbuf.st_uid);
	setgrent();
	if(g = getgrgid(h.sbuf.st_gid))
		strcpy(h.gname, g->gr_name);
	else
		sprint(h.gname, "#%d", h.sbuf.st_gid);
	strncpy(h.oname, file, FNAMELEN);
	h.oname[FNAMELEN-1] = 0;
	h.bname[0] = 0;
	csum = sum(((unsigned char *)&h)+2, sizeof h - 2, 0);
	WRITE((char *)&h, sizeof(h));
	size -= sizeof h;
	switch(h.sbuf.st_mode&S_IFMT)
	{
	case S_IFLNK:
		if(readlink(file, buf, sizeof buf) < 0){
			perror(file);
			exit(5);
		}
		WRITE(buf, (int)size);
		csum = sum((unsigned char *)buf, (int)size, csum);
		break;
	case S_IFDIR:
		if(dsend(file, size)){
			perror(file);
			exit(6);
		}
		break;
	case S_IFREG:
		if(send(ifd, size)){
			perror(file);
			exit(3);
		}
		break;
	}
	close(ifd);
	WRITE((char *)&csum, 2);
	ifd = 0;
	while((n = read(ofd, buf, sizeof buf)) > 0){
		if((n == 1) && (buf[0] == 'X'))
			break;
		if(buf[0] == '@')
			write(2, buf+1, n-1);
		else if(buf[0] == '*'){
			if(ret == 0)
				write(2, buf+1, n-1);
			ret = 1;
		} else {
			write(2, buf, n);
			ifd = 1;
		}
	}
	if(ifd)
		exit(8);
	return(ret);
}

send(ifd, size)
	long size;
{
	char buf[512];
	int n;

	while((n = read(ifd, buf, sizeof buf)) > 0){
		if(n < 0)
			return(1);
		if(n > size) n = size;
		if(n)
			WRITE(buf, n);
		csum = sum((unsigned char *)buf, n, csum);
		if((size -= n) == 0) break;
	}
	memset(buf, 0, sizeof buf);
	while(size){
		n = min((int)size, sizeof buf);
		write(ofd, buf, n);
		csum = sum((unsigned char *)buf, n, csum);
		size -= n;
	}
	return(0);
}

#include	<ndir.h>

dsend(name, size)
	char *name;
	long size;
{
	char buf[512];
	int n;
	DIR *dirp;
	register struct direct *d;

	memset(buf, 0, 4);
	WRITE(buf, 4);
	csum = sum((unsigned char *)buf, 4, csum);
	size -= 5;	/* one later on */
	dirp = opendir(name);
	while(d = readdir(dirp)){
		n = d->d_namlen+1;
		if(n > size)
			break;
		WRITE(d->d_name, n);
		csum = sum((unsigned char *)d->d_name, n, csum);
		size -= n;
	}
	closedir(dirp);
	memset(buf, 0, sizeof buf);
	csum = sum((unsigned char *)buf, 1, csum);
	WRITE(buf, 1);
	while(size){
		n = min((int)size, sizeof buf);
		WRITE(buf, n);
		csum = sum((unsigned char *)buf, n, csum);
		size -= n;
	}
	return(0);
}

WRITE(b, n)
	char *b;
{
	register ret;

	if((ret = write(ofd, b, n)) != n){
		fprint(2, "%s: write(%d)=%d", fname, n, ret);
		perror("");
		exit(7);
	}
}