[comp.sources.bugs] pax tar append bugfix and MSDOS port

walters@oksce1.okstate.edu (Harold G. Walters) (02/16/89)

Enclosed are the patches to apply to version 1.2 of pax and files to fix
the tar append bug and port to MSDOS.  It supports both the DOS
filesystem and the "tape on a disk" system used by micro UN*X systems. 
ALL the MSDOS stuff is "#ifdef"ed so it will still compile on other
machines.  The patches patch Makefile and config.h so you might want to
save your current one before applying.  If so you will then need to add
backsp.c to the SRC line and backsp.o to the OBJ line in the makefile. 
The tar append bugfix has been tested on Ultrix v2.2 and MSDOS. 

--
Harold G. Walters			walters@1.ce.okstate.edu
School of Civil Engineering		okstate!oksce1!walters
Oklahoma State University		"If all you have is a hammer, 
Stillwater, OK  74078			 everything looks like a nail".

#! /bin/sh
# This is a shell archive.  Remove anything before this line, then unpack
# it by saving it into a file and typing "sh file".  To overwrite existing
# files, type "sh file -c".  You can also feed this as standard input via
# unshar, or by typing "sh <file", e.g..  If this archive is complete, you
# will see the following message at the end:
#		"End of shell archive."
# Contents:  README.APP README.DOS backsp.c getopt.c linkit msd_dio.c
#   msd_dio.h msd_dir.c msd_dir.h paxpatch
# Wrapped by walters@oksce1 on Wed Feb 15 11:54:43 1989
PATH=/bin:/usr/bin:/usr/ucb ; export PATH
if test -f 'README.APP' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'README.APP'\"
else
echo shar: Extracting \"'README.APP'\" \(560 characters\)
sed "s/^X//" >'README.APP' <<'END_OF_FILE'
XEnclosed are the patches to apply to version 1.2 of pax and files to fix
the tar append bug and port to MSDOS.  It supports both the DOS
filesystem and the "tape on a disk" system used by micro UN*X systems. 
ALL the MSDOS stuff is "#ifdef"ed so it will still compile on other
machines.  The patches patch Makefile and config.h so you might want to
save your current one before applying.  If so you will then need to add
backsp.c to the SRC line and backsp.o to the OBJ line in the makefile. 
The tar append bugfix has been tested on Ultrix v2.2 and MSDOS. 
X
X
END_OF_FILE
if test 560 -ne `wc -c <'README.APP'`; then
    echo shar: \"'README.APP'\" unpacked with wrong size!
fi
# end of 'README.APP'
fi
if test -f 'README.DOS' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'README.DOS'\"
else
echo shar: Extracting \"'README.DOS'\" \(1642 characters\)
sed "s/^X//" >'README.DOS' <<'END_OF_FILE'
DOS stuff:
This is an MSDOS port of PAX which was recently released to
comp.sources.unix.  It supports both the DOS filesystem and the "tape on
a disk" system used by micro UN*X systems.  This will allow for easy
transfer of files to and from UN*X systems.  To get TAR.EXE and CPIO.EXE
just copy PAX.EXE to TAR.EXE and CPIO.EXE.  To use the "tape on a disk"
feature give an archive filename of "a:dio" or "b:dio" (dio stands for
direct i/o) for floppy drives "a" and "b".  This program will support
any media supported by DOS, but you MUST do a DIR on an MSDOS formatted
disk at the density you want to use before using PAX, TAR, or CPIO with
direct i/o.  Note that the direct i/o destroys the logical structure of
the disk.  Multiple volumes and the tar append option are supported. 
X
XExamples:
X
Using direct i/o on a floppy with tar (a:dio and b:dio are special)
X
X	1) Put high or low density MSDOS formatted floppy in drive "a".
X	2) Do a DIR
X	3) Remove the floppy
X	4) tar cvf "a:dio" .
X
Using direct i/o on a floppy with cpio (a:dio and b:dio are special)
X
X	1) Put high or low density MSDOS formatted floppy in drive "a".
X	2) Do a DIR
X	3) Remove the floppy
X	4) find . -print | cpio -ocvBD "a:dio"
X
Using tar within the MSDOS filesystem (the filename does not matter)
Will not destroy the logical structure of the disk.
X
X	1) Put high or low density MSDOS formatted floppy in drive "a".
X	4) tar cvf "a:whatever.tar" .
X
X
XEnjoy,
X--
Harold G. Walters			walters@1.ce.okstate.edu
School of Civil Engineering		okstate!oksce1!walters
Oklahoma State University		"If all you have is a hammer, 
Stillwater, OK  74078			 everything looks like a nail".
X
END_OF_FILE
if test 1642 -ne `wc -c <'README.DOS'`; then
    echo shar: \"'README.DOS'\" unpacked with wrong size!
fi
# end of 'README.DOS'
fi
if test -f 'backsp.c' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'backsp.c'\"
else
echo shar: Extracting \"'backsp.c'\" \(1507 characters\)
sed "s/^X//" >'backsp.c' <<'END_OF_FILE'
X/*backsp.c***************************************************************/     
X/*									*/
X/*			    back_space_records 				*/
X/*									*/
X/*		   Copyright (c) 1989 Harold G. Walters			*/
X/*									*/
X/* Redistribution and use in source and binary forms are permitted	*/
X/* provided that the above copyright notice is duplicated in the 	*/
X/* source form.								*/
X/*									*/
X/* THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR	*/
X/* IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED	*/
X/* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.	*/
X/*									*/
X/************************************************************************/
X
X#include "pax.h"
X
X#ifdef MTIOCTOP
X#include <sys/mtio.h>
X#endif
X
X/* note: a tar append without a warning message does not mean sucess, to */
X/* be sure, do a tar tv to see if your device can support backspacing */
X
X#ifdef __STDC__
X
int back_space_records(int n)
X
X#else
X
int back_space_records(n)
int n;
X
X#endif
X{
X	OFFSET pos;
X
X#ifdef MTIOCTOP
X	struct mtop mt;
X
X	mt.mt_op = MTBSR;
X	mt.mt_count = n;
X	if (ioctl(archivefd, MTIOCTOP, &mt) < 0)
X	{
X		if (errno == EIO) /* try again */
X		{
X			if (ioctl(archivefd, MTIOCTOP, &mt) < 0)
X			{
X				warn(strerror(), 
X					"probably can't backspace on device");
X				return(-1);
X			}
X		}
X	}
X	else
X	{
X		return(n);
X	}
X#endif
X	pos = LSEEK(archivefd, (OFFSET) -n * BLOCKSIZE, 1);
X	if (pos == -1L)
X	{
X		warn(strerror(), "probably can't backspace on device");
X		return(-1);
X	}
X	return(n);
X}	
END_OF_FILE
if test 1507 -ne `wc -c <'backsp.c'`; then
    echo shar: \"'backsp.c'\" unpacked with wrong size!
fi
# end of 'backsp.c'
fi
if test -f 'getopt.c' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'getopt.c'\"
else
echo shar: Extracting \"'getopt.c'\" \(2996 characters\)
sed "s/^X//" >'getopt.c' <<'END_OF_FILE'
X/*
X	I got this off net.sources from Henry Spencer.
X	It is a public domain getopt(3) like in System V.
X	I have made the following modifications:
X
X	index(s,c) was added because too many people could
X	not compile getopt without it.
X
X	A test main program was added, ifdeffed by GETOPT.
X	This main program is a public domain implementation
X	of the getopt(1) program like in System V.  The getopt
X	program can be used to standardize shell option handling.
X		e.g.  cc -DGETOPT getopt.c -o getopt
X*/
X#include <stdio.h>
X
X#ifndef lint
static	char	sccsfid[] = "@(#) getopt.c 5.0 (UTZoo) 1985";
X#endif
X
X#define	ARGCH    (int)':'
X#define BADCH	 (int)'?'
X#define EMSG	 ""
X#define	ENDARGS  "--"
X
X/* this is included because index is not on some UNIX systems */
static
char *
index (s, c)
register	char	*s;
register	int 	c;
X	{
X	while (*s)
X		if (c == *s) return (s);
X		else s++;
X	return (NULL);
X	}
X
X/*
X * get option letter from argument vector
X */
int	opterr = 1,		/* useless, never set or used */
X	optind = 1,		/* index into parent argv vector */
X	optopt;			/* character checked for validity */
char	*optarg;		/* argument associated with option */
X
X#define tell(s)	fputs(*nargv,stderr);fputs(s,stderr); \
X		fputc(optopt,stderr);fputc('\n',stderr);return(BADCH);
X
X
getopt(nargc,nargv,ostr)
int	nargc;
char	**nargv,
X	*ostr;
X{
X	static char	*place = EMSG;	/* option letter processing */
X	register char	*oli;		/* option letter list index */
X	char	*index();
X
X	if(!*place) {			/* update scanning pointer */
X		if(optind >= nargc || *(place = nargv[optind]) != '-' || !*++place) return(EOF);
X		if (*place == '-') {	/* found "--" */
X			++optind;
X			return(EOF);
X		}
X	}				/* option letter okay? */
X	if ((optopt = (int)*place++) == ARGCH || !(oli = index(ostr,optopt))) {
X		if(!*place) ++optind;
X		tell(": illegal option -- ");
X	}
X	if (*++oli != ARGCH) {		/* don't need argument */
X		optarg = NULL;
X		if (!*place) ++optind;
X	}
X	else {				/* need an argument */
X		if (*place) optarg = place;	/* no white space */
X		else if (nargc <= ++optind) {	/* no arg */
X			place = EMSG;
X			tell(": option requires an argument -- ");
X		}
X	 	else optarg = nargv[optind];	/* white space */
X		place = EMSG;
X		++optind;
X	}
X	return(optopt);			/* dump back option letter */
X}
X
X
X#ifdef GETOPT
X
X#ifndef lint
static	char	sccspid[] = "@(#) getopt.c 5.1 (WangInst) 6/15/85";
X#endif
X
main (argc, argv) char **argv;
X	{
X	char	*optstring = argv[1];
X	char	*argv0 = argv[0];
X	extern	int 	optind;
X	extern	char	*optarg;
X	int 	opterr = 0;
X	int 	C;
X	char	*opi;
X	if (argc == 1)
X		{
X		fprintf (stderr, "Usage: %s optstring args\n", argv0);
X		exit (1);
X		}
X	argv++;
X	argc--;
X	argv[0] = argv0;
X	while ((C = getopt (argc, argv, optstring)) != EOF)
X		{
X		if (C == BADCH) opterr++;
X		printf ("-%c ", C);
X		opi = index (optstring, C);
X		if (opi && opi[1] == ARGCH)
X			if (optarg)
X				printf ("\"%s\" ", optarg);
X			else opterr++;
X		}
X	printf ("%s", ENDARGS);
X	while (optind < argc)
X		printf (" \"%s\"", argv[optind++]);
X	putchar ('\n');
X	exit (opterr);
X	}
X
X#endif
END_OF_FILE
if test 2996 -ne `wc -c <'getopt.c'`; then
    echo shar: \"'getopt.c'\" unpacked with wrong size!
