static char *RCSid
= "$Header: cpio.c,v 1.4 83/12/16 13:18:54 ks Exp $";
/* cpio COMPILE: cc -O cpio.c -s -i -o cpio
cpio -- copy file collections
#define EQ(x,y) (strcmp(x,y)==0)
/* for VAX, Interdata, ... */
#define MKSHORT(v,lv) {U.l=1L;if(U.c[0]) U.l=lv,v[0]=U.s[1],v[1]=U.s[0]; else U.l=lv,v[0]=U.s[0],v[1]=U.s[1];}
#define MAGIC 070707 /* cpio magic number */
#define IN 1 /* copy in */
#define OUT 2 /* copy out */
#define PASS 3 /* direct copy */
#define HDRSIZE (Hdr.h_name - (char *)&Hdr) /* header size minus filename field */
#define LINKS 1000 /* max no. of links allowed */
#define CHARS 76 /* ASCII header size minus filename field */
#define BUFSIZE 512 /* In u370, can't use BUFSIZ nor BSIZE */
#define CPIOBSZ 8192 /* file read/write */
#define MAXPATHLEN 1024 /* Maximum length of any single path name */
struct stat Statb
, Xstatb
;
char h_name
[MAXPATHLEN
+1];
unsigned Bufsize
= BUFSIZE
; /* default record size */
short Buf
[CPIOBSZ
/2], *Dbuf
;
char BBuf
[CPIOBSZ
], *Cbuf
;
char Fullname
[MAXPATHLEN
+1],
union { long l
; short s
[2]; char c
[4]; } U
;
/* for VAX, Interdata, ... */
U
.s
[0] = v
[1], U
.s
[1] = v
[0];
U
.s
[0] = v
[0], U
.s
[1] = v
[1];
case 'a': /* reset access time */
case 'B': /* change record size to 5120 bytes */
if(argc
> 2 ) { /* save patterns, if any */
for(i
= 0; (i
+2) < argc
; ++i
)
case 'f': /* do not consider patterns in cmd line */
if(access(argv
[2], 2) == -1) {
fprintf(stderr
,"cannot write in <%s>\n", argv
[2]);
strcpy(Fullname
, argv
[2]); /* destination directory */
hflag
? stat(Fullname
, &Xstatb
) : lstat(Fullname
, &Xstatb
);
if((Xstatb
.st_mode
&S_IFMT
) != S_IFDIR
)
case 'c': /* ASCII header */
case 'd': /* create directories when needed */
case 'l': /* link files, when necessary */
case 'm': /* retain mod time */
case 'r': /* rename files interactively */
Rtty
= fopen("/dev/tty", "r");
Wtty
= fopen("/dev/tty", "w");
if(Rtty
==NULL
|| Wtty
==NULL
) {
"Cannot rename (/dev/tty missing)\n");
case 'S': /* swap halfwords */
case 's': /* swap bytes */
case 't': /* table of contents */
case 'u': /* copy unconditionally */
case 'v': /* verbose table of contents */
case '6': /* for old, sixth-edition files */
fprintf(stderr
,"Options must include o|i|p\n");
setio(-1,1); /* turn on physio */
fprintf(stderr
,"Pass and Rename cannot be used together\n");
printf("`B' option is irrelevant with the '-p' option\n");
Cp
= Cbuf
= (char *)malloc(Bufsize
);
Wp
= Dbuf
= (short *)malloc(Bufsize
);
case OUT
: /* get filename, copy header and file out */
if( mklong(Hdr
.h_filesize
) == 0L) {
if((Hdr
.h_mode
&S_IFMT
) == S_IFLNK
) {
writehdr(Chdr
,CHARS
+Hdr
.h_namesize
);
bwrite(&Hdr
, HDRSIZE
+Hdr
.h_namesize
);
if (One_extent
|| Multi_extent
) {
writehdr(Chdr
,CHARS
+Hdr
.h_namesize
);
bwrite(&Hdr
, HDRSIZE
+Hdr
.h_namesize
);
if((Ifile
= open(Hdr
.h_name
, 0)) < 0) {
fprintf(stderr
,"<%s> ?\n", Hdr
.h_name
);
writehdr(Chdr
,CHARS
+Hdr
.h_namesize
);
bwrite(&Hdr
, HDRSIZE
+Hdr
.h_namesize
);
if (One_extent
|| Multi_extent
) {
writehdr(Chdr
,CHARS
+Hdr
.h_namesize
);
bwrite(&Hdr
, HDRSIZE
+Hdr
.h_namesize
);
Hdr
.h_filesize
[0] = Actual_size
[0];
Hdr
.h_filesize
[1] = Actual_size
[1];
for(filesz
=mklong(Hdr
.h_filesize
); filesz
>0; filesz
-= CPIOBSZ
){
ct
= filesz
>CPIOBSZ
? CPIOBSZ
: filesz
;
if(read(Ifile
, Cflag
? BBuf
: (char *)Buf
, ct
) < 0) {
fprintf(stderr
,"Cannot read %s\n", Hdr
.h_name
);
Cflag
? writehdr(BBuf
,ct
): bwrite(Buf
,ct
);
set_time(Hdr
.h_name
, Statb
.st_atime
,
fprintf(stderr
,"%s\n", Hdr
.h_name
);
/* copy trailer, after all files have been copied */
strcpy(Hdr
.h_name
, "TRAILER!!!");
MKSHORT(Hdr
.h_filesize
, 0L);
Hdr
.h_namesize
= strlen("TRAILER!!!") + 1;
writehdr(Chdr
,CHARS
+Hdr
.h_namesize
);
bwrite(&Hdr
, HDRSIZE
+Hdr
.h_namesize
);
Cflag
? writehdr(Cbuf
, Bufsize
): bwrite(Dbuf
, Bufsize
);
Ofile
= ckname(Hdr
.h_name
)? openout(Hdr
.h_name
): 0;
if ((Hdr
.h_mode
&S_IFMT
) != S_IFLNK
)
for(filesz
=mklong(Hdr
.h_filesize
); filesz
>0; filesz
-= CPIOBSZ
){
ct
= filesz
>CPIOBSZ
? CPIOBSZ
: filesz
;
Cflag
? readhdr(BBuf
,ct
): bread(Buf
, ct
);
Cflag
? swap(BBuf
,ct
): swap(Buf
,ct
);
if(write(Ofile
, Cflag
? BBuf
: (char *)Buf
, ct
) < 0) {
fprintf(stderr
,"Cannot write %s\n", Hdr
.h_name
);
if(chmod(Hdr
.h_name
, Hdr
.h_mode
) < 0) {
fprintf(stderr
,"Cannot chmod <%s> (errno:%d)\n", Hdr
.h_name
, errno
);
set_time(Hdr
.h_name
, mklong(Hdr
.h_mtime
), mklong(Hdr
.h_mtime
));
case PASS
: /* move files around */
fullp
= Fullname
+ strlen(Fullname
);
fprintf(stderr
,"Use `-d' option to copy <%s>\n",Hdr
.h_name
);
while(Hdr
.h_name
[i
] == '/')
strcpy(fullp
, &(Hdr
.h_name
[i
]));
&& ((Hdr
.h_mode
&S_IFMT
)!=S_IFLNK
)
&& (Uid
== Statb
.st_uid
|| !Uid
)) {
if(link(Hdr
.h_name
, Fullname
) < 0) { /* missing dir.? */
if(link(Hdr
.h_name
, Fullname
) < 0) {
"Cannot link <%s> & <%s>\n",
/* try creating (only twice) */
if(link(Hdr
.h_name
, Fullname
) < 0) { /* missing dir.? */
}while(ans
< 2 && missdir(Fullname
) == 0);
fprintf(stderr
,"Cannot create directory for <%s> (errno:%d)\n", Fullname
, errno
);
fprintf(stderr
,"Cannot link <%s> & <%s>\n", Hdr
.h_name
, Fullname
);
if(chmod(Hdr
.h_name
, Hdr
.h_mode
) < 0) {
fprintf(stderr
,"Cannot chmod <%s> (errno:%d)\n", Hdr
.h_name
, errno
);
set_time(Hdr
.h_name
, mklong(Hdr
.h_mtime
), mklong(Hdr
.h_mtime
));
if (One_extent
|| Multi_extent
)
if(!(Ofile
= openout(Fullname
))) {
if((Ifile
= open(Hdr
.h_name
, 0)) < 0) {
fprintf(stderr
,"<%s> ?\n", Hdr
.h_name
);
for(; filesz
> 0; filesz
-= CPIOBSZ
) {
ct
= filesz
>CPIOBSZ
? CPIOBSZ
: filesz
;
if(read(Ifile
, Buf
, ct
) < 0) {
fprintf(stderr
,"Cannot read %s\n", Hdr
.h_name
);
if(write(Ofile
, Buf
, ct
) < 0) {
fprintf(stderr
,"Cannot write %s\n", Hdr
.h_name
);
Blocks
+= ((ct
+ (BUFSIZE
- 1)) / BUFSIZE
);
set_time(Hdr
.h_name
, Statb
.st_atime
,
if(chmod(Fullname
, Hdr
.h_mode
) < 0) {
fprintf(stderr
,"Cannot chmod <%s> (errno:%d)\n", Fullname
, errno
);
set_time(Fullname
, Statb
.st_atime
, mklong(Hdr
.h_mtime
));
/* print number of blocks actually copied */
fprintf(stderr
,"%ld blocks\n", Blocks
* (Bufsize
>>9));
fprintf(stderr
,"Usage: cpio -o[acvB] <name-list >collection\n%s\n%s\n",
" cpio -i[cdmrstuvfB6] [pattern ...] <collection",
" cpio -p[adlmruv] directory <name-list");
getname() /* get file name, get info for header */
register char *namep
= Name
;
if (fgets(namep
, MAXPATHLEN
, stdin
) == NULL
)
namep
[namelen
- 1] = '\0';
fprintf(stderr
,"Warning: filename <%s> too long for older versions of cpio\n", namep
);
if(*namep
== '.' && namep
[1] == '/')
strcpy(Hdr
.h_name
, namep
);
if((hflag
? stat(namep
, &Statb
) : lstat(namep
, &Statb
)) < 0) {
fprintf(stderr
,"< %s > ?\n", Hdr
.h_name
);
ftype
= Statb
.st_mode
& Filetype
;
A_directory
= (ftype
== S_IFDIR
);
A_special
= (ftype
== S_IFBLK
)
A_special
|= (ftype
== S_IFREC
);
One_extent
= (ftype
== S_IF1EXT
);
Multi_extent
= (ftype
== S_IFEXT
);
Hdr
.h_namesize
= strlen(Hdr
.h_name
) + 1;
Hdr
.h_uid
= Statb
.st_uid
;
Hdr
.h_gid
= Statb
.st_gid
;
Hdr
.h_dev
= Statb
.st_dev
;
Hdr
.h_ino
= Statb
.st_ino
;
Hdr
.h_mode
= Statb
.st_mode
;
MKSHORT(Hdr
.h_mtime
, Statb
.st_mtime
);
Hdr
.h_nlink
= Statb
.st_nlink
;
tlong
= ((Hdr
.h_mode
&S_IFMT
) == S_IFREG
)? Statb
.st_size
: 0L;
if (One_extent
|| Multi_extent
) tlong
= Statb
.st_size
;
MKSHORT(Hdr
.h_filesize
, tlong
);
Hdr
.h_rdev
= Statb
.st_rdev
;
bintochar(t
) /* ASCII header write */
sprintf(Chdr
,"%.6o%.6ho%.6ho%.6ho%.6ho%.6ho%.6ho%.6ho%.11lo%.6ho%.11lo%s",
MAGIC
,Statb
.st_dev
,Statb
.st_ino
,Statb
.st_mode
,Statb
.st_uid
,
Statb
.st_gid
,Statb
.st_nlink
,Statb
.st_rdev
& 00000177777,
Statb
.st_mtime
,(short)strlen(Hdr
.h_name
)+1,t
,Hdr
.h_name
);
chartobin() /* ASCII header read */
sscanf(Chdr
,"%6ho%6ho%6ho%6ho%6ho%6ho%6ho%6ho%11lo%6ho%11lo",
&Hdr
.h_magic
,&Hdr
.h_dev
,&Hdr
.h_ino
,&Hdr
.h_mode
,&Hdr
.h_uid
,
&Hdr
.h_gid
,&Hdr
.h_nlink
,&Hdr
.h_rdev
,&Longtime
,&Hdr
.h_namesize
,
MKSHORT(Hdr
.h_filesize
, Longfile
);
MKSHORT(Hdr
.h_mtime
, Longtime
);
gethdr() /* get file headers */
if(Hdr
.h_magic
!= MAGIC
) {
fprintf(stderr
,"Out of phase--get help\n");
readhdr(Hdr
.h_name
, Hdr
.h_namesize
);
bread(Hdr
.h_name
, Hdr
.h_namesize
);
if(EQ(Hdr
.h_name
, "TRAILER!!!"))
ftype
= Hdr
.h_mode
& Filetype
;
A_directory
= (ftype
== S_IFDIR
);
A_special
=(ftype
== S_IFBLK
)
A_special
|= (ftype
== S_IFREC
);
One_extent
= (ftype
== S_IF1EXT
);
Multi_extent
= (ftype
== S_IFEXT
);
if (One_extent
|| Multi_extent
) {
Actual_size
[0] = Hdr
.h_filesize
[0];
Actual_size
[1] = Hdr
.h_filesize
[1];
if(Hdr
.h_magic
!= MAGIC
) {
fprintf(stderr
,"Out of phase--get RT help\n");
readhdr(Hdr
.h_name
, Hdr
.h_namesize
);
bread(Hdr
.h_name
, Hdr
.h_namesize
);
ckname(namep
) /* check filenames with patterns given on cmd line */
if(fflag
^ !nmatch(namep
, Pattern
)) {
if(Rename
&& !A_directory
) { /* rename interactively */
fprintf(Wtty
, "Rename <%s>\n", namep
);
fgets(namep
, MAXPATHLEN
, Rtty
);
namep
[strlen(namep
) - 1] = '\0';
if ((Hdr
.h_mode
&S_IFMT
) == S_IFLNK
)
discardfile(mklong(Hdr
.h_filesize
));
if (Toc
&& ((Hdr
.h_mode
&S_IFMT
) == S_IFLNK
))
discardfile(mklong(Hdr
.h_filesize
));
openout(namep
) /* open files for writing, set all necessary info */
if(!strncmp(namep
, "./", 2))
Cd_name = namep = cd(namep);
|| EQ(namep
, "..")) /* do not consider . or .. files */
if((hflag
? stat(namep
, &Xstatb
) : lstat(namep
, &Xstatb
)) == -1) {
/* try creating (only twice) */
}while(ans
< 2 && missdir(namep
) == 0);
fprintf(stderr
,"Cannot create directory for <%s> (errno:%d)\n", namep
, errno
);
fprintf(stderr
,"Cannot create directory <%s> (errno:%d)\n", namep
, errno
);
if(chmod(namep
, Hdr
.h_mode
) < 0) {
fprintf(stderr
,"Cannot chmod <%s> (errno:%d)\n", namep
, errno
);
if(chown(namep
, Hdr
.h_uid
, Hdr
.h_gid
) < 0) {
fprintf(stderr
,"Cannot chown <%s> (errno:%d)\n", namep
, errno
);
set_time(namep
, mklong(Hdr
.h_mtime
), mklong(Hdr
.h_mtime
));
if((hflag
? stat(namep
, &Xstatb
) : lstat(namep
, &Xstatb
)) == 0) {
if((Uncond
&& !((!(Xstatb
.st_mode
& S_IWRITE
) || A_special
) && (Uid
!= 0)))) {
fprintf(stderr
,"cannot unlink current <%s> (errno:%d)\n", namep
, errno
);
if(!Uncond
&& (mklong(Hdr
.h_mtime
) <= Xstatb
.st_mtime
) &&
((Hdr
.h_mode
&S_IFMT
)!=S_IFLNK
)) {
/* There's a newer version of file on destination */
if(mklong(Hdr
.h_mtime
) < Xstatb
.st_mtime
)
fprintf(stderr
,"current <%s> newer\n", np
);
&& Hdr
.h_ino
== Xstatb
.st_ino
&& Hdr
.h_dev
== Xstatb
.st_dev
) {
fprintf(stderr
,"Attempt to pass file to self!\n");
if ((Hdr
.h_mode
& Filetype
) == S_IFLNK
) {
if((Hdr
.h_mode
& Filetype
) == S_IFIFO
)
/* try creating (only twice) */
if(mknod(namep
, Hdr
.h_mode
, Hdr
.h_rdev
) < 0) {
}while(ans
< 2 && missdir(np
) == 0);
fprintf(stderr
,"Cannot create directory for <%s> (errno:%d)\n", namep
, errno
);
fprintf(stderr
,"Cannot mknod <%s> (errno:%d)\n", namep
, errno
);
if(One_extent
|| Multi_extent
) {
/* try creating (only twice) */
if((f
= falloc(namep
, Hdr
.h_mode
, longword(Hdr
.h_filesize
[0]))) < 0) {
}while(ans
< 2 && missdir(np
) == 0);
fprintf(stderr
,"Cannot create directory for <%s> (errno:%d)\n", namep
, errno
);
fprintf(stderr
,"Cannot create <%s> (errno:%d)\n", namep
, errno
);
if(filespace
< longword(Hdr
.h_filesize
[0])){
fprintf(stderr
,"Cannot create contiguous file <%s> proper size\n", namep
);
fprintf(stderr
," <%s> will be created as a regular file\n", namep
);
if(unlink(Fullname
) != 0)
fprintf(stderr
,"<%s> not removed\n", namep
);
Hdr
.h_mode
= (Hdr
.h_mode
& !S_IFMT
) | S_IFREG
;
One_extent
= Multi_extent
= 0;
Hdr
.h_filesize
[0] = Actual_size
[0];
Hdr
.h_filesize
[1] = Actual_size
[1];
if (!(One_extent
|| Multi_extent
)) {
/* try creating (only twice) */
if((f
= creat(namep
, Hdr
.h_mode
)) < 0) {
}while(ans
< 2 && missdir(np
) == 0);
fprintf(stderr
,"Cannot create directory for <%s> (errno:%d)\n", namep
, errno
);
fprintf(stderr
,"Cannot create <%s> (errno:%d)\n", namep
, errno
);
chown(namep
, Hdr
.h_uid
, Hdr
.h_gid
);
while((rv
=read(Input
, &(((char *)Dbuf
)[in
]), Bufsize
- in
)) != Bufsize
- in
) {
Input
= chgreel(0, Input
);
while((rv
=read(Input
, &(((char *)Cbuf
)[in
]), Bufsize
- in
)) != Bufsize
- in
) {
Input
= chgreel(0, Input
);
if(write(Output
, Dbuf
, Bufsize
)<0) {
Output
= chgreel(1, Output
);
if(write(Output
,Cbuf
,Bufsize
)<0) {
Output
= chgreel(1,Output
);
postml(namep
, np
) /* linking funtion */
register char *namep
, *np
;
for(i
= 0; i
< mlinks
; ++i
) {
if(mlinks
== LINKS
) break;
if(ml
[i
]->m_ino
==Hdr
.h_ino
&&
ml
[i
]->m_dev
==Hdr
.h_dev
) {
printf("%s linked to %s\n", ml
[i
]->m_name
,
if(Option
== IN
&& *ml
[i
]->m_name
!= '/') {
Fullname
[Pathend
] = '\0';
strcat(Fullname
, ml
[i
]->m_name
);
/* try linking (only twice) */
if(link(mlp
, namep
) < 0) {
}while(ans
< 2 && missdir(np
) == 0);
fprintf(stderr
,"Cannot create directory for <%s> (errno:%d)\n", np
, errno
);
fprintf(stderr
,"Cannot link <%s> & <%s>.\n", ml
[i
]->m_name
, np
);
set_time(namep
, mklong(Hdr
.h_mtime
), mklong(Hdr
.h_mtime
));
|| !(ml
[mlinks
] = (struct ml
*)malloc(strlen(np
) + 2 + sizeof(struct ml
)))) {
fprintf(stderr
,"Too many links\n");
fprintf(stderr
,"No memory for links\n");
ml
[mlinks
]->m_dev
= Hdr
.h_dev
;
ml
[mlinks
]->m_ino
= Hdr
.h_ino
;
strcpy(ml
[mlinks
]->m_name
, np
);
pentry(namep
) /* print verbose table of contents */
static short lastid
= -1;
static struct passwd
*pw
;
struct passwd
*getpwuid();
printf("%-7o", Hdr
.h_mode
& 0177777);
printf("%-6s", pw
->pw_name
);
if(pw
= getpwuid((int)Hdr
.h_uid
)) {
printf("%-6s", pw
->pw_name
);
printf("%-6d", Hdr
.h_uid
);
printf("%7ld ", mklong(Hdr
.h_filesize
));
U
.l
= mklong(Hdr
.h_mtime
);
strcpy(tbuf
, ctime((long *)&U
.l
));
printf(" %s %s\n", &tbuf
[4], namep
);
/* pattern matching functions */
if((**pat
== '!' && !gmatch(s
, *pat
+1))
register cc
, ok
, lc
, scc
;
return(gmatch(++s
, ++p
));
ok
|= ((lc
<= scc
) && (scc
<= (cc
=p
[1])));
if(scc
) return(gmatch(++s
, ++p
));
if (gmatch(s
++,p
)) return(1);
/* If 4.2 BSD or greater, we have a nifty syscall for this .. */
* Error: mkdir returns -1, makdir returns 1
* Success: mkdir returns 0, makdir returns 0
return(-mkdir(namep
, 0777));
makdir(namep
) /* make needed directories */
while(wait(&status
) != pid
);
execl("/bin/mkdir", "mkdir", namep
, 0);
return ((status
>>8) & 0377)? 1: 0;
swap(buf
, ct
) /* swap halfwords, bytes or both */
register union swp
{ long longw
; short shortv
[2]; char charv
[4]; } *pbuf
;
savect
= ct
; savebuf
= buf
;
if(byteswap
|| bothswap
) {
pbuf
= (union swp
*)savebuf
;
if (n
= ct
% sizeof(union swp
)) {
for(i
= ct
+ 1; i
<= ct
+ (sizeof(union swp
) - n
); i
++) pbuf
->charv
[i
] = 0;
for (i
= ct
; i
< ct
+ (sizeof(union swp
) - n
); i
++) pbuf
->charv
[i
] = 0;
ct
= (ct
+ (sizeof(union swp
) -1)) / sizeof(union swp
);
pbuf
->shortv
[0] = pbuf
->shortv
[1];
if (n
= ct
% sizeof(union swp
))
for (i
= ct
; i
< ct
+ (sizeof(union swp
) - n
); i
++) pbuf
->charv
[i
] = 0;
ct
= (ct
+ (sizeof(union swp
) -1)) / sizeof(union swp
);
pbuf
->shortv
[0] = pbuf
->shortv
[1];
set_time(namep
, atime
, mtime
) /* set access and modification times */
fprintf(stderr
,"errno: %d, ", errno
);
fprintf(stderr
,"Can't %s\n", x
? "write output": "read input");
if((statb
.st_mode
&S_IFMT
) != S_IFCHR
)
if((statb
.st_mode
& (S_IFBLK
|S_IFREC
))==0)
fprintf(stderr
,"If you want to go on, type device/file name when ready\n");
devtty
= fopen("/dev/tty", "r");
str
[strlen(str
) - 1] = '\0';
if((f
= open(str
, x
? 1: 0)) < 0) {
fprintf(stderr
,"That didn't work");
for(np
= namep
; *np
; ++np
)
if(np
== namep
) continue; /* skip over 'root slash' */
if((hflag
? stat(namep
, &Xstatb
) : lstat(namep
, &Xstatb
)) == -1) {
if((ct
= makdir(namep
)) != 0) {
fprintf(stderr
,"missing 'd' option\n");
if (ct
== 2) ct
= 0; /* the file already exists */
pwd() /* get working directory */
fgets(Fullname
, 256, dir
);
Pathend
= strlen(Fullname
);
Fullname
[Pathend
- 1] = '/';
char * cd(n
) /* change directories */
char *p_save
= Name
, *n_save
= n
, *p_end
= 0;
static char dotdot
[]="../../../../../../../../../../../../../../../../../../../../../../../../../../../../../../../../";
if(*n
== '/') /* don't try to chdir on full pathnames */
for(; *p
&& *n
== *p
; ++p
, ++n
) { /* whatever part of strings == */
p_save
= p
+1, n_save
= n
+1;
for(slashes
= 0; *p
; ++p
) { /* if prev is longer, chdir("..") */
slashes
= slashes
* 3 - 1;
p_end
= p
+1, n_save
= n
+1;
if(chdir(p_save
) == -1) {
if((ans
= missdir(p_save
)) == -1) {
fprintf(stderr
,"Cannot chdir (no `d' option)\n");
fprintf(stderr
,"Cannot chdir - no write permission\n");
} else if(chdir(p_save
) == -1) {
fprintf(stderr
,"Cannot chdir\n");
Actual_size
[0] = Hdr
.h_filesize
[0];
Actual_size
[1] = Hdr
.h_filesize
[1];
else if ((tfile
= open(Hdr
.h_name
,0)) < 0)
MKSHORT(Hdr
.h_filesize
,tlong
);
readlink(Hdr
.h_name
, Cflag
? BBuf
: (char *)Buf
, CPIOBSZ
)) < 0) {
fprintf(stderr
,"<%s> ?\n", Hdr
.h_name
);
MKSHORT(Hdr
.h_filesize
, (long)(simlnksz
));
if (Option
== OUT
) { /* Option!=PASS */
writehdr(Chdr
,CHARS
+Hdr
.h_namesize
);
writehdr(BBuf
, simlnksz
);
bwrite(&Hdr
, HDRSIZE
+Hdr
.h_namesize
);
set_time(Hdr
.h_name
, Statb
.st_atime
, Statb
.st_mtime
);
if(Verbose
&& Option
== OUT
)
fprintf(stderr
,"%s\n", Hdr
.h_name
);
* Get information concerning symbolic link.
linklen
= mklong(Hdr
.h_filesize
);
/* This is fucked up.... */
/* Print error and try to recover.... */
fprintf(stderr
,"Symbolic link <%s> too long\n", namep
);
* This is what normally happens for IN Option..
readhdr(BBuf
, (int)linklen
);
bread(Buf
, (int)linklen
);
else { /* Option == PASS */
linklen
= mklong(Hdr
.h_filesize
);
* Null terminate the value of the symbolic link...
((char *)Buf
)[linklen
] = '\0';
statres
= hflag
? stat(namep
, &Xstatb
) : lstat(namep
, &Xstatb
);
if(!Uncond
&& (statres
== 0) &&
(mklong(Hdr
.h_mtime
) <= Xstatb
.st_mtime
)) {
/* There's a newer version of symbolic link on destination */
fprintf(stderr
,"current <%s> newer\n", namep
);
* unlink an old symbolic link if it is present..
if ((statres
== 0) && (unlink(namep
) < 0)) {
fprintf(stderr
,"cannot unlink existing symbolic link <%s> (errno:%d)\n", namep
, errno
);
umask((~Hdr
.h_mode
)&0777);
if (symlink((Cflag
? BBuf
: (char *)(Buf
)), namep
) < 0) {
} while (ans
< 2 && missdir(namep
) == 0);
fprintf(stderr
,"Cannot create directory for <%s> (errno:%d)\n", namep
, errno
);
fprintf(stderr
,"Cannot create symbolic link <%s> (errno:%d)\n", namep
, errno
);
if(Uid
== 0 && chown(namep
, Hdr
.h_uid
, Hdr
.h_gid
) < 0) {
fprintf(stderr
,"Cannot chown <%s> (errno:%d)\n", namep
, errno
);
* No way to set the modify time on a symbolic link..
* Pass through option will miss printing this one..
if ((Option
== PASS
) && Verbose
)