summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDavid Oberhollenzer <david.oberhollenzer@sigma-star.at>2022-06-29 18:21:58 +0200
committerDavid Oberhollenzer <david.oberhollenzer@sigma-star.at>2022-07-08 19:17:35 +0200
commite6a19ba1a05f77f051187a6b1a828ee6d39ce052 (patch)
treec8a1566b10883edbe4a8bc9a724461f4003aaa10
parent359d71e90050a8b83f7bc7d2ecd4ff29c477cc22 (diff)
Cleanup: split libtar header, move to sub directory
Some of the on-disk format internals are moved to a separate header and some of the stuff from internal.h is moved to that format header. C++ guards are added in addtion. Everything PAX related is moved to pax_header.c, some internal functions are marked as static. Signed-off-by: David Oberhollenzer <david.oberhollenzer@sigma-star.at>
-rw-r--r--bin/sqfs2tar/sqfs2tar.h2
-rw-r--r--bin/tar2sqfs/tar2sqfs.h3
-rw-r--r--include/common.h1
-rw-r--r--include/tar/format.h105
-rw-r--r--include/tar/tar.h (renamed from include/tar.h)83
-rw-r--r--lib/tar/Makemodule.am6
-rw-r--r--lib/tar/base64.c59
-rw-r--r--lib/tar/checksum.c4
-rw-r--r--lib/tar/cleanup.c2
-rw-r--r--lib/tar/internal.h36
-rw-r--r--lib/tar/number.c24
-rw-r--r--lib/tar/padd_file.c3
-rw-r--r--lib/tar/pax_header.c161
-rw-r--r--lib/tar/read_header.c2
-rw-r--r--lib/tar/read_sparse_map.c54
-rw-r--r--lib/tar/read_sparse_map_new.c5
-rw-r--r--lib/tar/read_sparse_map_old.c4
-rw-r--r--lib/tar/record_to_memory.c3
-rw-r--r--lib/tar/urldecode.c38
-rw-r--r--lib/tar/write_header.c1
-rw-r--r--tests/libtar/tar_big_file.c2
-rw-r--r--tests/libtar/tar_fuzz.c2
-rw-r--r--tests/libtar/tar_simple.c2
-rw-r--r--tests/libtar/tar_sparse.c2
-rw-r--r--tests/libtar/tar_sparse_gnu.c2
-rw-r--r--tests/libtar/tar_target_filled.c2
-rw-r--r--tests/libtar/tar_xattr.c2
-rw-r--r--tests/libtar/tar_xattr_bin.c2
28 files changed, 310 insertions, 302 deletions
diff --git a/bin/sqfs2tar/sqfs2tar.h b/bin/sqfs2tar/sqfs2tar.h
index 587e8ad..4575793 100644
--- a/bin/sqfs2tar/sqfs2tar.h
+++ b/bin/sqfs2tar/sqfs2tar.h
@@ -9,7 +9,7 @@
#include "config.h"
#include "common.h"
-#include "tar.h"
+#include "tar/tar.h"
#include "io/xfrm.h"
diff --git a/bin/tar2sqfs/tar2sqfs.h b/bin/tar2sqfs/tar2sqfs.h
index d5a4ada..40c3b75 100644
--- a/bin/tar2sqfs/tar2sqfs.h
+++ b/bin/tar2sqfs/tar2sqfs.h
@@ -10,8 +10,9 @@
#include "config.h"
#include "common.h"
#include "compat.h"
-#include "tar.h"
+#include "tar/tar.h"
+#include "tar/format.h"
#include "io/xfrm.h"
#include <stdlib.h>
diff --git a/include/common.h b/include/common.h
index ab07461..91dccaa 100644
--- a/include/common.h
+++ b/include/common.h
@@ -25,7 +25,6 @@
#include "io/std.h"
#include "compat.h"
#include "fstree.h"
-#include "tar.h"
#include <stddef.h>
diff --git a/include/tar/format.h b/include/tar/format.h
new file mode 100644
index 0000000..53a4665
--- /dev/null
+++ b/include/tar/format.h
@@ -0,0 +1,105 @@
+/* SPDX-License-Identifier: GPL-3.0-or-later */
+/*
+ * format.h
+ *
+ * Copyright (C) 2019 David Oberhollenzer <goliath@infraroot.at>
+ */
+#ifndef TAR_FORMAT_H
+#define TAR_FORMAT_H
+
+#include "sqfs/predef.h"
+
+typedef struct {
+ char name[100];
+ char mode[8];
+ char uid[8];
+ char gid[8];
+ char size[12];
+ char mtime[12];
+ char chksum[8];
+ char typeflag;
+ char linkname[100];
+ char magic[6];
+ char version[2];
+ char uname[32];
+ char gname[32];
+ char devmajor[8];
+ char devminor[8];
+ union {
+ struct {
+ char prefix[155];
+ char padding[12];
+ } posix;
+
+ struct {
+ char atime[12];
+ char ctime[12];
+ char offset[12];
+ char deprecated[4];
+ char unused;
+ struct {
+ char offset[12];
+ char numbytes[12];
+ } sparse[4];
+ char isextended;
+ char realsize[12];
+ char padding[17];
+ } gnu;
+ } tail;
+} tar_header_t;
+
+typedef struct {
+ struct {
+ char offset[12];
+ char numbytes[12];
+ } sparse[21];
+ char isextended;
+ char padding[7];
+} gnu_sparse_t;
+
+#define TAR_TYPE_FILE '0'
+#define TAR_TYPE_LINK '1'
+#define TAR_TYPE_SLINK '2'
+#define TAR_TYPE_CHARDEV '3'
+#define TAR_TYPE_BLOCKDEV '4'
+#define TAR_TYPE_DIR '5'
+#define TAR_TYPE_FIFO '6'
+
+#define TAR_TYPE_GNU_SLINK 'K'
+#define TAR_TYPE_GNU_PATH 'L'
+#define TAR_TYPE_GNU_SPARSE 'S'
+
+#define TAR_TYPE_PAX 'x'
+#define TAR_TYPE_PAX_GLOBAL 'g'
+
+#define TAR_MAGIC "ustar"
+#define TAR_VERSION "00"
+
+#define TAR_MAGIC_OLD "ustar "
+#define TAR_VERSION_OLD " "
+
+#define TAR_RECORD_SIZE (512)
+
+/* artificially imposed implementation limits */
+#define TAR_MAX_SYMLINK_LEN (65536)
+#define TAR_MAX_PATH_LEN (65536)
+#define TAR_MAX_PAX_LEN (65536)
+#define TAR_MAX_SPARSE_ENT (65536)
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+int read_octal(const char *str, int digits, sqfs_u64 *out);
+
+int read_number(const char *str, int digits, sqfs_u64 *out);
+
+void update_checksum(tar_header_t *hdr);
+
+bool is_checksum_valid(const tar_header_t *hdr);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* TAR_FORMAT_H */
diff --git a/include/tar.h b/include/tar/tar.h
index dadc16e..128464e 100644
--- a/include/tar.h
+++ b/include/tar/tar.h
@@ -22,54 +22,6 @@ typedef struct sparse_map_t {
sqfs_u64 count;
} sparse_map_t;
-typedef struct {
- char name[100];
- char mode[8];
- char uid[8];
- char gid[8];
- char size[12];
- char mtime[12];
- char chksum[8];
- char typeflag;
- char linkname[100];
- char magic[6];
- char version[2];
- char uname[32];
- char gname[32];
- char devmajor[8];
- char devminor[8];
- union {
- struct {
- char prefix[155];
- char padding[12];
- } posix;
-
- struct {
- char atime[12];
- char ctime[12];
- char offset[12];
- char deprecated[4];
- char unused;
- struct {
- char offset[12];
- char numbytes[12];
- } sparse[4];
- char isextended;
- char realsize[12];
- char padding[17];
- } gnu;
- } tail;
-} tar_header_t;
-
-typedef struct {
- struct {
- char offset[12];
- char numbytes[12];
- } sparse[21];
- char isextended;
- char padding[7];
-} gnu_sparse_t;
-
typedef struct tar_xattr_t {
struct tar_xattr_t *next;
char *key;
@@ -95,28 +47,9 @@ typedef struct {
sqfs_s64 mtime;
} tar_header_decoded_t;
-#define TAR_TYPE_FILE '0'
-#define TAR_TYPE_LINK '1'
-#define TAR_TYPE_SLINK '2'
-#define TAR_TYPE_CHARDEV '3'
-#define TAR_TYPE_BLOCKDEV '4'
-#define TAR_TYPE_DIR '5'
-#define TAR_TYPE_FIFO '6'
-
-#define TAR_TYPE_GNU_SLINK 'K'
-#define TAR_TYPE_GNU_PATH 'L'
-#define TAR_TYPE_GNU_SPARSE 'S'
-
-#define TAR_TYPE_PAX 'x'
-#define TAR_TYPE_PAX_GLOBAL 'g'
-
-#define TAR_MAGIC "ustar"
-#define TAR_VERSION "00"
-
-#define TAR_MAGIC_OLD "ustar "
-#define TAR_VERSION_OLD " "
-
-#define TAR_RECORD_SIZE (512)
+#ifdef __cplusplus
+extern "C" {
+#endif
/*
Returns < 0 on failure, > 0 if cannot encode, 0 on success.
@@ -140,8 +73,6 @@ int skip_entry(istream_t *fp, sqfs_u64 size);
int read_header(istream_t *fp, tar_header_decoded_t *out);
-void free_xattr_list(tar_xattr_t *list);
-
void clear_header(tar_header_decoded_t *hdr);
/*
@@ -150,4 +81,12 @@ void clear_header(tar_header_decoded_t *hdr);
*/
int padd_file(ostream_t *fp, sqfs_u64 size);
+void free_sparse_list(sparse_map_t *sparse);
+
+void free_xattr_list(tar_xattr_t *list);
+
+#ifdef __cplusplus
+}
+#endif
+
#endif /* TAR_H */
diff --git a/lib/tar/Makemodule.am b/lib/tar/Makemodule.am
index 414aca1..7f93d13 100644
--- a/lib/tar/Makemodule.am
+++ b/lib/tar/Makemodule.am
@@ -1,10 +1,10 @@
libtar_a_SOURCES = lib/tar/read_header.c lib/tar/write_header.c
libtar_a_SOURCES += lib/tar/number.c lib/tar/checksum.c lib/tar/cleanup.c
-libtar_a_SOURCES += lib/tar/read_sparse_map.c lib/tar/read_sparse_map_old.c
-libtar_a_SOURCES += lib/tar/base64.c lib/tar/urldecode.c lib/tar/internal.h
+libtar_a_SOURCES += lib/tar/read_sparse_map_old.c
+libtar_a_SOURCES += lib/tar/internal.h
libtar_a_SOURCES += lib/tar/padd_file.c lib/tar/record_to_memory.c
libtar_a_SOURCES += lib/tar/pax_header.c lib/tar/read_sparse_map_new.c
-libtar_a_SOURCES += include/tar.h
+libtar_a_SOURCES += include/tar/tar.h include/tar/format.h
libtar_a_CFLAGS = $(AM_CFLAGS)
libtar_a_CPPFLAGS = $(AM_CPPFLAGS)
diff --git a/lib/tar/base64.c b/lib/tar/base64.c
deleted file mode 100644
index f88444a..0000000
--- a/lib/tar/base64.c
+++ /dev/null
@@ -1,59 +0,0 @@
-/* SPDX-License-Identifier: GPL-3.0-or-later */
-/*
- * base64.c
- *
- * Copyright (C) 2019 David Oberhollenzer <goliath@infraroot.at>
- */
-#include "config.h"
-
-#include "internal.h"
-
-static sqfs_u8 convert(char in)
-{
- if (isupper(in))
- return in - 'A';
- if (islower(in))
- return in - 'a' + 26;
- if (isdigit(in))
- return in - '0' + 52;
- if (in == '+')
- return 62;
- if (in == '/' || in == '-')
- return 63;
- return 0;
-}
-
-size_t base64_decode(sqfs_u8 *out, const char *in, size_t len)
-{
- sqfs_u8 *start = out;
-
- while (len > 0) {
- unsigned int diff = 0, value = 0;
-
- while (diff < 4 && len > 0) {
- if (*in == '=' || *in == '_' || *in == '\0') {
- len = 0;
- } else {
- value = (value << 6) | convert(*(in++));
- --len;
- ++diff;
- }
- }
-
- if (diff < 2)
- break;
-
- value <<= 6 * (4 - diff);
-
- switch (diff) {
- case 4: out[2] = value & 0xff; /* fall-through */
- case 3: out[1] = (value >> 8) & 0xff; /* fall-through */
- default: out[0] = (value >> 16) & 0xff;
- }
-
- out += (diff * 3) / 4;
- }
-
- *out = '\0';
- return out - start;
-}
diff --git a/lib/tar/checksum.c b/lib/tar/checksum.c
index 144ba43..6541373 100644
--- a/lib/tar/checksum.c
+++ b/lib/tar/checksum.c
@@ -6,7 +6,9 @@
*/
#include "config.h"
-#include "internal.h"
+#include "tar/format.h"
+
+#include <stdio.h>
static unsigned int get_checksum(const tar_header_t *hdr)
{
diff --git a/lib/tar/cleanup.c b/lib/tar/cleanup.c
index 2f814bf..9f33336 100644
--- a/lib/tar/cleanup.c
+++ b/lib/tar/cleanup.c
@@ -7,6 +7,8 @@
#include "config.h"
#include "internal.h"
+#include <stdlib.h>
+#include <string.h>
void free_sparse_list(sparse_map_t *sparse)
{
diff --git a/lib/tar/internal.h b/lib/tar/internal.h
index b7c4c34..cfbb938 100644
--- a/lib/tar/internal.h
+++ b/lib/tar/internal.h
@@ -9,13 +9,8 @@
#include "config.h"
-#include "tar.h"
-
-#include <string.h>
-#include <stdlib.h>
-#include <limits.h>
-#include <ctype.h>
-#include <stdio.h>
+#include "tar/tar.h"
+#include "tar/format.h"
enum {
PAX_SIZE = 0x001,
@@ -38,37 +33,10 @@ enum {
ETV_POSIX,
};
-
-#define TAR_MAX_SYMLINK_LEN (65536)
-#define TAR_MAX_PATH_LEN (65536)
-#define TAR_MAX_PAX_LEN (65536)
-#define TAR_MAX_SPARSE_ENT (65536)
-
-
-int read_octal(const char *str, int digits, sqfs_u64 *out);
-
-int read_binary(const char *str, int digits, sqfs_u64 *out);
-
-int read_number(const char *str, int digits, sqfs_u64 *out);
-
-int pax_read_decimal(const char *str, sqfs_u64 *out);
-
-void update_checksum(tar_header_t *hdr);
-
-bool is_checksum_valid(const tar_header_t *hdr);
-
-sparse_map_t *read_sparse_map(const char *line);
-
sparse_map_t *read_gnu_old_sparse(istream_t *fp, tar_header_t *hdr);
sparse_map_t *read_gnu_new_sparse(istream_t *fp, tar_header_decoded_t *out);
-void free_sparse_list(sparse_map_t *sparse);
-
-size_t base64_decode(sqfs_u8 *out, const char *in, size_t len);
-
-void urldecode(char *str);
-
char *record_to_memory(istream_t *fp, size_t size);
int read_pax_header(istream_t *fp, sqfs_u64 entsize, unsigned int *set_by_pax,
diff --git a/lib/tar/number.c b/lib/tar/number.c
index 50cb658..2f179df 100644
--- a/lib/tar/number.c
+++ b/lib/tar/number.c
@@ -6,7 +6,10 @@
*/
#include "config.h"
-#include "internal.h"
+#include "tar/format.h"
+
+#include <ctype.h>
+#include <stdio.h>
int read_octal(const char *str, int digits, sqfs_u64 *out)
{
@@ -31,7 +34,7 @@ int read_octal(const char *str, int digits, sqfs_u64 *out)
return 0;
}
-int read_binary(const char *str, int digits, sqfs_u64 *out)
+static int read_binary(const char *str, int digits, sqfs_u64 *out)
{
sqfs_u64 x, ov, result = 0;
bool first = true;
@@ -74,20 +77,3 @@ int read_number(const char *str, int digits, sqfs_u64 *out)
return read_octal(str, digits, out);
}
-
-int pax_read_decimal(const char *str, sqfs_u64 *out)
-{
- sqfs_u64 result = 0;
-
- while (*str >= '0' && *str <= '9') {
- if (result > 0xFFFFFFFFFFFFFFFFUL / 10) {
- fputs("numeric overflow parsing pax header\n", stderr);
- return -1;
- }
-
- result = (result * 10) + (*(str++) - '0');
- }
-
- *out = result;
- return 0;
-}
diff --git a/lib/tar/padd_file.c b/lib/tar/padd_file.c
index 1173096..6a1ca05 100644
--- a/lib/tar/padd_file.c
+++ b/lib/tar/padd_file.c
@@ -5,7 +5,8 @@
* Copyright (C) 2019 David Oberhollenzer <goliath@infraroot.at>
*/
#include "config.h"
-#include "tar.h"
+#include "tar/tar.h"
+#include "tar/format.h"
#include <stdlib.h>
#include <stdio.h>
diff --git a/lib/tar/pax_header.c b/lib/tar/pax_header.c
index d24def0..8a1b077 100644
--- a/lib/tar/pax_header.c
+++ b/lib/tar/pax_header.c
@@ -7,6 +7,105 @@
#include "config.h"
#include "internal.h"
+#include <ctype.h>
+#include <string.h>
+#include <stdlib.h>
+
+static sqfs_u8 base64_convert(char in)
+{
+ if (isupper(in))
+ return in - 'A';
+ if (islower(in))
+ return in - 'a' + 26;
+ if (isdigit(in))
+ return in - '0' + 52;
+ if (in == '+')
+ return 62;
+ if (in == '/' || in == '-')
+ return 63;
+ return 0;
+}
+
+static int xdigit(int x)
+{
+ if (isupper(x))
+ return x - 'A' + 0x0A;
+ if (islower(x))
+ return x - 'a' + 0x0A;
+ return x - '0';
+}
+
+static size_t base64_decode(sqfs_u8 *out, const char *in, size_t len)
+{
+ sqfs_u8 *start = out;
+
+ while (len > 0) {
+ unsigned int diff = 0, value = 0;
+
+ while (diff < 4 && len > 0) {
+ if (*in == '=' || *in == '_' || *in == '\0') {
+ len = 0;
+ } else {
+ value = (value << 6) | base64_convert(*(in++));
+ --len;
+ ++diff;
+ }
+ }
+
+ if (diff < 2)
+ break;
+
+ value <<= 6 * (4 - diff);
+
+ switch (diff) {
+ case 4: out[2] = value & 0xff; /* fall-through */
+ case 3: out[1] = (value >> 8) & 0xff; /* fall-through */
+ default: out[0] = (value >> 16) & 0xff;
+ }
+
+ out += (diff * 3) / 4;
+ }
+
+ *out = '\0';
+ return out - start;
+}
+
+static int pax_read_decimal(const char *str, sqfs_u64 *out)
+{
+ sqfs_u64 result = 0;
+
+ while (*str >= '0' && *str <= '9') {
+ if (result > 0xFFFFFFFFFFFFFFFFUL / 10) {
+ fputs("numeric overflow parsing pax header\n", stderr);
+ return -1;
+ }
+
+ result = (result * 10) + (*(str++) - '0');
+ }
+
+ *out = result;
+ return 0;
+}
+
+static void urldecode(char *str)
+{
+ unsigned char *out = (unsigned char *)str;
+ char *in = str;
+ int x;
+
+ while (*in != '\0') {
+ x = *(in++);
+
+ if (x == '%' && isxdigit(in[0]) && isxdigit(in[1])) {
+ x = xdigit(*(in++)) << 4;
+ x |= xdigit(*(in++));
+ }
+
+ *(out++) = x;
+ }
+
+ *out = '\0';
+}
static int pax_uid(tar_header_decoded_t *out, sqfs_u64 id)
{
@@ -52,6 +151,55 @@ static int pax_slink(tar_header_decoded_t *out, char *path)
return 0;
}
+static int pax_sparse_map(tar_header_decoded_t *out, const char *line)
+{
+ sparse_map_t *last = NULL, *list = NULL, *ent = NULL;
+
+ free_sparse_list(out->sparse);
+ out->sparse = NULL;
+
+ do {
+ ent = calloc(1, sizeof(*ent));
+ if (ent == NULL)
+ goto fail_errno;
+
+ if (pax_read_decimal(line, &ent->offset))
+ goto fail_format;
+
+ while (isdigit(*line))
+ ++line;
+
+ if (*(line++) != ',')
+ goto fail_format;
+
+ if (pax_read_decimal(line, &ent->count))
+ goto fail_format;
+
+ while (isdigit(*line))
+ ++line;
+
+ if (last == NULL) {
+ list = last = ent;
+ } else {
+ last->next = ent;
+ last = ent;
+ }
+ } while (*(line++) == ',');
+
+ out->sparse = list;
+ return 0;
+fail_errno:
+ perror("parsing GNU pax sparse file record");
+ goto fail;
+fail_format:
+ fputs("malformed GNU pax sparse file record\n", stderr);
+ goto fail;
+fail:
+ free_sparse_list(list);
+ free(ent);
+ return -1;
+}
+
static int pax_xattr_schily(tar_header_decoded_t *out,
tar_xattr_t *xattr)
{
@@ -76,6 +224,7 @@ enum {
PAX_TYPE_SINT = 0,
PAX_TYPE_UINT,
PAX_TYPE_STRING,
+ PAX_TYPE_CONST_STRING,
PAX_TYPE_PREFIXED_XATTR,
PAX_TYPE_IGNORE,
};
@@ -88,6 +237,7 @@ static const struct pax_handler_t {
int (*sint)(tar_header_decoded_t *out, sqfs_s64 sval);
int (*uint)(tar_header_decoded_t *out, sqfs_u64 uval);
int (*str)(tar_header_decoded_t *out, char *str);
+ int (*cstr)(tar_header_decoded_t *out, const char *str);
int (*xattr)(tar_header_decoded_t *out, tar_xattr_t *xattr);
} cb;
} pax_fields[] = {
@@ -110,6 +260,8 @@ static const struct pax_handler_t {
{ .xattr = pax_xattr_schily } },
{ "LIBARCHIVE.xattr", 0, PAX_TYPE_PREFIXED_XATTR,
{ .xattr = pax_xattr_libarchive } },
+ { "GNU.sparse.map", 0, PAX_TYPE_CONST_STRING,
+ { .cstr = pax_sparse_map } },
};
static const struct pax_handler_t *find_handler(const char *key)
@@ -183,6 +335,8 @@ static int apply_handler(tar_header_decoded_t *out,
if (pax_read_decimal(value, &uval))
return -1;
return field->cb.uint(out, uval);
+ case PAX_TYPE_CONST_STRING:
+ return field->cb.cstr(out, value);
case PAX_TYPE_STRING:
copy = strdup(value);
if (copy == NULL) {
@@ -264,13 +418,6 @@ int read_pax_header(istream_t *fp, sqfs_u64 entsize, unsigned int *set_by_pax,
}
*set_by_pax |= field->flag;
- } else if (!strcmp(key, "GNU.sparse.map")) {
- free_sparse_list(out->sparse);
- sparse_last = NULL;
-
- out->sparse = read_sparse_map(value);
- if (out->sparse == NULL)
- goto fail;
} else if (!strcmp(key, "GNU.sparse.offset")) {
if (pax_read_decimal(value, &offset))
goto fail;
diff --git a/lib/tar/read_header.c b/lib/tar/read_header.c
index d1790de..ea4873b 100644
--- a/lib/tar/read_header.c
+++ b/lib/tar/read_header.c
@@ -7,6 +7,8 @@
#include "config.h"
#include "internal.h"
+#include <string.h>
+#include <stdlib.h>
static bool is_zero_block(const tar_header_t *hdr)
{
diff --git a/lib/tar/read_sparse_map.c b/lib/tar/read_sparse_map.c
deleted file mode 100644
index 0779b96..0000000
--- a/lib/tar/read_sparse_map.c
+++ /dev/null
@@ -1,54 +0,0 @@
-/* SPDX-License-Identifier: GPL-3.0-or-later */
-/*
- * read_sparse_map.c
- *
- * Copyright (C) 2019 David Oberhollenzer <goliath@infraroot.at>
- */
-#include "config.h"
-
-#include "internal.h"
-
-sparse_map_t *read_sparse_map(const char *line)
-{
- sparse_map_t *last = NULL, *list = NULL, *ent = NULL;
-
- do {
- ent = calloc(1, sizeof(*ent));
- if (ent == NULL)
- goto fail_errno;
-
- if (pax_read_decimal(line, &ent->offset))
- goto fail_format;
-
- while (isdigit(*line))
- ++line;
-
- if (*(line++) != ',')
- goto fail_format;
-
- if (pax_read_decimal(line, &ent->count))
- goto fail_format;
-
- while (isdigit(*line))
- ++line;
-
- if (last == NULL) {
- list = last = ent;
- } else {
- last->next = ent;
- last = ent;
- }
- } while (*(line++) == ',');
-
- return list;
-fail_errno:
- perror("parsing GNU pax sparse file record");
- goto fail;
-fail_format:
- fputs("malformed GNU pax sparse file record\n", stderr);
- goto fail;
-fail:
- free_sparse_list(list);
- free(ent);
- return NULL;
-}
diff --git a/lib/tar/read_sparse_map_new.c b/lib/tar/read_sparse_map_new.c
index d9f6c6e..de1b6a4 100644
--- a/lib/tar/read_sparse_map_new.c
+++ b/lib/tar/read_sparse_map_new.c
@@ -5,9 +5,12 @@
* Copyright (C) 2019 David Oberhollenzer <goliath@infraroot.at>
*/
#include "config.h"
-
#include "internal.h"
+#include <ctype.h>
+#include <string.h>
+#include <stdlib.h>
+
static int decode(const char *str, size_t len, size_t *out)
{
size_t count = 0;
diff --git a/lib/tar/read_sparse_map_old.c b/lib/tar/read_sparse_map_old.c
index cd7177d..3dd3300 100644
--- a/lib/tar/read_sparse_map_old.c
+++ b/lib/tar/read_sparse_map_old.c
@@ -5,9 +5,11 @@
* Copyright (C) 2019 David Oberhollenzer <goliath@infraroot.at>
*/
#include "config.h"
-
#include "internal.h"
+#include <ctype.h>
+#include <stdlib.h>
+
sparse_map_t *read_gnu_old_sparse(istream_t *fp, tar_header_t *hdr)
{
sparse_map_t *list = NULL, *end = NULL, *node;
diff --git a/lib/tar/record_to_memory.c b/lib/tar/record_to_memory.c
index 822608c..ba422de 100644
--- a/lib/tar/record_to_memory.c
+++ b/lib/tar/record_to_memory.c
@@ -6,8 +6,9 @@
*/
#include "config.h"
-#include "tar.h"
+#include "tar/tar.h"
#include "internal.h"
+#include <stdlib.h>
char *record_to_memory(istream_t *fp, size_t size)
{
diff --git a/lib/tar/urldecode.c b/lib/tar/urldecode.c
deleted file mode 100644
index 6fac4d3..0000000
--- a/lib/tar/urldecode.c
+++ /dev/null
@@ -1,38 +0,0 @@
-/* SPDX-License-Identifier: GPL-3.0-or-later */
-/*
- * urldecode.c
- *
- * Copyright (C) 2019 David Oberhollenzer <goliath@infraroot.at>
- */
-#include "config.h"
-
-#include "internal.h"
-
-static int xdigit(int x)
-{
- if (isupper(x))
- return x - 'A' + 0x0A;
- if (islower(x))
- return x - 'a' + 0x0A;
- return x - '0';
-}
-
-void urldecode(char *str)
-{
- unsigned char *out = (unsigned char *)str;
- char *in = str;
- int x;
-
- while (*in != '\0') {
- x = *(in++);
-
- if (x == '%' && isxdigit(in[0]) && isxdigit(in[1])) {
- x = xdigit(*(in++)) << 4;
- x |= xdigit(*(in++));
- }
-
- *(out++) = x;
- }
-
- *out = '\0';
-}
diff --git a/lib/tar/write_header.c b/lib/tar/write_header.c
index a337b74..b0711b3 100644
--- a/lib/tar/write_header.c
+++ b/lib/tar/write_header.c
@@ -7,6 +7,7 @@
#include "config.h"
#include "internal.h"
+#include <string.h>
static void write_binary(char *dst, sqfs_u64 value, int digits)
{
diff --git a/tests/libtar/tar_big_file.c b/tests/libtar/tar_big_file.c
index 6e5af50..47332b7 100644
--- a/tests/libtar/tar_big_file.c
+++ b/tests/libtar/tar_big_file.c
@@ -5,7 +5,7 @@
* Copyright (C) 2019 David Oberhollenzer <goliath@infraroot.at>
*/
#include "config.h"
-#include "tar.h"
+#include "tar/tar.h"
#include "io/file.h"
#include "../test.h"
diff --git a/tests/libtar/tar_fuzz.c b/tests/libtar/tar_fuzz.c
index e7ab2b4..5942426 100644
--- a/tests/libtar/tar_fuzz.c
+++ b/tests/libtar/tar_fuzz.c
@@ -7,7 +7,7 @@
#include "config.h"
#include "io/file.h"
-#include "tar.h"
+#include "tar/tar.h"
#include <stdlib.h>
#include <stdio.h>
diff --git a/tests/libtar/tar_simple.c b/tests/libtar/tar_simple.c
index 4fc1b8b..d72044a 100644
--- a/tests/libtar/tar_simple.c
+++ b/tests/libtar/tar_simple.c
@@ -6,7 +6,7 @@
*/
#include "config.h"
#include "io/file.h"
-#include "tar.h"
+#include "tar/tar.h"
#include "../test.h"
#ifndef TESTUID
diff --git a/tests/libtar/tar_sparse.c b/tests/libtar/tar_sparse.c
index d868c80..305e5e7 100644
--- a/tests/libtar/tar_sparse.c
+++ b/tests/libtar/tar_sparse.c
@@ -6,7 +6,7 @@
*/
#include "config.h"
#include "io/file.h"
-#include "tar.h"
+#include "tar/tar.h"
#include "../test.h"
static void test_case_sparse(const char *path)
diff --git a/tests/libtar/tar_sparse_gnu.c b/tests/libtar/tar_sparse_gnu.c
index c55f175..2ce7975 100644
--- a/tests/libtar/tar_sparse_gnu.c
+++ b/tests/libtar/tar_sparse_gnu.c
@@ -6,7 +6,7 @@
*/
#include "config.h"
#include "io/file.h"
-#include "tar.h"
+#include "tar/tar.h"
#include "../test.h"
int main(int argc, char **argv)
diff --git a/tests/libtar/tar_target_filled.c b/tests/libtar/tar_target_filled.c
index 34bf20f..13b089f 100644
--- a/tests/libtar/tar_target_filled.c
+++ b/tests/libtar/tar_target_filled.c
@@ -6,7 +6,7 @@
*/
#include "config.h"
#include "io/file.h"
-#include "tar.h"
+#include "tar/tar.h"
#include "../test.h"
int main(int argc, char **argv)
diff --git a/tests/libtar/tar_xattr.c b/tests/libtar/tar_xattr.c
index 7dde243..5fc7064 100644
--- a/tests/libtar/tar_xattr.c
+++ b/tests/libtar/tar_xattr.c
@@ -6,7 +6,7 @@
*/
#include "config.h"
#include "io/file.h"
-#include "tar.h"
+#include "tar/tar.h"
#include "../test.h"
int main(int argc, char **argv)
diff --git a/tests/libtar/tar_xattr_bin.c b/tests/libtar/tar_xattr_bin.c
index ea2bc28..8679c2d 100644
--- a/tests/libtar/tar_xattr_bin.c
+++ b/tests/libtar/tar_xattr_bin.c
@@ -6,7 +6,7 @@
*/
#include "config.h"
#include "io/file.h"
-#include "tar.h"
+#include "tar/tar.h"
#include "../test.h"
static const uint8_t value[] = {