fi
# end of 'getopt.c'
fi
if test -f 'linkit' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'linkit'\"
else
echo shar: Extracting \"'linkit'\" \(315 characters\)
sed "s/^X//" >'linkit' <<'END_OF_FILE'
pax.obj+append.obj+fileio.obj+msd_dir.obj+ttyio.obj+
buffer.obj+link.obj+namelist.obj+port.obj+warn.obj+
cpio.obj+list.obj+names.obj+regexp.obj+wildmat.obj+
create.obj+mem.obj+pass.obj+replace.obj+extract.obj+
msd_dio.obj+pathname.obj+tar.obj+getopt.obj+backsp.obj+\lib\setargv.obj
tar.exe /e/noi/stack:32768
nul
X
X
END_OF_FILE
if test 315 -ne `wc -c <'linkit'`; then
    echo shar: \"'linkit'\" unpacked with wrong size!
fi
# end of 'linkit'
fi
if test -f 'msd_dio.c' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'msd_dio.c'\"
else
echo shar: Extracting \"'msd_dio.c'\" \(11742 characters\)
sed "s/^X//" >'msd_dio.c' <<'END_OF_FILE'
X/*msd_dio.c**************************************************************/     
X/*									*/
X/*			        msd_dio	 				*/
X/*									*/
X/*		   Copyright (c) 1989 Harold G. Walters			*/
X/*									*/
X/* Redistribution and use in source and binary forms are permitted	*/
X/* provided that the above copyright notice is duplicated in the 	*/
X/* source form.								*/
X/*									*/
X/* THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR	*/
X/* IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED	*/
X/* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.	*/
X/*									*/
X/************************************************************************/
X
X/*
NOTE: Before these routines can be used to read/write directly to the
disk, bypassing the logical file structure, MSDOS MUST know what kind of
disk is in the drive you intend to write to.  This can be accomplished
by putting a formatted disk in the drive of interest and doing a DIR on
it.  MSDOS then remembers the disk type for a while. 
X
WARNING: DISABLING THE BUILT IN CHECK AND CALLING THESE ROUTINES WITH
THE DRIVE SET TO CORRESPOND TO YOUR HARD DISK WILL PROBABLY TRASH IT
COMPLETELY
X*/
X
X#ifdef MSDOS
X
X#include <sys/types.h>
X#include <stdio.h>
X#include <stdlib.h>
X#include <string.h>
X#include <errno.h>
X#include <dos.h>
X#include "msd_dio.h"
X
X#ifdef __STDC__
X
static  int dio_adw(unsigned int drive,char *buf,unsigned int secnum,
X	unsigned int secknt,unsigned int *err);
static  int dio_adr(unsigned int drive,char *buf,unsigned int secnum,
X	unsigned int secknt,unsigned int *err);
static  int dio_drive_check(int d);
static  int dio_err_hand(unsigned int drive,int rw,unsigned int err);
static  int dio_read1(int drive,char *buf,unsigned int sec);
static  int dio_write1(int drive,char *buf,unsigned int sec);
X
X#else
X
static  int dio_adw();
static  int dio_adr();
static  int dio_drive_check();
static  int dio_err_hand();
static  int dio_read1();
static  int dio_write1();
X
X#endif
X
X#define SECSIZ 512
X
static unsigned long fptr = 0L;
static char secbuf[SECSIZ];
static int rwsec = 0;
X
static union REGS reg, rreg;
X
X#if defined(M_I86LM)
static struct SREGS sreg;
X#endif
X
static int dio_adw(drive, buf, secnum, secknt, err)
unsigned int drive, secnum, secknt, *err;
char *buf;
X{
X	rwsec = secnum;
X	reg.x.ax = drive;
X	reg.x.dx = secnum;
X	reg.x.cx = secknt;
X#if defined(M_I86LM)
X	reg.x.bx = FP_OFF(buf);
X	sreg.ds = FP_SEG(buf);
X	int86x(0x26, &reg, &rreg, &sreg);
X#else
X	reg.x.dx = (int) buf;
X	int86(0x26, &reg, &rreg);
X#endif
X	*err = rreg.x.ax;
X	if (rreg.x.cflag)
X		return(-1);
X	else
X		return(0);
X}
X
static int dio_adr(drive, buf, secnum, secknt, err)
unsigned int drive, secnum, secknt, *err;
char *buf;
X{
X	rwsec = secnum;
X	reg.x.ax = drive;
X	reg.x.dx = secnum;
X	reg.x.cx = secknt;
X#if defined(M_I86LM)
X	reg.x.bx = FP_OFF(buf);
X	sreg.ds = FP_SEG(buf);
X	int86x(0x25, &reg, &rreg, &sreg);
X#else
X	reg.x.dx = (int) buf;
X	int86(0x25, &reg, &rreg);
X#endif
X	*err = rreg.x.ax;
X	if (rreg.x.cflag)
X		return(-1);
X	else
X		return(0);
X}
X
X
static char *doserr[] = {
X"write-protect error",
X"unknown unit",
X"drive not ready",
X"unknown command",
X"data error (bad CRC)",
X"bad request structure length",
X"seek error",
X"unknown media type",
X"sector not found",
X"printer out of paper",
X"write fault",
X"read fault",
X"general failure",
X" ",
X" ",
X"invalid disk change (DOS 3.x)",
X""
X};
X
static char *bioserr[] = {
X"general error",
X"",
X"bad address mark",
X"write-protect error",
X"sector not found",
X"", "", "",
X"DMA failure",
X"", "", "", "", "",
X"", "",
X"data error (bad CRC)",
X"", "", "", "", "", "", "", "", "", "",
X"", "", "", "", "",
X"controller failed",
X"", "", "", "", "", "", "", "", "", "",
X"", "", "", "", "", "", "", "", "", "",
X"", "", "", "", "", "", "", "", "", "",
X"",
X"seek error",
X"", "", "", "", "", "", "", "", "", "",
X"", "", "", "", "", "", "", "", "", "",
X"", "", "", "", "", "", "", "", "", "",
X"", "", "", "", "", "", "", "", "", "",
X"", "", "", "", "", "", "", "", "", "",
X"", "", "", "", "", "", "", "", "", "",
X"", "", "",
X"disk time out",
X""
X};
X
static int dio_drive_check(d)
int d;
X{
X	d = -(d + 1);
X	switch(d)
X	{
X	case 0: /* a */
X	case 1: /* b */
X		break;
X	default:
X		fprintf(stderr, "dio: dio to drive %1c: not supported\n",
X			'a' + d);
X		exit(1);
X	}
X	return(d);
X}
X
static int dio_err_hand(drive, rw, err)
unsigned int drive;
int rw;
unsigned int err;
X{
X	unsigned int high, low;
X
X	low = err & 0x000f;
X	high = (err >> 8) & 0x00ff;
X 	if (!(high == 0x04 && low == 0x08))
X		fprintf(stderr, 
X		"dio: sector %d: %s error 0x%x\ndio: dos: %s: bios: %s\n",
X		(rw == (int) 'r') ? rwsec : rwsec,
X		(rw == (int) 'r') ? "read" : "write", err,
X		doserr[low], bioserr[high]);
X	if (high == 0x04 && low == 0x08) /* sector not found */
X	{
X		if (rw == (int) 'r')
X		{
X			rwsec = 0;
X			return(0);
X		}
X		else
X		{
X			errno = ENOSPC;
X			rwsec = 0;
X			return(-1);
X		}
X	}
X	exit(1);
X}
X
static int dio_read1(drive, buf, sec)
int drive;
char *buf;
unsigned int sec;
X{
X	unsigned int err;
X	
X	if (dio_adr(drive, buf, sec, 1, &err) == -1)
X	if (dio_adr(drive, buf, sec, 1, &err) == -1)
X	if (dio_adr(drive, buf, sec, 1, &err) == -1)
X		if (dio_err_hand(drive, (int) 'r', err) == 0)
X			return(0);
X	return(SECSIZ);
X}
X
static int dio_write1(drive, buf, sec)
int drive;
char *buf;
unsigned int sec;
X{
X	unsigned int err;
X	
X	if (dio_adw(drive, buf, sec, 1, &err) == -1)
X	if (dio_adw(drive, buf, sec, 1, &err) == -1)
X	if (dio_adw(drive, buf, sec, 1, &err) == -1)
X		if (dio_err_hand(drive, (int) 'w', err) == -1)
X			return(-1);
X	return(SECSIZ);
X}
X
X
int dio_write(drive, from_buf, from_cnt)
int drive;		/* a -> -1, b -> -2, etc */
char *from_buf;		/* buffer containing bytes to be written */
unsigned int from_cnt;	/* number of bytes to write */
X{
X	unsigned int amt, err, nn, fquo, frem, cquo, crem;
X
X	drive = dio_drive_check(drive);
X	amt = 0; err = 0; cquo = 0; crem = 0;
X/*printf("W drive %d from_cnt %d fptr %ld\n", drive, from_cnt, fptr);*/
X	fquo = (unsigned int) (fptr / SECSIZ);
X	frem = (unsigned int) (fptr % SECSIZ);
X	if (frem > 0)
X	{
X		if (dio_read1(drive, secbuf, fquo) == 0)
X			return(-1);
X		if ((nn = SECSIZ - frem) > from_cnt)
X			nn = from_cnt;
X		memcpy(&secbuf[frem], from_buf, nn);
X		if (dio_write1(drive, secbuf, fquo) == -1)
X			return(-1);
X		amt += nn;
X		fptr += nn;
X		if (SECSIZ - frem <= from_cnt)
X			fquo++;
X		from_buf += nn;
X		from_cnt -= nn;
X/*printf("W fr fptr %ld fquo %d frem %d cquo %d crem %d amt %d from_cnt %d\n",
fptr, fquo, frem, cquo, crem, amt, from_cnt);*/
X	}
X	cquo = from_cnt / SECSIZ;
X	crem = from_cnt % SECSIZ;
X	if (cquo > 0)
X	{
X		if (dio_adw(drive, from_buf, fquo, cquo, &err) == -1)
X		if (dio_adw(drive, from_buf, fquo, cquo, &err) == -1)
X		if (dio_adw(drive, from_buf, fquo, cquo, &err) == -1)
X			if (dio_err_hand(drive, (int) 'w', err) == -1)
X				return(-1);
X		nn = cquo * SECSIZ;
X		amt += nn;
X		fptr += nn;
X		fquo += cquo;
X		from_buf += nn;
X		from_cnt -= nn;
X/*printf("W cq fptr %ld fquo %d frem %d cquo %d crem %d amt %d from_cnt %d\n",
fptr, fquo, frem, cquo, crem, amt, from_cnt);*/
X	}
X	if (crem > 0)
X	{
X		if (dio_read1(drive, secbuf, fquo) == 0)
X			return(-1);
X		nn = crem;
X		memcpy(&secbuf[0], from_buf, nn);
X		if (dio_write1(drive, secbuf, fquo) == -1)
X			return(-1);
X		amt += nn;
X		fptr += nn;
X		from_buf += nn;
X		from_cnt -= nn;
X/*printf("W cr fptr %ld fquo %d frem %d cquo %d crem %d amt %d from_cnt %d\n",
fptr, fquo, frem, cquo, crem, amt, from_cnt);*/
X	}
X	return(amt);
X}
X
X/* read data directly from the disk using INT 25 */
X
int dio_read(drive, to_buf, to_cnt)
int drive;		/* a -> -1, b -> -2, etc */
char *to_buf;		/* buffer containing bytes to be written */
unsigned int to_cnt;	/* number of bytes to write */
X{
X	unsigned int amt, err, nn, fquo, frem, cquo, crem;
X
X	drive = dio_drive_check(drive);
X	amt = 0; err = 0; cquo = 0; crem = 0;
X/*printf("R drive %d to_cnt %d fptr %ld\n", drive, to_cnt, fptr);*/
X	fquo = (unsigned int) (fptr / SECSIZ);
X	frem = (unsigned int) (fptr % SECSIZ);
X	if (frem > 0)
X	{
X		if (dio_read1(drive, secbuf, fquo) == 0)
X			return(0);
X		if ((nn = SECSIZ - frem) > to_cnt)
X			nn = to_cnt;
X		memcpy(to_buf, &secbuf[frem], nn);
X		amt += nn;
X		fptr += nn;
X		if (SECSIZ - frem <= to_cnt)
X			fquo++;
X		to_buf += nn;
X		to_cnt -= nn;
X/*printf("R fr fptr %ld fquo %d frem %d cquo %d crem %d amt %d to_cnt %d\n",
fptr, fquo, frem, cquo, crem, amt, to_cnt);*/
X	}
X	cquo = to_cnt / SECSIZ;
X	crem = to_cnt % SECSIZ;
X	if (cquo > 0)
X	{
X		if (dio_adr(drive, to_buf, fquo, cquo, &err) == -1)
X		if (dio_adr(drive, to_buf, fquo, cquo, &err) == -1)
X		if (dio_adr(drive, to_buf, fquo, cquo, &err) == -1)
X			if (dio_err_hand(drive, (int) 'r', err) == 0)
X				return(0);
X		nn = cquo * SECSIZ;
X		amt += nn;
X		fptr += nn;
X		fquo += cquo;
X		to_buf += nn;
X		to_cnt -= nn;
X/*printf("R cq fptr %ld fquo %d frem %d cquo %d crem %d amt %d to_cnt %d\n",
fptr, fquo, frem, cquo, crem, amt, to_cnt);*/
X	}
X	if (crem > 0)
X	{
X		if (dio_read1(drive, secbuf, fquo) == 0)
X			return(0);
X		nn = crem;
X		memcpy(to_buf, &secbuf[0], nn);
X		amt += nn;
X		fptr += nn;
X		to_buf += nn;
X		to_cnt -= nn;
X/*printf("R cr fptr %ld fquo %d frem %d cquo %d crem %d amt %d to_cnt %d\n",
fptr, fquo, frem, cquo, crem, amt, to_cnt);*/
X	}
X	return(amt);
X}
X
int dio_open_check(s)
char *s;
X{
X	if (!stricmp(s, "a:dio") || !stricmp(s, "b:dio"))
X		return(-(*s - 'a' + 1));
X	else
X		return(0);
X}	
X	
int dio_open2(p, f)
char *p;
int f;
X{
X	int h;
X
X	h = dio_open_check(p);
X	if (h < 0)
X		fptr = 0L;
X	return(h);
X}
X
int dio_open3(p, f, m)
char *p;
int f, m;
X{
X	int h;
X
X	h = dio_open_check(p);
X	if (h < 0)
X		fptr = 0L;
X	return(h);
X}
X
int dio_close(h)
int h;
X{
X	return(0);
X}
X
long dio_lseek(h, o, r)
int h;
long o;
int r;
X{
X	long check;
X
X	if (h >= 0)
X	{
X		errno = EBADF;
X		return(-1L);
X	}
X	check = fptr;
X	switch(r)
X	{
X	case 0: 
X		check = o;
X		break;
X	case 1:
X		check += o;
X		break;
X	case 2:
X	default:
X		errno = EINVAL;
X		fprintf(stderr, "dio: origin %d not supported\n", r);
X		return(-1L);
X	}
X	if (check < 0L)
X	{
X		errno = EINVAL;
X		return(-1L);
X	}
X	fptr = check;
X	return(fptr);
X}
X
X#endif
X
X#ifdef DTWRITE
X
X/* dtwrite.exe - for testing writing multiple disks */
X
X#define DISKBY15 450000L
X#define BUF 65535L
char rd_buf[BUF], wr_buf[BUF];
int blocking = 20, blocksize = 20 * SECSIZ;
X
main()
X{
X	unsigned int iter, wr_send, wr_ret, i;
X	long wr_total;
X	char junk[10];
X	
X	srand(256);
X	iter = 0;
X	wr_total = 0L;
X	while(1)
X	{
X		wr_send = (unsigned int) rand();
X		wr_total += (long) wr_send;
X		for (i = 0; i < wr_send; i++)
X			wr_buf[i] = (char) rand();
X 		wr_ret = dio_write(-1, wr_buf, wr_send);
X		printf("iter %u wr_send %u wr_return %u\n",
X			iter, wr_send, wr_ret);
X		if (wr_ret == -1)
X		{
X			gets(junk);
X			dio_open2("a:dio", 0);
X			wr_ret = dio_write(-1, wr_buf, wr_send);
X			printf("finish iter %u wr_send %u wr_return %u\n",
X				iter, wr_send, wr_ret);
X		}
X		if (wr_total > DISKBY15)
X			exit(0);
X		iter++;
X	}	
X}
X
X#endif
X
X#ifdef DTREAD
X
X/* dtread.exe - for testing reading multiple disks */
X
X#define DISKBY15 450000L
X#define BUF 65535L
char rd_buf[BUF], wr_buf[BUF];
int blocking = 20, blocksize = 20 * SECSIZ;
X
main()
X{
X	unsigned int iter, rd_send, rd_ret, i;
X	long rd_total;
X	char junk[10];
X	
X	srand(256);
X	iter = 0;
X	rd_total = 0L;
X	while(1)
X	{
X		rd_send = (unsigned int) rand();
X		rd_total += (long) rd_send;
X		for (i = 0; i < rd_send; i++)
X			wr_buf[i] = (char) rand();
X		rd_ret = dio_read(-1, rd_buf, rd_send);
X		printf("iter %u rd_send %u rd_ret %u\n",
X			iter, rd_send, rd_ret);
X		if (rd_ret == 0)
X		{
X			gets(junk);
X			dio_open2("a:dio", 0);
X			rd_ret = dio_read(-1, rd_buf, rd_send);
X			printf("finish iter %u rd_send %u rd_ret %u\n",
X				iter, rd_send, rd_ret);
X		}
X		for (i = 0; i < rd_send; i++)
X		{
X			if (rd_buf[i] != wr_buf[i])
X			{
X				printf("error byte %u rd %u wr %u\n",
X				i, rd_buf[i], wr_buf[i]);
X			}
X		}
X		if (rd_total > DISKBY15)
X			exit(0);
X		iter++;
X	}	
X}
X
X
X#endif
END_OF_FILE
if test 11742 -ne `wc -c <'msd_dio.c'`; then
    echo shar: \"'msd_dio.c'\" unpacked with wrong size!
