* Copyright (c) 1983, 1993
* The Regents of the University of California. All rights reserved.
* %sccs.include.redist.c%
static char sccsid
[] = "@(#)utilities.c 8.4 (Berkeley) %G%";
#include <ufs/ufs/dinode.h>
* Insure that all the components of a pathname exist.
start
= index(name
, '/');
for (cp
= start
; *cp
!= '\0'; cp
++) {
/* Safe; we know the pathname exists in the dump. */
ep
= addentry(name
, pathsearch(name
)->d_ino
, NODE
);
* Change a name to a unique temporary name.
register struct entry
*ep
;
char oldname
[MAXPATHLEN
];
if (ep
->e_flags
& TMPNAME
)
badentry(ep
, "mktempname: called with TMPNAME");
(void) strcpy(oldname
, myname(ep
));
ep
->e_name
= savename(gentempname(ep
));
ep
->e_namlen
= strlen(ep
->e_name
);
renameit(oldname
, myname(ep
));
* Generate a temporary name for an entry.
static char name
[MAXPATHLEN
];
for (np
= lookupino(ep
->e_ino
);
np
!= NULL
&& np
!= ep
; np
= np
->e_links
)
badentry(ep
, "not on ino list");
(void) sprintf(name
, "%s%d%d", TMPHDR
, i
, ep
->e_ino
);
* Rename a file or directory.
if (!Nflag
&& rename(from
, to
) < 0) {
fprintf(stderr
, "warning: cannot rename %s to %s: %s\n",
from
, to
, strerror(errno
));
vprintf(stdout
, "rename %s to %s\n", from
, to
);
* Create a new node (directory).
badentry(np
, "newnode: not a node");
if (!Nflag
&& mkdir(cp
, 0777) < 0) {
fprintf(stderr
, "warning: %s: %s\n", cp
, strerror(errno
));
vprintf(stdout
, "Make node %s\n", cp
);
* Remove an old node (directory).
register struct entry
*ep
;
badentry(ep
, "removenode: not a node");
if (ep
->e_entries
!= NULL
)
badentry(ep
, "removenode: non-empty directory");
if (!Nflag
&& rmdir(cp
) < 0) {
fprintf(stderr
, "warning: %s: %s\n", cp
, strerror(errno
));
vprintf(stdout
, "Remove node %s\n", cp
);
register struct entry
*ep
;
badentry(ep
, "removeleaf: not a leaf");
if (!Nflag
&& unlink(cp
) < 0) {
fprintf(stderr
, "warning: %s: %s\n", cp
, strerror(errno
));
vprintf(stdout
, "Remove leaf %s\n", cp
);
linkit(existing
, new, type
)
if (!Nflag
&& symlink(existing
, new) < 0) {
"warning: cannot create symbolic link %s->%s: %s\n",
new, existing
, strerror(errno
));
} else if (type
== HARDLINK
) {
if (!Nflag
&& link(existing
, new) < 0) {
"warning: cannot create hard link %s->%s: %s\n",
new, existing
, strerror(errno
));
panic("linkit: unknown type %d\n", type
);
vprintf(stdout
, "Create %s link %s->%s\n",
type
== SYMLINK
? "symbolic" : "hard", new, existing
);
if (!Nflag
&& mknod(name
, S_IFWHT
, 0) < 0) {
fprintf(stderr
, "warning: cannot create whiteout %s: %s\n",
vprintf(stdout
, "Create whiteout %s\n", name
);
register struct entry
*ep
;
badentry(ep
, "delwhiteout: not a leaf");
if (!Nflag
&& undelete(name
) < 0) {
fprintf(stderr
, "warning: cannot delete whiteout %s: %s\n",
vprintf(stdout
, "Delete whiteout %s\n", name
);
* find lowest number file (above "start") that needs to be extracted
register struct entry
*ep
;
for ( ; start
< maxino
; start
++) {
if (ep
== NULL
|| ep
->e_type
== NODE
)
if (ep
->e_flags
& (NEW
|EXTRACT
))
* find highest number file (below "start") that needs to be extracted
register struct entry
*ep
;
for ( ; start
> ROOTINO
; start
--) {
if (ep
== NULL
|| ep
->e_type
== NODE
)
if (ep
->e_flags
& (NEW
|EXTRACT
))
* report on a badly formed entry
register struct entry
*ep
;
fprintf(stderr
, "bad entry: %s\n", msg
);
fprintf(stderr
, "name: %s\n", myname(ep
));
fprintf(stderr
, "parent name %s\n", myname(ep
->e_parent
));
if (ep
->e_sibling
!= NULL
)
fprintf(stderr
, "sibling name: %s\n", myname(ep
->e_sibling
));
if (ep
->e_entries
!= NULL
)
fprintf(stderr
, "next entry name: %s\n", myname(ep
->e_entries
));
fprintf(stderr
, "next link name: %s\n", myname(ep
->e_links
));
"next hashchain name: %s\n", myname(ep
->e_next
));
fprintf(stderr
, "entry type: %s\n",
ep
->e_type
== NODE
? "NODE" : "LEAF");
fprintf(stderr
, "inode number: %ld\n", ep
->e_ino
);
panic("flags: %s\n", flagvalues(ep
));
* Construct a string indicating the active flag bits of an entry.
register struct entry
*ep
;
static char flagbuf
[BUFSIZ
];
(void) strcpy(flagbuf
, "|NIL");
if (ep
->e_flags
& REMOVED
)
(void) strcat(flagbuf
, "|REMOVED");
if (ep
->e_flags
& TMPNAME
)
(void) strcat(flagbuf
, "|TMPNAME");
if (ep
->e_flags
& EXTRACT
)
(void) strcat(flagbuf
, "|EXTRACT");
(void) strcat(flagbuf
, "|NEW");
(void) strcat(flagbuf
, "|KEEP");
if (ep
->e_flags
& EXISTED
)
(void) strcat(flagbuf
, "|EXISTED");
* Check to see if a name is on a dump tape.
ino
= ((dp
= pathsearch(name
)) == NULL
) ? 0 : dp
->d_ino
;
if (ino
== 0 || TSTINO(ino
, dumpmap
) == 0)
fprintf(stderr
, "%s is not on the tape\n", name
);
fprintf(stderr
, "%s? [yn] ", question
);
while (c
!= '\n' && getc(terminal
) != '\n')
} while (c
!= 'y' && c
!= 'n');
* handle unexpected inconsistencies
panic(const char *fmt
, ...)
vfprintf(stderr
, fmt
, ap
);
if (reply("abort") == GOOD
) {
if (reply("dump core") == GOOD
)