summaryrefslogtreecommitdiffstats
path: root/usr.bin
diff options
context:
space:
mode:
authorkientzle <kientzle@FreeBSD.org>2004-04-08 06:12:01 +0000
committerkientzle <kientzle@FreeBSD.org>2004-04-08 06:12:01 +0000
commit1b8aab3f614c2c9ea94f3995fcd1d713c7fa5e32 (patch)
treecd1718ff7ecd194b94603738159e2fea2fa75f0f /usr.bin
parent79523261f7033c669a4667180dca6dfeef18be2c (diff)
downloadFreeBSD-src-1b8aab3f614c2c9ea94f3995fcd1d713c7fa5e32.zip
FreeBSD-src-1b8aab3f614c2c9ea94f3995fcd1d713c7fa5e32.tar.gz
Add support for -T option on create.
(Required by pkg_create.)
Diffstat (limited to 'usr.bin')
-rw-r--r--usr.bin/tar/bsdtar.c11
-rw-r--r--usr.bin/tar/bsdtar.h2
-rw-r--r--usr.bin/tar/write.c53
3 files changed, 60 insertions, 6 deletions
diff --git a/usr.bin/tar/bsdtar.c b/usr.bin/tar/bsdtar.c
index 98c3c83..083779d8 100644
--- a/usr.bin/tar/bsdtar.c
+++ b/usr.bin/tar/bsdtar.c
@@ -57,7 +57,7 @@ static const char *progname;
static char ** rewrite_argv(int *argc, char ** src_argv,
const char *optstring);
-const char *tar_opts = "b:C:cF:f:HhjkLlmnOoPprtUuvwXxyZz";
+const char *tar_opts = "b:C:cF:f:HhjkLlmnOoPprtT:UuvwXxyZz";
#ifdef HAVE_GETOPT_LONG
/*
@@ -179,8 +179,9 @@ main(int argc, char **argv)
case 'c': case 'r': case 'u': case 'x':
break;
default:
- fprintf(stderr,
- "First option must be one of: -c, -r, -t, -u, -x\n");
+ bsdtar_errc(1, 0,
+ "First option '%c' unrecognized; "
+ "should be -c, -r, -t, -u, -x", mode);
usage();
exit(1);
}
@@ -279,6 +280,10 @@ main(int argc, char **argv)
umask(0);
bsdtar->extract_flags |= ARCHIVE_EXTRACT_PERM;
break;
+ case 'T': /* GNU tar */
+ only_mode(mode, opt, "c");
+ bsdtar->names_from_file = optarg;
+ break;
case 'U': /* GNU tar */
only_mode(mode, opt, "x");
bsdtar->extract_flags |= ARCHIVE_EXTRACT_UNLINK;
diff --git a/usr.bin/tar/bsdtar.h b/usr.bin/tar/bsdtar.h
index 428c1b4..dd37326 100644
--- a/usr.bin/tar/bsdtar.h
+++ b/usr.bin/tar/bsdtar.h
@@ -47,8 +47,8 @@ struct bsdtar {
const char *filename; /* -f filename */
const char *create_format; /* -F format */
const char *start_dir; /* -C dir */
+ const char *names_from_file; /* -T file */
int bytes_per_block; /* -b block_size */
- int records_per_block;
int verbose; /* -v */
int extract_flags; /* Flags for extract operation */
char symlink_mode; /* H or L, per BSD conventions */
diff --git a/usr.bin/tar/write.c b/usr.bin/tar/write.c
index 17f62a1..5bf9884 100644
--- a/usr.bin/tar/write.c
+++ b/usr.bin/tar/write.c
@@ -70,6 +70,8 @@ struct archive_dir_entry {
static void add_dir_list(struct bsdtar *bsdtar, const char *path,
time_t mtime_sec, int mtime_nsec);
+void archive_names_from_file(struct bsdtar *bsdtar,
+ struct archive *a);
static void create_cleanup(struct bsdtar *);
static int append_archive(struct bsdtar *, struct archive *,
const char *fname);
@@ -96,7 +98,7 @@ tar_mode_c(struct bsdtar *bsdtar)
struct archive *a;
int r;
- if (*bsdtar->argv == NULL)
+ if (*bsdtar->argv == NULL && bsdtar->names_from_file == NULL)
bsdtar_errc(1, 0, "no files or directories specified");
a = archive_write_new();
@@ -273,7 +275,7 @@ tar_mode_u(struct bsdtar *bsdtar)
/*
- * Write files/dirs given on command line to opened archive.
+ * Write user-specified files/dirs to opened archive.
*/
static void
write_archive(struct archive *a, struct bsdtar *bsdtar)
@@ -286,6 +288,9 @@ write_archive(struct archive *a, struct bsdtar *bsdtar)
if (bsdtar->start_dir != NULL && chdir(bsdtar->start_dir))
bsdtar_errc(1, errno, "chdir(%s) failed", bsdtar->start_dir);
+ if (bsdtar->names_from_file != NULL)
+ archive_names_from_file(bsdtar, a);
+
while (*bsdtar->argv) {
arg = *bsdtar->argv;
if (arg[0] == 'C' && arg[1] == '=') {
@@ -360,6 +365,50 @@ write_archive(struct archive *a, struct bsdtar *bsdtar)
create_cleanup(bsdtar);
}
+/* Archive names specified in file. */
+void
+archive_names_from_file(struct bsdtar *bsdtar, struct archive *a)
+{
+ FILE *f;
+ char buff[1024];
+ int l;
+
+ if (strcmp(bsdtar->names_from_file, "-") == 0)
+ f = stdin;
+ else
+ f = fopen(bsdtar->names_from_file, "r");
+
+ while (fgets(buff, sizeof(buff), f) != NULL) {
+ l = strlen(buff);
+ if (buff[l-1] == '\n')
+ buff[l-1] = '\0';
+
+ /*
+ * This -C processing hack is really quite ugly, but
+ * gtar does it this way and pkg_create depends on it,
+ * so I guess I'm stuck having to implement it.
+ *
+ * Someday, pkg_create will just use libarchive directly
+ * and this will just be a bad memory.
+ */
+ if (strcmp(buff, "-C") == 0) {
+ if (fgets(buff, sizeof(buff), f) == NULL)
+ bsdtar_errc(1, errno,
+ "Unexpected end of filename list; "
+ "directory expected after -C");
+ l = strlen(buff);
+ if (buff[l-1] == '\n')
+ buff[l-1] = '\0';
+ if (chdir(buff))
+ bsdtar_errc(1, errno, "chdir(%s) failed", buff);
+ } else {
+ write_heirarchy(bsdtar, a, buff);
+ }
+ }
+
+ if (strcmp(bsdtar->names_from_file, "-") != 0)
+ fclose(f);
+}
/* Copy from specified archive to current archive. */
static int
OpenPOWER on IntegriCloud