fi
# end of 'msd_dio.c'
fi
if test -f 'msd_dio.h' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'msd_dio.h'\"
else
echo shar: Extracting \"'msd_dio.h'\" \(1208 characters\)
sed "s/^X//" >'msd_dio.h' <<'END_OF_FILE'
X/* msd_dio.h */
X
X#ifdef MSDOS
X
X#ifdef __STDC__
X
extern  int dio_write(int drive,char *from_buf,unsigned int from_cnt);
extern  int dio_read(int drive,char *to_buf,unsigned int to_cnt);
extern  int dio_open_check(char *s);
extern  int dio_open2(char *p,int f);
extern  int dio_open3(char *p,int f,int m);
extern  int dio_close(int h);
extern  long dio_lseek(int h,long o,int r);
X
X#else
X
extern  int dio_write();
extern  int dio_read();
extern  int dio_open_check();
extern  int dio_open2();
extern  int dio_open3();
extern  int dio_close();
extern  long dio_lseek();
X
X#endif
X
X#define OPEN2(p,f) \
X	( (dio_open_check(p) < 0) ? dio_open2(p,f) : open(p,f) )
X#define OPEN3(p,f,m) \
X	( (dio_open_check(p) < 0) ? dio_open3(p,f,m) : open(p,f,m) )
X#define CLOSE(h) \
X	( (h < 0) ? dio_close(h) : close(h) )
X#define READ(h,b,c) \
X	( (h < 0) ? dio_read(h,b,c) : read(h,b,c) )
X#define WRITE(h,b,c) \
X	( (h < 0) ? dio_write(h,b,c) : write(h,b,c) )
X#define LSEEK(h,o,r) \
X	( (h < 0) ? dio_lseek(h,o,r) : lseek(h,o,r) )
X
X#else
X
X#define OPEN2(p,f) open(p,f)
X#define OPEN3(p,f,m) open(p,f,m)
X#define CLOSE(h) close(h)
X#define READ(h,b,c) read(h,b,c)
X#define WRITE(h,b,c) write(h,b,c)
X#define LSEEK(h,o,r) lseek(h,o,r)
X
X#endif
END_OF_FILE
if test 1208 -ne `wc -c <'msd_dio.h'`; then
    echo shar: \"'msd_dio.h'\" unpacked with wrong size!
