wok rev 888

busybox/cpio: do not link syslinks
author Pascal Bellard <pascal.bellard@slitaz.org>
date Mon Jun 09 08:17:02 2008 +0000 (2008-06-09)
parents ca68c3fca6c9
children dad0d2002ac1
files busybox/stuff/busybox-1.10.3-cpio.u
line diff
     1.1 --- a/busybox/stuff/busybox-1.10.3-cpio.u	Sun Jun 08 23:22:25 2008 +0200
     1.2 +++ b/busybox/stuff/busybox-1.10.3-cpio.u	Mon Jun 09 08:17:02 2008 +0000
     1.3 @@ -1,1 +1,220 @@
     1.4 -busybox-1.10.1-cpio.u
     1.5 \ No newline at end of file
     1.6 +diff -purN busybox-1.10.0/archival/Config.in busybox/archival/Config.in
     1.7 +--- busybox-1.10.0/archival/Config.in	2008-03-29 21:47:37.000000000 +0100
     1.8 ++++ busybox-1.10.0/archival/Config.in	2008-03-29 21:47:37.000000000 +0100
     1.9 +@@ -78,6 +78,14 @@ config CPIO
    1.10 + 	  Unless you have a specific application which requires cpio, you should
    1.11 + 	  probably say N here.
    1.12 + 
    1.13 ++config FEATURE_CPIO_O
    1.14 ++	bool "Support for archive creation"
    1.15 ++	default n
    1.16 ++	depends on CPIO
    1.17 ++	help
    1.18 ++	  This implementation of cpio can create cpio archives in the "newc"
    1.19 ++	  format only.
    1.20 ++
    1.21 + config DPKG
    1.22 + 	bool "dpkg"
    1.23 + 	default n
    1.24 +diff -purN busybox-1.10.0/archival/cpio.c busybox/archival/cpio.c
    1.25 +--- busybox-1.10.0/archival/cpio.c	2008-03-29 21:47:55.000000000 +0100
    1.26 ++++ busybox-1.10.0/archival/cpio.c	2008-03-29 21:47:55.000000000 +0100
    1.27 +@@ -21,12 +21,146 @@
    1.28 + #define CPIO_OPT_FILE                   0x10
    1.29 + #define CPIO_OPT_CREATE_LEADING_DIR     0x20
    1.30 + #define CPIO_OPT_PRESERVE_MTIME         0x40
    1.31 ++#define CPIO_OPT_CREATE                 0x80
    1.32 ++#define CPIO_OPT_FORMAT                0x100
    1.33 ++
    1.34 ++#if ENABLE_FEATURE_CPIO_O
    1.35 ++static void cpio_pad(off_t *size, int n)
    1.36 ++{
    1.37 ++    int i;
    1.38 ++    for (*size += i = (-*size) & n; --i >= 0; bb_putchar(0));
    1.39 ++}
    1.40 ++
    1.41 ++static void cpio_o(void)
    1.42 ++{
    1.43 ++    struct name_s {
    1.44 ++        struct name_s *next;
    1.45 ++        char name[0];
    1.46 ++    };
    1.47 ++    struct inodes_s {
    1.48 ++        struct name_s *names;
    1.49 ++        struct inodes_s *next;
    1.50 ++        struct stat st;
    1.51 ++    } *links = NULL;
    1.52 ++    off_t bytes = 0; // output bytes count
    1.53 ++#if CONFIG_FEATURE_COPYBUF_KB < 1
    1.54 ++    char buf[1024];
    1.55 ++#else
    1.56 ++    char buf[CONFIG_FEATURE_COPYBUF_KB * 1024];
    1.57 ++#endif
    1.58 ++	
    1.59 ++    while (1) {
    1.60 ++        const char *name = "TRAILER!!!";
    1.61 ++        char *line = xmalloc_getline(stdin);
    1.62 ++        // allocate inode struct each loop to avoid struct stat copy
    1.63 ++        struct inodes_s *inode = xzalloc(sizeof(*inode)); // die if fail
    1.64 ++        off_t size;
    1.65 ++
    1.66 ++        inode->st.st_nlink++; // =1
    1.67 ++        if (line) {
    1.68 ++            /* Strip leading `./' from the filename.  */
    1.69 ++            for (name = line; name[0] == '.' && name[1] == '/';) {
    1.70 ++                while (*++name == '/');
    1.71 ++            }
    1.72 ++            if (!*name) goto free_and_continue; // line empty
    1.73 ++            if (lstat(name, &inode->st)) {
    1.74 ++          abort_cpio_o:
    1.75 ++                bb_perror_msg_and_die(name);
    1.76 ++            }
    1.77 ++            if (!S_ISLNK(inode->st.st_mode) && !S_ISREG(inode->st.st_mode))
    1.78 ++                inode->st.st_size = 0;
    1.79 ++        }
    1.80 ++        // hard links will are stored and will be processed later
    1.81 ++        if (!S_ISDIR(inode->st.st_mode) && !S_ISLNK(inode->st.st_mode) && inode->st.st_nlink > 1) {
    1.82 ++            struct name_s *n;
    1.83 ++            struct inodes_s *l;
    1.84 ++
    1.85 ++            for (l = links; l && l->st.st_ino != inode->st.st_ino; l = l->next);
    1.86 ++            if (l == NULL) { // not found: new hard links set
    1.87 ++                l = inode; // l->names = NULL; l->st = inode->st
    1.88 ++                l->next = links;
    1.89 ++                links = l;
    1.90 ++            }
    1.91 ++            n = xmalloc(sizeof(*n) + strlen(name) + 1); // die if fail
    1.92 ++            strcpy(n->name, name);
    1.93 ++            n->next = l->names;
    1.94 ++            l->names = n; // will not free inode if l == inode
    1.95 ++            goto free_and_continue;
    1.96 ++        }
    1.97 ++        size = inode->st.st_size;
    1.98 ++        // no more files ? process hard links
    1.99 ++        if (!line && links) {
   1.100 ++            struct name_s *n;
   1.101 ++
   1.102 ++            free(inode); // trailer pseudo inode
   1.103 ++            inode = links;
   1.104 ++            n = links->names;
   1.105 ++            name = line = xstrdup(n->name);    // line will free *name memory
   1.106 ++            links->names = n->next;
   1.107 ++            if (links->names == NULL) {        // inode will free *links memory
   1.108 ++                size = links->st.st_size;
   1.109 ++                links = links->next;
   1.110 ++            }
   1.111 ++            free(n);
   1.112 ++        }
   1.113 ++        bytes += printf("070701%08lx%08lx%08lx%08lx%08lx%08lx%08lx"
   1.114 ++                        "%08lx%08lx%08lx%08lx%08lx%08lx%s%c",
   1.115 ++                        (unsigned long) inode->st.st_ino,
   1.116 ++                        (unsigned long) inode->st.st_mode, 
   1.117 ++                        (unsigned long) inode->st.st_uid,
   1.118 ++                        (unsigned long) inode->st.st_gid,
   1.119 ++                        (unsigned long) inode->st.st_nlink,
   1.120 ++                        (unsigned long) inode->st.st_mtime,
   1.121 ++                        (unsigned long) size,
   1.122 ++                        (unsigned long) major(inode->st.st_dev),
   1.123 ++                        (unsigned long) minor(inode->st.st_dev),
   1.124 ++                        (unsigned long) major(inode->st.st_rdev), 
   1.125 ++                        (unsigned long) minor(inode->st.st_rdev),
   1.126 ++                        strlen(name) + 1UL, 0UL, name, 0);
   1.127 ++        cpio_pad(&bytes, (line) ? 4-1 : 512-1);
   1.128 ++        if (size) {
   1.129 ++            if (S_ISLNK(inode->st.st_mode)) {
   1.130 ++                char *lpath = xmalloc_readlink_or_warn(name);
   1.131 ++
   1.132 ++                if (!lpath) goto abort_cpio_o;
   1.133 ++                bytes += printf("%s", lpath);
   1.134 ++                free(lpath);
   1.135 ++            }
   1.136 ++            if (S_ISREG(inode->st.st_mode)) {
   1.137 ++                int fd = open_or_warn(name, O_RDONLY);
   1.138 ++
   1.139 ++                while (1) {
   1.140 ++                    int len = full_read(fd, buf, sizeof(buf));
   1.141 ++                    if (len < 0) goto abort_cpio_o;
   1.142 ++                    if (len == 0) break;
   1.143 ++                    bytes += len;
   1.144 ++                    fwrite(buf, 1, len, stdout);
   1.145 ++                }
   1.146 ++                close(fd);
   1.147 ++            }
   1.148 ++            cpio_pad(&bytes, 4-1);
   1.149 ++        }
   1.150 ++
   1.151 ++        if (!line) {
   1.152 ++            fputc('\n', stderr); // GNU cpio do that...
   1.153 ++            return; // was trailer
   1.154 ++        }
   1.155 ++
   1.156 ++    free_and_continue:
   1.157 ++        if (!inode->names) free(inode);
   1.158 ++            free(line);
   1.159 ++    }
   1.160 ++}
   1.161 ++#endif
   1.162 + 
   1.163 + int cpio_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE;
   1.164 + int cpio_main(int argc, char **argv)
   1.165 + {
   1.166 + 	archive_handle_t *archive_handle;
   1.167 + 	char *cpio_filename = NULL;
   1.168 ++#if ENABLE_FEATURE_CPIO_O
   1.169 ++	const char *cpio_fmt = "";
   1.170 ++#endif
   1.171 + 	unsigned opt;
   1.172 + 
   1.173 + 	/* Initialise */
   1.174 +@@ -35,10 +169,26 @@ int cpio_main(int argc, char **argv)
   1.175 + 	archive_handle->seek = seek_by_read;
   1.176 + 	archive_handle->flags = ARCHIVE_EXTRACT_NEWER | ARCHIVE_PRESERVE_DATE;
   1.177 + 
   1.178 ++#if ENABLE_FEATURE_CPIO_O
   1.179 ++	opt = getopt32(argv, "ituvF:dmoH:", &cpio_filename,&cpio_fmt);
   1.180 ++
   1.181 ++	if (opt & CPIO_OPT_CREATE) {
   1.182 ++		if (*cpio_fmt != 'n')
   1.183 ++			goto cpio_show_usage;
   1.184 ++		if (cpio_filename) {
   1.185 ++			fclose(stdout);
   1.186 ++			stdout = fopen(cpio_filename,"w");
   1.187 ++		}
   1.188 ++		cpio_o();
   1.189 ++		return EXIT_SUCCESS;
   1.190 ++	}
   1.191 ++#else
   1.192 + 	opt = getopt32(argv, "ituvF:dm", &cpio_filename);
   1.193 ++#endif
   1.194 + 
   1.195 + 	/* One of either extract or test options must be given */
   1.196 + 	if ((opt & (CPIO_OPT_TEST | CPIO_OPT_EXTRACT)) == 0) {
   1.197 ++ cpio_show_usage:
   1.198 + 		bb_show_usage();
   1.199 + 	}
   1.200 + 
   1.201 +diff -purN busybox-1.10.0/include/usage.h busybox/include/usage.h
   1.202 +--- busybox-1.10.0/include/usage.h	2008-03-29 21:48:22.000000000 +0100
   1.203 ++++ busybox-1.10.0/include/usage.h	2008-03-29 21:48:22.000000000 +0100
   1.204 +@@ -496,13 +496,19 @@
   1.205 +      "\n	-l,-s	Create (sym)links" \
   1.206 + 
   1.207 + #define cpio_trivial_usage \
   1.208 +-       "-[dimtuv][F cpiofile]"
   1.209 ++       "-[dim" USE_FEATURE_CPIO_O("o") "tuv][F cpiofile]" \
   1.210 ++       USE_FEATURE_CPIO_O( "[H newc]" ) 
   1.211 + #define cpio_full_usage \
   1.212 +-       "Extract or list files from a cpio archive\n" \
   1.213 ++       "Extract or list files from a cpio archive" \
   1.214 ++       USE_FEATURE_CPIO_O( ", or create a cpio archive" ) "\n" \
   1.215 +        "Main operation mode:" \
   1.216 +      "\n	d	Make leading directories" \
   1.217 +      "\n	i	Extract" \
   1.218 +      "\n	m	Preserve mtime" \
   1.219 ++       USE_FEATURE_CPIO_O( \
   1.220 ++     "\n	o	Create" \
   1.221 ++     "\n	H newc	Define format" \
   1.222 ++       ) \
   1.223 +      "\n	t	List" \
   1.224 +      "\n	v	Verbose" \
   1.225 +      "\n	u	Unconditional overwrite" \