aboutsummaryrefslogtreecommitdiff
path: root/bin/rdsquashfs/rdsquashfs.c
diff options
context:
space:
mode:
authorDavid Oberhollenzer <david.oberhollenzer@sigma-star.at>2023-01-31 11:21:30 +0100
committerDavid Oberhollenzer <david.oberhollenzer@sigma-star.at>2023-01-31 13:51:49 +0100
commitcdccc69c62579b0c13b35fad0728079652b8f3c9 (patch)
tree9fa54c710f73c5e08a9c8466e7a712eb63ee07ac /bin/rdsquashfs/rdsquashfs.c
parent2182129c8f359c4fa1390eaba7a65b595ccd4182 (diff)
Move library source into src sub-directory
Signed-off-by: David Oberhollenzer <david.oberhollenzer@sigma-star.at>
Diffstat (limited to 'bin/rdsquashfs/rdsquashfs.c')
-rw-r--r--bin/rdsquashfs/rdsquashfs.c275
1 files changed, 0 insertions, 275 deletions
diff --git a/bin/rdsquashfs/rdsquashfs.c b/bin/rdsquashfs/rdsquashfs.c
deleted file mode 100644
index bdcc5a0..0000000
--- a/bin/rdsquashfs/rdsquashfs.c
+++ /dev/null
@@ -1,275 +0,0 @@
-/* SPDX-License-Identifier: GPL-3.0-or-later */
-/*
- * rdsquashfs.c
- *
- * Copyright (C) 2019 David Oberhollenzer <goliath@infraroot.at>
- */
-#include "rdsquashfs.h"
-
-static sqfs_tree_node_t *list_merge(sqfs_tree_node_t *lhs,
- sqfs_tree_node_t *rhs)
-{
- sqfs_tree_node_t *it, *head = NULL, **next_ptr = &head;
-
- while (lhs != NULL && rhs != NULL) {
- if (strcmp((const char *)lhs->name,
- (const char *)rhs->name) <= 0) {
- it = lhs;
- lhs = lhs->next;
- } else {
- it = rhs;
- rhs = rhs->next;
- }
-
- *next_ptr = it;
- next_ptr = &it->next;
- }
-
- it = (lhs != NULL ? lhs : rhs);
- *next_ptr = it;
- return head;
-}
-
-static sqfs_tree_node_t *list_sort(sqfs_tree_node_t *head)
-{
- sqfs_tree_node_t *it, *half, *prev;
-
- it = half = prev = head;
-
- while (it != NULL) {
- prev = half;
- half = half->next;
- it = it->next;
-
- if (it != NULL)
- it = it->next;
- }
-
- if (half == NULL)
- return head;
-
- prev->next = NULL;
-
- return list_merge(list_sort(head), list_sort(half));
-}
-
-static int tree_sort(sqfs_tree_node_t *root)
-{
- sqfs_tree_node_t *it;
-
- if (root->children == NULL)
- return 0;
-
- root->children = list_sort(root->children);
-
- /*
- XXX: not only an inconvenience but a security issue: e.g. we unpack a
- SquashFS image that has a symlink pointing somewhere, and then a
- sub-directory or file with the same name, the unpacker can be tricked
- to follow the symlink and write anything, anywhere on the filesystem.
- */
- for (it = root->children; it->next != NULL; it = it->next) {
- if (strcmp((const char *)it->name,
- (const char *)it->next->name) == 0) {
- char *path;
- int ret;
-
- ret = sqfs_tree_node_get_path(it, &path);
-
- if (ret == 0) {
- fprintf(stderr,
- "Entry '%s' found more than once!\n",
- path);
- } else {
- fputs("Entry found more than once!\n", stderr);
- }
-
- sqfs_free(path);
- return -1;
- }
- }
-
- for (it = root->children; it != NULL; it = it->next) {
- if (tree_sort(it))
- return -1;
- }
-
- return 0;
-}
-
-int main(int argc, char **argv)
-{
- sqfs_xattr_reader_t *xattr = NULL;
- sqfs_data_reader_t *data = NULL;
- sqfs_dir_reader_t *dirrd = NULL;
- sqfs_compressor_t *cmp = NULL;
- sqfs_id_table_t *idtbl = NULL;
- sqfs_compressor_config_t cfg;
- sqfs_tree_node_t *n = NULL;
- int status = EXIT_FAILURE;
- sqfs_file_t *file = NULL;
- sqfs_super_t super;
- options_t opt;
- int ret;
-
- process_command_line(&opt, argc, argv);
-
- file = sqfs_open_file(opt.image_name, SQFS_FILE_OPEN_READ_ONLY);
- if (file == NULL) {
- perror(opt.image_name);
- goto out;
- }
-
- ret = sqfs_super_read(&super, file);
- if (ret) {
- sqfs_perror(opt.image_name, "reading super block", ret);
- goto out;
- }
-
- sqfs_compressor_config_init(&cfg, super.compression_id,
- super.block_size,
- SQFS_COMP_FLAG_UNCOMPRESS);
-
- ret = sqfs_compressor_create(&cfg, &cmp);
-
-#ifdef WITH_LZO
- if (super.compression_id == SQFS_COMP_LZO && ret != 0)
- ret = lzo_compressor_create(&cfg, &cmp);
-#endif
-
- if (ret != 0) {
- sqfs_perror(opt.image_name, "creating compressor", ret);
- goto out;
- }
-
- if (!(super.flags & SQFS_FLAG_NO_XATTRS)) {
- xattr = sqfs_xattr_reader_create(0);
- if (xattr == NULL) {
- sqfs_perror(opt.image_name, "creating xattr reader",
- SQFS_ERROR_ALLOC);
- goto out;
- }
-
- ret = sqfs_xattr_reader_load(xattr, &super, file, cmp);
- if (ret) {
- sqfs_perror(opt.image_name, "loading xattr table",
- ret);
- goto out;
- }
- }
-
- idtbl = sqfs_id_table_create(0);
- if (idtbl == NULL) {
- sqfs_perror(opt.image_name, "creating ID table",
- SQFS_ERROR_ALLOC);
- goto out;
- }
-
- ret = sqfs_id_table_read(idtbl, file, &super, cmp);
- if (ret) {
- sqfs_perror(opt.image_name, "loading ID table", ret);
- goto out;
- }
-
- dirrd = sqfs_dir_reader_create(&super, cmp, file, 0);
- if (dirrd == NULL) {
- sqfs_perror(opt.image_name, "creating dir reader",
- SQFS_ERROR_ALLOC);
- goto out;
- }
-
- data = sqfs_data_reader_create(file, super.block_size, cmp, 0);
- if (data == NULL) {
- sqfs_perror(opt.image_name, "creating data reader",
- SQFS_ERROR_ALLOC);
- goto out;
- }
-
- ret = sqfs_data_reader_load_fragment_table(data, &super);
- if (ret) {
- sqfs_perror(opt.image_name, "loading fragment table", ret);
- goto out;
- }
-
- ret = sqfs_dir_reader_get_full_hierarchy(dirrd, idtbl, opt.cmdpath,
- opt.rdtree_flags, &n);
- if (ret) {
- sqfs_perror(opt.image_name, "reading filesystem tree", ret);
- goto out;
- }
-
- switch (opt.op) {
- case OP_LS:
- list_files(n);
- break;
- case OP_STAT:
- if (stat_file(n))
- goto out;
- break;
- case OP_CAT: {
- ostream_t *fp;
-
- if (!S_ISREG(n->inode->base.mode)) {
- fprintf(stderr, "/%s: not a regular file\n",
- opt.cmdpath);
- goto out;
- }
-
- fp = ostream_open_stdout();
- if (fp == NULL)
- goto out;
-
- ret = sqfs_data_reader_dump(opt.cmdpath, data, n->inode,
- fp, super.block_size);
- sqfs_drop(fp);
- if (ret)
- goto out;
- break;
- }
- case OP_UNPACK:
- if (tree_sort(n))
- goto out;
-
- if (opt.unpack_root != NULL) {
- if (mkdir_p(opt.unpack_root))
- goto out;
-
- if (chdir(opt.unpack_root)) {
- perror(opt.unpack_root);
- goto out;
- }
- }
-
- if (restore_fstree(n, opt.flags))
- goto out;
-
- if (fill_unpacked_files(super.block_size, n, data, opt.flags))
- goto out;
-
- if (update_tree_attribs(xattr, n, opt.flags))
- goto out;
- break;
- case OP_DESCRIBE:
- if (describe_tree(n, opt.unpack_root))
- goto out;
- break;
- case OP_RDATTR:
- if (dump_xattrs(xattr, n->inode))
- goto out;
- break;
- default:
- break;
- }
-
- status = EXIT_SUCCESS;
-out:
- sqfs_dir_tree_destroy(n);
- sqfs_drop(data);
- sqfs_drop(dirrd);
- sqfs_drop(idtbl);
- sqfs_drop(xattr);
- sqfs_drop(cmp);
- sqfs_drop(file);
- free(opt.cmdpath);
- return status;
-}