fi
# end of 'msd_dio.h'
fi
if test -f 'msd_dir.c' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'msd_dir.c'\"
else
echo shar: Extracting \"'msd_dir.c'\" \(4282 characters\)
sed "s/^X//" >'msd_dir.c' <<'END_OF_FILE'
X/*
X * @(#)msd_dir.c 1.4 87/11/06	Public Domain.
X *
X *  A public domain implementation of BSD directory routines for
X *  MS-DOS.  Written by Michael Rendell ({uunet,utai}michael@garfield),
X *  August 1897
X */
X
X#include	<sys/types.h>
X#include	<sys/stat.h>
X#include	<sys/dir.h>
X#include	<malloc.h>
X#include	<string.h>
X#include	<dos.h>
X
X#ifndef	NULL
X# define	NULL	0
X#endif	/* NULL */
X
X#ifndef	MAXPATHLEN
X# define	MAXPATHLEN	255
X#endif	/* MAXPATHLEN */
X
X/* attribute stuff */
X#define	A_RONLY		0x01
X#define	A_HIDDEN	0x02
X#define	A_SYSTEM	0x04
X#define	A_LABEL		0x08
X#define	A_DIR		0x10
X#define	A_ARCHIVE	0x20
X
X/* dos call values */
X#define	DOSI_FINDF	0x4e
X#define	DOSI_FINDN	0x4f
X#define	DOSI_SDTA	0x1a
X
X#define	Newisnull(a, t)		((a = (t *) malloc(sizeof(t))) == (t *) NULL)
X#define	ATTRIBUTES		(A_DIR | A_HIDDEN | A_SYSTEM)
X
X/* what find first/next calls look use */
typedef struct {
X	char		d_buf[21];
X	char		d_attribute;
X	unsigned short	d_time;
X	unsigned short	d_date;
X	long		d_size;
X	char		d_name[13];
X} Dta_buf;
X
static	char	*getdirent();
static	void	setdta();
static	void	free_dircontents();
X
static	Dta_buf		dtabuf;
static	Dta_buf		*dtapnt = &dtabuf;
static	union REGS	reg, nreg;
X
X#if	defined(M_I86LM)
static	struct SREGS	sreg;
X#endif
X
DIR	*
opendir(name)
X	char	*name;
X{
X	struct	stat		statb;
X	DIR			*dirp;
X	char			c;
X	char			*s;
X	struct _dircontents	*dp;
X	char			nbuf[MAXPATHLEN + 1];
X	
X	strcpy(nbuf, name);
X	if ((s = strrchr(nbuf, '/')) != (char *) NULL)
X		*s = '\0';
X	else if ((s = strrchr(nbuf, '\\')) != (char *) NULL)
X		*s = '0';
X	if (stat(nbuf, &statb) < 0 || (statb.st_mode & S_IFMT) != S_IFDIR)
X		return (DIR *) NULL;
X	if (Newisnull(dirp, DIR))
X		return (DIR *) NULL;
X	if (*name && (c = name[strlen(name) - 1]) != '\\' && c != '/')
X		(void) strcat(strcpy(nbuf, name), "\\*.*");
X	else
X		(void) strcat(strcpy(nbuf, name), "*.*");
X	dirp->dd_loc = 0;
X	setdta();
X	dirp->dd_contents = dirp->dd_cp = (struct _dircontents *) NULL;
X	if ((s = getdirent(nbuf)) == (char *) NULL)
X		return dirp;
X	do {
X		if (Newisnull(dp, struct _dircontents) || (dp->_d_entry =
X			malloc((unsigned) (strlen(s) + 1))) == (char *) NULL)
X		{
X			if (dp)
X				free((char *) dp);
X			free_dircontents(dirp->dd_contents);
X			return (DIR *) NULL;
X		}
X		if (dirp->dd_contents)
X			dirp->dd_cp = dirp->dd_cp->_d_next = dp;
X		else
X			dirp->dd_contents = dirp->dd_cp = dp;
X		(void) strcpy(dp->_d_entry, s);
X		dp->_d_next = (struct _dircontents *) NULL;
X	} while ((s = getdirent((char *) NULL)) != (char *) NULL);
X	dirp->dd_cp = dirp->dd_contents;
X
X	return dirp;
X}
X
void
closedir(dirp)
X	DIR	*dirp;
X{
X	free_dircontents(dirp->dd_contents);
X	free((char *) dirp);
X}
X
struct direct	*
readdir(dirp)
X	DIR	*dirp;
X{
X	static	struct direct	dp;
X	
X	if (dirp->dd_cp == (struct _dircontents *) NULL)
X		return (struct direct *) NULL;
X	dp.d_namlen = dp.d_reclen =
X		strlen(strcpy(dp.d_name, dirp->dd_cp->_d_entry));
X	strlwr(dp.d_name);
X	dp.d_ino = 0;
X	dirp->dd_cp = dirp->dd_cp->_d_next;
X	dirp->dd_loc++;
X
X	return &dp;
X}
X
void
seekdir(dirp, off)
X	DIR	*dirp;
X	long	off;
X{
X	long			i = off;
X	struct _dircontents	*dp;
X
X	if (off < 0)
X		return;
X	for (dp = dirp->dd_contents ; --i >= 0 && dp ; dp = dp->_d_next)
X		;
X	dirp->dd_loc = off - (i + 1);
X	dirp->dd_cp = dp;
X}
X
long
telldir(dirp)
X	DIR	*dirp;
X{
X	return dirp->dd_loc;
X}
X
static	void
free_dircontents(dp)
X	struct	_dircontents	*dp;
X{
X	struct _dircontents	*odp;
X
X	while (dp) {
X		if (dp->_d_entry)
X			free(dp->_d_entry);
X		dp = (odp = dp)->_d_next;
X		free((char *) odp);
X	}
X}
X
static	char	*
getdirent(dir)
X	char	*dir;
X{
X	if (dir != (char *) NULL) {		/* get first entry */
X		reg.h.ah = DOSI_FINDF;
X		reg.h.cl = ATTRIBUTES;
X#if	defined(M_I86LM)
X		reg.x.dx = FP_OFF(dir);
X		sreg.ds = FP_SEG(dir);
X#else
X		reg.x.dx = (unsigned) dir;
X#endif
X	} else {				/* get next entry */
X		reg.h.ah = DOSI_FINDN;
X#if	defined(M_I86LM)
X		reg.x.dx = FP_OFF(dtapnt);
X		sreg.ds = FP_SEG(dtapnt);
X#else
X		reg.x.dx = (unsigned) dtapnt;
X#endif
X	}
X#if	defined(M_I86LM)
X	intdosx(&reg, &nreg, &sreg);
X#else
X	intdos(&reg, &nreg);
X#endif
X	if (nreg.x.cflag)
X		return (char *) NULL;
X
X	return dtabuf.d_name;
X}
X
static	void
setdta()
X{
X	reg.h.ah = DOSI_SDTA;
X#if	defined(M_I86LM)
X	reg.x.dx = FP_OFF(dtapnt);
X	sreg.ds = FP_SEG(dtapnt);
X	intdosx(&reg, &nreg, &sreg);
X#else
X	reg.x.dx = (int) dtapnt;
X	intdos(&reg, &nreg);
X#endif
X}
END_OF_FILE
if test 4282 -ne `wc -c <'msd_dir.c'`; then
    echo shar: \"'msd_dir.c'\" unpacked with wrong size!
fi
# end of 'msd_dir.c'
fi
if test -f 'msd_dir.h' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'msd_dir.h'\"
else
echo shar: Extracting \"'msd_dir.h'\" \(954 characters\)
sed "s/^X//" >'msd_dir.h' <<'END_OF_FILE'
X/*
X * @(#)msd_dir.h 1.4 87/11/06	Public Domain.
X *
X *  A public domain implementation of BSD directory routines for
X *  MS-DOS.  Written by Michael Rendell ({uunet,utai}michael@garfield),
X *  August 1897
X */
X
X#define	rewinddir(dirp)	seekdir(dirp, 0L)
X
X#define	MAXNAMLEN	12
X
struct direct {
X	ino_t	d_ino;			/* a bit of a farce */
X	int	d_reclen;		/* more farce */
X	int	d_namlen;		/* length of d_name */
X	char	d_name[MAXNAMLEN + 1];		/* garentee null termination */
X};
X
struct _dircontents {
X	char	*_d_entry;
X	struct _dircontents	*_d_next;
X};
X
typedef struct _dirdesc {
X	int		dd_id;	/* uniquely identify each open directory */
X	long		dd_loc;	/* where we are in directory entry is this */
X	struct _dircontents	*dd_contents;	/* pointer to contents of dir */
X	struct _dircontents	*dd_cp;	/* pointer to current position */
X} DIR;
X
extern	DIR		*opendir();
extern	struct direct	*readdir();
extern	void		seekdir();
extern	long		telldir();
extern	void		closedir();
END_OF_FILE
if test 954 -ne `wc -c <'msd_dir.h'`; then
    echo shar: \"'msd_dir.h'\" unpacked with wrong size!
fi
# end of 'msd_dir.h'
fi
if test -f 'paxpatch' -a "${1}" != "-c" ; then 
  echo shar: Will not clobber existing file \"'paxpatch'\"
else
echo shar: Extracting \"'paxpatch'\" \(23594 characters\)
sed "s/^X//" >'paxpatch' <<'END_OF_FILE'
diff -rc ../paxorig/Makefile ./Makefile
X*** ../paxorig/Makefile	Tue Feb 14 13:37:58 1989
X--- ./Makefile	Wed Feb 15 11:00:34 1989
X***************
X*** 26,33 ****
X  # Set CFLAGS to whatever makes your C compiler happy.  Be sure to include 
X  # the definition of $(POSIX) in the flag.
X  #
X! CFLAGS = -O $(POSIX)
X! CC = cc
X  
X  #
X  # Set LIBS to any additional libraries that you need linked in with pax.
X--- 26,33 ----
X  # Set CFLAGS to whatever makes your C compiler happy.  Be sure to include 
X  # the definition of $(POSIX) in the flag.
X  #
X! CFLAGS = -Ml $(POSIX)
X! CC = cl
X  
X  #
X  # Set LIBS to any additional libraries that you need linked in with pax.
X***************
X*** 83,91 ****
X  #    to this directory and choose the DIROBJ lines.  Please note that this 
X  #    version of dirent has been modified to work as a stand-alone. 
X  #
X! DIRENT=
X  #DIRENT= -ldirent
X! #DIROBJ= paxdir.o
X  
X  #
X  # END CONFIGURATION SECTION 
X--- 83,91 ----
X  #    to this directory and choose the DIROBJ lines.  Please note that this 
X  #    version of dirent has been modified to work as a stand-alone. 
X  #
X! #DIRENT=
X  #DIRENT= -ldirent
X! DIROBJ= msd_dir.obj msd_dio.obj getopt.obj
X  
X  #
X  # END CONFIGURATION SECTION 
X***************
X*** 98,107 ****
X  HEADERS= config.h func.h limits.h port.h pax.h 
X  SOURCE= pax.c append.c buffer.c cpio.c create.c extract.c fileio.c\
X  	link.c list.c mem.c namelist.c names.c pass.c pathname.c\
X! 	port.c regexp.c replace.c tar.c ttyio.c warn.c wildmat.c
X! OBJECT= pax.o append.o buffer.o cpio.o create.o extract.o fileio.o\
X! 	link.o list.o mem.o namelist.o names.o pass.o pathname.o\
X! 	port.o regexp.o replace.o tar.o ttyio.o warn.o wildmat.o $(DIROBJ)
X  PROGS = pax tar cpio
X  PMAN1 = pax.1 tar.1
X  PMAN5 = pax.5 tar.5
X--- 98,107 ----
X  HEADERS= config.h func.h limits.h port.h pax.h 
X  SOURCE= pax.c append.c buffer.c cpio.c create.c extract.c fileio.c\
X  	link.c list.c mem.c namelist.c names.c pass.c pathname.c\
X! 	port.c regexp.c replace.c tar.c ttyio.c warn.c wildmat.c backsp.c
X! OBJECT= pax.obj append.obj buffer.obj cpio.obj create.obj extract.obj fileio.obj\
X! 	link.obj list.obj mem.obj namelist.obj names.obj pass.obj pathname.obj\
X! 	port.obj regexp.obj replace.obj tar.obj ttyio.obj warn.obj wildmat.obj backsp.obj $(DIROBJ)
X  PROGS = pax tar cpio
X  PMAN1 = pax.1 tar.1
X  PMAN5 = pax.5 tar.5
X***************
X*** 125,131 ****
X  	lint $(LINTFLAGS) $(SOURCE)
X  
X  pax : $(OBJECT)
X! 	$(CC) $(CFLAGS) $(LDFLAGS) -o pax $(OBJECT) $(DIRENT) $(LIBS)
X  
X  tar: pax
X  	rm -f tar
X--- 125,132 ----
X  	lint $(LINTFLAGS) $(SOURCE)
X  
X  pax : $(OBJECT)
X! #	$(CC) $(CFLAGS) $(LDFLAGS) -o pax $(OBJECT) $(DIRENT) $(LIBS)
X! 	link @linkit
X  
X  tar: pax
X  	rm -f tar
diff -rc ../paxorig/append.c ./append.c
X*** ../paxorig/append.c	Tue Feb 14 13:36:07 1989
X--- ./append.c	Wed Feb 15 10:59:55 1989
X***************
X*** 48,54 ****
X  
X  #include "pax.h"
X  
X- 
X  /* append_archive - main loop for appending to a tar archive
X   *
X   * DESCRIPTION
X--- 48,53 ----
X***************
X*** 72,88 ****
X  {
X      Stat            sb;
X      char            name[PATH_MAX + 1];
X  
X      name[0] = '\0';
X      while (get_header(name, &sb) == 0) {
X! 	if (((ar_format == TAR)
X! 	     ? buf_skip(ROUNDUP((OFFSET) sb.sb_size, BLOCKSIZE))
X! 	     : buf_skip((OFFSET) sb.sb_size)) < 0) {
X  	    warn(name, "File data is corrupt");
X  	}
X      }
X      /* we have now gotten to the end of the archive... */
X  
X      /* reset the buffer now that we have read the entire archive */
X      bufend = bufidx = bufstart;
X      create_archive();
X--- 71,102 ----
X  {
X      Stat            sb;
X      char            name[PATH_MAX + 1];
X+     int             blk;
X+     OFFSET          btotal, skp;
X  
X+     btotal = 0;
X      name[0] = '\0';
X      while (get_header(name, &sb) == 0) {
X! 	skp = (ar_format == TAR)
X! 	     ? ROUNDUP((OFFSET) sb.sb_size, BLOCKSIZE)
X! 	     : (OFFSET) sb.sb_size;
X! 	if (buf_skip(skp) < 0) {
X  	    warn(name, "File data is corrupt");
X  	}
X+         /* the tar file header is written out in one BLOCKSIZE block */
X+         btotal += skp + BLOCKSIZE;
X      }
X      /* we have now gotten to the end of the archive... */
X  
X+     /* backspace to the end of the last archive */
X+     if (ar_format == TAR)
X+     {
X+         blk = (OFFSET) (bufend - bufstart - (btotal % blocksize)) / BLOCKSIZE;
X+     	blk = back_space_records(blk);
X+     	if (blk < 0)
X+     	    warn("can't backspace", "append archive may be no good");
X+     }
X+     
X      /* reset the buffer now that we have read the entire archive */
X      bufend = bufidx = bufstart;
X      create_archive();
diff -rc ../paxorig/buffer.c ./buffer.c
X*** ../paxorig/buffer.c	Tue Feb 14 13:36:11 1989
X--- ./buffer.c	Wed Feb 15 11:00:00 1989
X***************
X*** 581,587 ****
X  
X      /* if (bufidx - buf > 0) */
X  	for (buf = bufstart; len = bufidx - buf;) {
X! 	    if ((got = write(archivefd, buf, MIN(len, blocksize))) > 0) {
X  		buf += got;
X  	    } else if (got < 0) {
X  		next(AR_WRITE);
X--- 581,587 ----
X  
X      /* if (bufidx - buf > 0) */
X  	for (buf = bufstart; len = bufidx - buf;) {
X! 	    if ((got = WRITE(archivefd, buf, MIN(len, blocksize))) > 0) {
X  		buf += got;
X  	    } else if (got < 0) {
X  		next(AR_WRITE);
X***************
X*** 627,633 ****
X  	    }
X  	}
X  	while (!failed && !areof && bufstart + blocksize - bufend >= blocksize) {
X! 	    if ((got = read(archivefd, bufend, (unsigned int) blocksize)) > 0) {
X  		bufend += got;
X  	    } else if (got < 0) {
X  		failed = -1;
X--- 627,633 ----
X  	    }
X  	}
X  	while (!failed && !areof && bufstart + blocksize - bufend >= blocksize) {
X! 	    if ((got = READ(archivefd, bufend, (unsigned int) blocksize)) > 0) {
X  		bufend += got;
X  	    } else if (got < 0) {
X  		failed = -1;
X***************
X*** 686,695 ****
X      bend = (bidx = buf) + len;
X      while (bidx < bend) {
X  	if (*bidx++) {
X! 	    return (write(fd, buf, len) == len ? 0 : -1);
X  	}
X      }
X!     return (lseek(fd, (OFFSET) len, 1) < 0 ? -1 : len);
X  }
X  
X  
X--- 686,695 ----
X      bend = (bidx = buf) + len;
X      while (bidx < bend) {
X  	if (*bidx++) {
X! 	    return (WRITE(fd, buf, len) == len ? 0 : -1);
X  	}
X      }
X!     return (LSEEK(fd, (OFFSET) len, 1) < 0 ? -1 : len);
X  }
X  
X  
diff -rc ../paxorig/config.h ./config.h
X*** ../paxorig/config.h	Tue Feb 14 13:36:13 1989
X--- ./config.h	Wed Feb 15 11:00:06 1989
X***************
X*** 45,51 ****
X   * Defining XENIX_286 will automatically define USG.
X   *
X   */
X! #define XENIX_286	/* Running on a XENIX 286 system */
X  
X  /*
X   * USG - USG (Unix System V) specific modifications
X--- 45,51 ----
X   * Defining XENIX_286 will automatically define USG.
X   *
X   */
X! /*#define XENIX_286	/* Running on a XENIX 286 system */
X  
X  /*
X   * USG - USG (Unix System V) specific modifications
X***************
X*** 59,65 ****
X   *
X   * Define BSD if you are running some version of BSD Unix
X   */
X! #define BSD 	/* Running on a BSD System */
X  
X  /*
X   * DEF_AR_FILE - tar only (required)
X--- 59,65 ----
X   *
X   * Define BSD if you are running some version of BSD Unix
X   */
X! /* #define BSD 	/* Running on a BSD System */
X  
X  /*
X   * DEF_AR_FILE - tar only (required)
X***************
X*** 77,84 ****
X   * received from.  On most unix systems, this should be /dev/tty, however, on
X   * some systems, such as MS-DOS, it my need to be different (e.g. "con:").
X   */
X! #define	TTY	"/dev/tty"	/* for most versions of UNIX */
X! /* #define	TTY	"con:"		/* For MS-DOS */
X  
X  /*
X   * PAXDIR - if you do not have directory access routines
X--- 77,84 ----
X   * received from.  On most unix systems, this should be /dev/tty, however, on
X   * some systems, such as MS-DOS, it my need to be different (e.g. "con:").
X   */
X! /* #define	TTY	"/dev/tty"	/* for most versions of UNIX */
X! #define	TTY	"/dev/con"		/* For MS-DOS */
X  
X  /*
X   * PAXDIR - if you do not have directory access routines
X***************
X*** 128,135 ****
X   * Some systems have signal defines to return an int *, other return a
X   * void *.  Please choose the correct value for your system.
X   */
X! /* #define SIG_T	void	/* signal defined as "void (*signal)()" */
X! #define SIG_T	int	/* signal defined as "int (*signal)()" */
X  
X  /*
X   * STRCSPN - use the strcspn function included with pax
X--- 128,135 ----
X   * Some systems have signal defines to return an int *, other return a
X   * void *.  Please choose the correct value for your system.
X   */
X! #define SIG_T	void	/* signal defined as "void (*signal)()" */
X! /* #define SIG_T	int	/* signal defined as "int (*signal)()" */
X  
X  /*
X   * STRCSPN - use the strcspn function included with pax
diff -rc ../paxorig/cpio.c ./cpio.c
X*** ../paxorig/cpio.c	Tue Feb 14 13:36:16 1989
X--- ./cpio.c	Wed Feb 15 11:00:12 1989
X***************
X*** 162,167 ****
X--- 162,173 ----
X  	}
X      }
X  
X+ #ifdef MSDOS
X+     setmode(fileno(msgfile), O_TEXT);
X+     if (names_from_stdin)
X+         setmode(fileno(stdin), O_TEXT);
X+ #endif
X+ 
X      if (f_create + f_pass + f_extract != 1) {
X  	usage();
X      }
diff -rc ../paxorig/fileio.c ./fileio.c
X*** ../paxorig/fileio.c	Tue Feb 14 13:36:28 1989
X--- ./fileio.c	Wed Feb 15 11:00:20 1989
X***************
X*** 87,105 ****
X  	    archivefd = STDOUT;
X  	}
X      } else if (mode == AR_READ) {
X! 	archivefd = open(ar_file, O_RDONLY | O_BINARY);
X  	bufend = bufidx = bufstart;	/* set up for initial read */
X      } else if (mode == AR_WRITE) {
X! 	archivefd = open(ar_file, O_WRONLY|O_TRUNC|O_CREAT|O_BINARY, 0666);
X      } else if (mode == AR_APPEND) {
X! 	archivefd = open(ar_file, O_RDWR | O_BINARY, 0666);
X  	bufend = bufidx = bufstart;	/* set up for initial read */
X      }
X  
X!     if (archivefd < 0) {
X! 	warnarch(strerror(), (OFFSET) 0);
X! 	return (-1);
X      }
X      ++arvolume;
X      return (0);
X  }
X--- 87,119 ----
X  	    archivefd = STDOUT;
X  	}
X      } else if (mode == AR_READ) {
X! 	archivefd = OPEN2(ar_file, O_RDONLY | O_BINARY);
X  	bufend = bufidx = bufstart;	/* set up for initial read */
X      } else if (mode == AR_WRITE) {
X! 	archivefd = OPEN3(ar_file, O_WRONLY|O_TRUNC|O_CREAT|O_BINARY, 0666);
X      } else if (mode == AR_APPEND) {
X! 	archivefd = OPEN3(ar_file, O_RDWR | O_BINARY, 0666);
X  	bufend = bufidx = bufstart;	/* set up for initial read */
X      }
X  
X! #ifndef MSDOS
X!      if (archivefd < 0) {
X!  	warnarch(strerror(), (OFFSET) 0);
X!  	return (-1);
X!      }
X! #else
X!     if (dio_open_check(ar_file) < 0) {
X! 	if (archivefd >= 0) {
X! 	    warnarch(strerror(), (OFFSET) 0);
X! 	    return (-1);
X!         }
X!     } else {
X!         if (archivefd < 0) {
X! 	    warnarch(strerror(), (OFFSET) 0);
X! 	    return (-1);
X!         }
X      }
X+ #endif
X      ++arvolume;
X      return (0);
X  }
X***************
X*** 124,130 ****
X  #endif
X  {
X      if (archivefd != STDIN && archivefd != STDOUT) {
X! 	close(archivefd);
X      }
X      areof = 0;
X  }
X--- 138,144 ----
X  #endif
X  {
X      if (archivefd != STDIN && archivefd != STDOUT) {
X! 	CLOSE(archivefd);
X      }
X      areof = 0;
X  }
X***************
X*** 225,230 ****
X--- 239,245 ----
X      }
X      perm = asb->sb_mode & S_IPERM;
X      switch (asb->sb_mode & S_IFMT) {
X+ #if defined(S_IFBLK) && defined(S_IFCHR)
X      case S_IFBLK:
X      case S_IFCHR:
X  	fd = 0;
X***************
X*** 261,266 ****
X--- 276,282 ----
X  	}
X  	return(0);
X  	break;
X+ #endif
X      case S_IFDIR:
X  	if (exists) {
X  	    if (perm != operm && chmod(name, (int) perm) < 0) {
diff -rc ../paxorig/func.h ./func.h
X*** ../paxorig/func.h	Tue Feb 14 13:36:30 1989
X--- ./func.h	Wed Feb 15 11:00:22 1989
X***************
X*** 43,48 ****
X--- 43,49 ----
X  extern char    	       *mem_str(char *);
X  extern char    	       *strerror(void);
X  extern int      	ar_read(void);
X+ extern int		back_space_records(int n);
X  extern int      	buf_read(char *, uint);
X  extern int      	buf_skip(OFFSET);
X  extern int      	create_archive(void);
X***************
X*** 81,92 ****
X  extern struct group    *getgrnam();
X  extern struct passwd   *getpwuid();
X  extern char    	       *getenv(char *);
X  extern SIG_T   	      (*signal())();
X  extern Link            *islink(char *, Stat *);
X  extern char            *finduname(int);
X  extern char            *findgname(int);
X  extern int		findgid(char *gname);
X! extern char    	       *malloc();
X  
X  #else /* !__STDC__ */
X  
X--- 82,95 ----
X  extern struct group    *getgrnam();
X  extern struct passwd   *getpwuid();
X  extern char    	       *getenv(char *);
X+ #ifndef MSDOS
X  extern SIG_T   	      (*signal())();
X+ #endif
X  extern Link            *islink(char *, Stat *);
X  extern char            *finduname(int);
X  extern char            *findgname(int);
X  extern int		findgid(char *gname);
X! extern char    	       *malloc(uint);
X  
X  #else /* !__STDC__ */
X  
X***************
X*** 96,101 ****
X--- 99,105 ----
X  extern char    	       *mem_str();
X  extern char    	       *strerror();
X  extern int      	ar_read();
X+ extern int		back_space_records();
X  extern int      	buf_read();
X  extern int      	buf_skip();
X  extern int      	create_archive();
diff -rc ../paxorig/list.c ./list.c
X*** ../paxorig/list.c	Tue Feb 14 13:36:50 1989
X--- ./list.c	Wed Feb 15 11:00:33 1989
X***************
X*** 217,224 ****
X--- 217,226 ----
X  	    asb->sb_mode |= S_IFREG;
X  	    break;
X  	case BLKTYPE:
X+ #ifdef S_IFBLK
X  	    asb->sb_mode |= S_IFBLK;
X  	    break;
X+ #endif
X  	case CHRTYPE:
X  	    asb->sb_mode |= S_IFCHR;
X  	    break;
X***************
X*** 430,437 ****
X  	if (f_verbose) {
X  	    atm = localtime(&asb->sb_mtime);
X  	    print_mode(asb->sb_mode);
X! 	    fprintf(msgfile," %d/%d %6d %3s %2d %02d:%02d %4d %s",
X! 		    asb->sb_uid, asb->sb_gid, asb->sb_size,
X  		    monnames[atm->tm_mon], atm->tm_mday, atm->tm_hour, 
X  		    atm->tm_min, atm->tm_year + 1900, name);
X  	} else {
X--- 432,439 ----
X  	if (f_verbose) {
X  	    atm = localtime(&asb->sb_mtime);
X  	    print_mode(asb->sb_mode);
X! 	    fprintf(msgfile," %d/%d %6ld %3s %2d %02d:%02d %4d %s",
X! 		    asb->sb_uid, asb->sb_gid, (long) asb->sb_size,
X  		    monnames[atm->tm_mon], atm->tm_mday, atm->tm_hour, 
X  		    atm->tm_min, atm->tm_year + 1900, name);
X  	} else {
X***************
X*** 508,521 ****
X  	} else {
X  	    fprintf(msgfile, " %-8u", USH(asb->sb_gid));
X  	}
X  	switch (asb->sb_mode & S_IFMT) {
X  	case S_IFBLK:
X  	case S_IFCHR:
X  	    fprintf(msgfile, "\t%3d, %3d",
X  		           major(asb->sb_rdev), minor(asb->sb_rdev));
X  	    break;
X  	case S_IFREG:
X! 	    fprintf(msgfile, "\t%8ld", asb->sb_size);
X  	    break;
X  	default:
X  	    fprintf(msgfile, "\t        ");
X--- 510,526 ----
X  	} else {
X  	    fprintf(msgfile, " %-8u", USH(asb->sb_gid));
X  	}
X+ 
X  	switch (asb->sb_mode & S_IFMT) {
X+ #ifdef S_IFBLK
X  	case S_IFBLK:
X+ #endif
X  	case S_IFCHR:
X  	    fprintf(msgfile, "\t%3d, %3d",
X  		           major(asb->sb_rdev), minor(asb->sb_rdev));
X  	    break;
X  	case S_IFREG:
X! 	    fprintf(msgfile, "\t%8ld", (long) asb->sb_size);
X  	    break;
X  	default:
X  	    fprintf(msgfile, "\t        ");
X***************
X*** 574,582 ****
X--- 579,589 ----
X  	    putc('l', msgfile); 
X  	    break;
X  #endif	/* S_IFLNK */
X+ #ifdef S_IFBLK
X  	case S_IFBLK: 
X  	    putc('b', msgfile); 
X  	    break;
X+ #endif
X  	case S_IFCHR: 
X  	    putc('c', msgfile); 
X  	    break;
diff -rc ../paxorig/namelist.c ./namelist.c
X*** ../paxorig/namelist.c	Tue Feb 14 13:36:56 1989
X--- ./namelist.c	Wed Feb 15 11:00:48 1989
X***************
X*** 137,142 ****
X--- 137,143 ----
X  {
X      int             i;		/* Length of string */
X      struct nm_list *p;		/* Current struct pointer */
X+     char *malloc();
X  
X      i = strlen(name);
X      p = (struct nm_list *) malloc((unsigned) (i + sizeof(struct nm_list)));
X***************
X*** 421,426 ****
X--- 422,430 ----
X  	    } while (in_subdir && (! dirp));
X  	}
X      } while (err < 0);
X+ #ifdef MSDOS
X+     strlwr(name);
X+ #endif    
X      return (0);
X  }
X  
diff -rc ../paxorig/names.c ./names.c
X*** ../paxorig/names.c	Tue Feb 14 13:36:58 1989
X--- ./names.c	Wed Feb 15 11:00:51 1989
X***************
X*** 56,62 ****
X  
X  
X  /* Internal Identifiers */
X! 
X  static int      saveuid = -993;
X  static char     saveuname[TUNMLEN];
X  static int      my_uid = -993;
X--- 56,62 ----
X  
X  
X  /* Internal Identifiers */
X! #ifndef MSDOS
X  static int      saveuid = -993;
X  static char     saveuname[TUNMLEN];
X  static int      my_uid = -993;
X***************
X*** 64,70 ****
X--- 64,78 ----
X  static int      savegid = -993;
X  static char     savegname[TGNMLEN];
X  static int      my_gid = -993;
X+ #else
X+ static int      saveuid = 0;
X+ static char     saveuname[TUNMLEN] = "";
X+ static int      my_uid = 0;
X  
X+ static int      savegid = 0;
X+ static char     savegname[TGNMLEN] = "";
X+ static int      my_gid = 0;
X+ #endif
X  
X  /* finduname - find a user or group name from a uid or gid
X   *
diff -rc ../paxorig/pax.c ./pax.c
X*** ../paxorig/pax.c	Tue Feb 14 13:37:10 1989
X--- ./pax.c	Wed Feb 15 11:01:04 1989
X***************
X*** 65,71 ****
X  
X  /* Headers */
X  
X! #define NO_EXTERN
X  #include "pax.h"
X  
X  
X--- 65,71 ----
X  
X  /* Headers */
X  
X! /* #define NO_EXTERN */
X  #include "pax.h"
X  
X  
X***************
X*** 160,165 ****
X--- 160,187 ----
X  
X  #endif
X  {
X+ #ifdef MSDOS
X+     {
X+     	extern int _fmode;
X+     	_fmode = O_BINARY;
X+ 	setmode(fileno(stdin), O_BINARY);
X+ 	setmode(fileno(stdout), O_BINARY);
X+     }
X+     /* strip the pathname off of the name of the executable */
X+     strlwr(argv[0]);
X+     if ((myname = strrchr(argv[0], '/')) != (char *)NULL) {
X+ 	myname++;
X+     } else if ((myname = strrchr(argv[0], '\\')) != (char *)NULL) {
X+ 	myname++;
X+     } else {
X+ 	myname = argv[0];
X+     }
X+     {
X+     	char *tmp;
X+     	if ((tmp = strrchr(myname, '.')) != (char *) NULL)
X+     		*tmp = '\0';
X+     }
X+ #else
X      /* strip the pathname off of the name of the executable */
X      if ((myname = strrchr(argv[0], '/')) != (char *)NULL) {
X  	myname++;
X***************
X*** 166,171 ****
X--- 188,194 ----
X      } else {
X  	myname = argv[0];
X      }
X+ #endif
X  
X      /* set upt for collecting other command line arguments */
X      name_init(argc, argv);
X***************
X*** 338,343 ****
X--- 361,370 ----
X  	}
X      }
X  
X+ #ifdef MSDOS
X+     setmode(fileno(msgfile), O_TEXT);
X+ #endif
X+ 
X      if (blocksize == 0) {
X  	blocking = 1;
X  	blocksize = blocking * BLOCKSIZE;
X***************
X*** 352,357 ****
X--- 379,388 ----
X  	if (optind >= n_argc) {
X  	    names_from_stdin++;		/* args from stdin */
X  	}
X+ #ifdef MSDOS
X+         if (names_from_stdin)
X+             setmode(fileno(stdin), O_TEXT);
X+ #endif
X  	open_archive(AR_WRITE);
X  	create_archive();
X      } else if (f_append) {
X***************
X*** 369,374 ****
X--- 400,409 ----
X  	if (optind >= n_argc) {
X  	    names_from_stdin++;		/* args from stdin */
X  	}
X+ #ifdef MSDOS
X+         if (names_from_stdin)
X+             setmode(fileno(stdin), O_TEXT);
X+ #endif
X  	pass(dirname);
X      } else {
X  	usage();
diff -rc ../paxorig/pax.h ./pax.h
X*** ../paxorig/pax.h	Tue Feb 14 13:37:12 1989
X--- ./pax.h	Wed Feb 15 11:01:06 1989
X***************
X*** 42,48 ****
X--- 42,50 ----
X  #include <signal.h>
X  #include <ctype.h>
X  #include <sys/types.h>
X+ #ifndef MSDOS
X  #include <sys/ioctl.h>
X+ #endif
X  #include <sys/stat.h>
X  #include "regexp.h"
X  
X***************
X*** 58,73 ****
X  # else
X  #  ifdef XENIX_286
X  #   include <sys/ndir.h>
X! #  else XENIX_286
X  #   include <sys/dir.h>
X! #  endif XENIX_286
X  # endif /* hpux */
X  # define dirent direct
X  #endif
X  
X  #ifndef	major
X  #   include <sys/sysmacros.h>
X! #endif				/* major */
X  
X  #ifdef	SYSTIME
X  #   include <sys/time.h>
X--- 60,77 ----
X  # else
X  #  ifdef XENIX_286
X  #   include <sys/ndir.h>
X! #  else /* XENIX_286 */
X  #   include <sys/dir.h>
X! #  endif /* XENIX_286 */
X  # endif /* hpux */
X  # define dirent direct
X  #endif
X  
X+ #ifndef MSDOS
X  #ifndef	major
X  #   include <sys/sysmacros.h>
X! #endif			/* major */	
X! #endif
X  
X  #ifdef	SYSTIME
X  #   include <sys/time.h>
X***************
X*** 84,96 ****
X  #endif
X  #ifdef XENIX_286
X  #include <sys/param.h>
X! #endif XENIX_286
X  
X  #include <pwd.h>
X  #include <grp.h>
X  #ifndef XENIX_286
X  #include <sys/file.h>
X! #endif XENIX_286
X  
X  /* Defines */
X  
X--- 88,132 ----
X  #endif
X  #ifdef XENIX_286
X  #include <sys/param.h>
X! #endif /* XENIX_286 */
X! 
X! 
X! #ifndef MSDOS
X  
X  #include <pwd.h>
X  #include <grp.h>
X+ 
X  #ifndef XENIX_286
X  #include <sys/file.h>
X! #endif /* XENIX_286 */
X! 
X! #else
X! #include <io.h>
X! #define	major(x)	(0)
X! #define	minor(x)	(0)
X! #define	makedev(x,y)	(0)
X! struct passwd
X! {
X! 	char	*pw_name;
X! 	char	*pw_passwd;
X! 	int	pw_uid;
X! 	int	pw_gid;
X! 	int	pw_quota;
X! 	char	*pw_comment;
X! 	char	*pw_gecos;
X! 	char	*pw_dir;
X! 	char	*pw_shell;
X! };
X! struct group
X! {
X! 	char	*gr_name;
X! 	char	*gr_passwd;
X! 	int	gr_gid;
X! 	char	**gr_mem;
X! };
X! #endif	
X! 
X! #include "msd_dio.h"
X  
X  /* Defines */
X  
diff -rc ../paxorig/port.c ./port.c
X*** ../paxorig/port.c	Tue Feb 14 13:37:33 1989
X--- ./port.c	Wed Feb 15 11:01:11 1989
X***************
X*** 58,64 ****
X   * the list in the #if !defined()'s below and it'll all be skipped. 
X   */
X  
X! #if !defined(mc300) && !defined(mc500) && !defined(mc700) && !defined(BSD)
X  
X  /* mkdir - make a directory
X   *
X--- 58,65 ----
X   * the list in the #if !defined()'s below and it'll all be skipped. 
X   */
X  
X! #if !defined(mc300) && !defined(mc500) && !defined(mc700) && !defined(BSD) \
X! && !defined(MSDOS)
X  
X  /* mkdir - make a directory
X   *
X***************
X*** 190,192 ****
X--- 191,246 ----
X  }
X  
X  #endif /* MASSCOMP, BSD */
X+ 
X+ #ifdef MSDOS
X+ 
X+ static struct passwd npwd = {"", "", 0, 0, 0, "", "", "", ""};
X+ static char gmem1[] = "";
X+ static char *gmem2[] = {gmem1, (char *) NULL};
X+ static struct group ngrp = {"", "", 0, gmem2};
X+ 
X+ struct passwd *getpwuid(x)
X+ int x;
X+ {
X+ 	return(&npwd);
X+ }
X+ struct passwd *getpwnam(s)
X+ char *s;
X+ {
X+ 	return(&npwd);
X+ }
X+ struct group *getgrgid(x)
X+ int x;
X+ {
X+ 	return(&ngrp);
X+ }
X+ struct group *getgrnam(s)
X+ char *s;
X+ {
X+ 	return(&ngrp);
X+ }
X+ int setgrent()
X+ {
X+ 	return(0);
X+ }
X+ int getuid()
X+ {
X+ 	return(0);
X+ }
X+ int getgid()
X+ {
X+ 	return(0);
X+ }
X+ int link(f, t)
X+ char *f, *t;
X+ {
X+ 	return(-1);
X+ }
X+ int chown(n, uid, gid)
X+ char *n;
X+ int uid, gid;
X+ {
X+ 	return(0);
X+ }
X+ #endif
X+ 
diff -rc ../paxorig/regexp.c ./regexp.c
X*** ../paxorig/regexp.c	Tue Feb 14 13:37:42 1989
X--- ./regexp.c	Wed Feb 15 11:01:17 1989
X***************
X*** 114,119 ****
X--- 114,120 ----
X  #define	OPEN	20		/* no	Mark this point in input as start of
X  				 * #n. */
X   /* OPEN+1 is number 1, etc. */
X+ #undef CLOSE
X  #define	CLOSE	30		/* no	Analogous to OPEN. */
X  
X  /*
diff -rc ../paxorig/tar.c ./tar.c
X*** ../paxorig/tar.c	Tue Feb 14 13:37:48 1989
X--- ./tar.c	Wed Feb 15 11:01:26 1989
X***************
X*** 171,176 ****
X--- 171,182 ----
X  	}
X      }
X  
X+ #ifdef MSDOS
X+     setmode(fileno(msgfile), O_TEXT);
X+     if (names_from_stdin)
X+         setmode(fileno(stdin), O_TEXT);
X+ #endif
X+ 
X      /* check command line argument sanity */
X      if (f_create + f_extract + f_list + f_append + f_newer != 1) {
X  	(void) fprintf(stderr,
X***************
X*** 182,187 ****
X--- 188,196 ----
X  
X      /* set the blocking factor, if not set by the user */
X      if (blocking == 0) {
X+ #ifdef MSDOS
X+         blocking = 20;
X+ #else
X  #ifdef USG
X  	if (f_extract || f_list) {
X  	    blocking = DEF_BLOCKING;
X***************
X*** 192,197 ****
X--- 201,207 ----
X  #else /* !USG */
X  	blocking = 20;
X  #endif /* USG */
X+ #endif
X      }
X      blocksize = blocking * BLOCKSIZE;
X      buf_allocate((OFFSET) blocksize);
diff -rc ../paxorig/ttyio.c ./ttyio.c
X*** ../paxorig/ttyio.c	Tue Feb 14 13:37:50 1989
X--- ./ttyio.c	Wed Feb 15 11:01:28 1989
X***************
X*** 91,96 ****
X--- 91,99 ----
X      if ((fd = open(TTY, O_RDWR)) < 0) {
X  	return (-1);
X      }
X+ #ifdef MSDOS
X+     setmode(fd, O_TEXT);
X+ #endif
X      if (isatty(fd)) {
X  	return (fd);
X      }
END_OF_FILE
if test 23594 -ne `wc -c <'paxpatch'`; then
    echo shar: \"'paxpatch'\" unpacked with wrong size!
fi
# end of 'paxpatch'
fi
echo shar: End of shell archive.
exit 0

-- 
Harold G. Walters			walters@1.ce.okstate.edu
School of Civil Engineering		okstate!oksce1!walters
Oklahoma State University		"If all you have is a hammer, 
Stillwater, OK  74078			 everything looks like a nail".