1) Remove isys cpio code and use libarchive in loader. 2) Add in some libarchive helper functions to loader/unpack.c. 3) Make use of the libarchive helper functions in rpmextract.c. 4) Remove mkdirChain() and related functions in favor of g_mkdir_with_parents() in glib. 5) Removal of various other unused related bits of code.
I'll test these at some point in the future (probably this coming weekend), but just wanted to toss them out now for people to look over.
The only place this code is still used is in loader. Loader is now using libarchive to unpack cpio streams and zlib to uncompress them, so we do not need these functions anymore. --- pyanaconda/isys/Makefile.am | 2 +- pyanaconda/isys/cpio.c | 46 --- pyanaconda/isys/cpio.h | 102 ------ pyanaconda/isys/lang.c | 4 +- pyanaconda/isys/lang.h | 2 +- pyanaconda/isys/stubs.h | 44 --- pyanaconda/isys/uncpio.c | 797 ------------------------------------------- 7 files changed, 4 insertions(+), 993 deletions(-) delete mode 100644 pyanaconda/isys/cpio.c delete mode 100644 pyanaconda/isys/cpio.h delete mode 100644 pyanaconda/isys/stubs.h delete mode 100644 pyanaconda/isys/uncpio.c
diff --git a/pyanaconda/isys/Makefile.am b/pyanaconda/isys/Makefile.am index 2b3130c..3d521d7 100644 --- a/pyanaconda/isys/Makefile.am +++ b/pyanaconda/isys/Makefile.am @@ -19,7 +19,7 @@
pkgpyexecdir = $(pyexecdir)/py$(PACKAGE_NAME)
-ISYS_SRCS = devices.c imount.c cpio.c uncpio.c lang.c \ +ISYS_SRCS = devices.c imount.c lang.c \ isofs.c linkdetect.c vio.c ethtool.c eddsupport.c iface.c \ auditd.c log.c mem.c
diff --git a/pyanaconda/isys/cpio.c b/pyanaconda/isys/cpio.c deleted file mode 100644 index fd83605..0000000 --- a/pyanaconda/isys/cpio.c +++ /dev/null @@ -1,46 +0,0 @@ -/* - * cpio.c - * - * Copyright (C) 2007 Red Hat, Inc. All rights reserved. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see http://www.gnu.org/licenses/. - */ - -#include <fcntl.h> -#include <stdio.h> -#include <stdlib.h> -#include <unistd.h> - -#include "cpio.h" - -int installCpioFile(gzFile fd, char * cpioName, char * outName, int inWin) { - struct cpioFileMapping map; - int rc; - const char * failedFile; - - if (outName) { - map.archivePath = cpioName; - map.fsPath = outName; - map.mapFlags = CPIO_MAP_PATH; - } - - rc = myCpioInstallArchive(fd, outName ? &map : NULL, 1, NULL, NULL, - &failedFile); - - if (rc || access(outName, R_OK)) { - return -1; - } - - return 0; -} diff --git a/pyanaconda/isys/cpio.h b/pyanaconda/isys/cpio.h deleted file mode 100644 index 4cbb7c0..0000000 --- a/pyanaconda/isys/cpio.h +++ /dev/null @@ -1,102 +0,0 @@ -/* - * cpio.h - * - * Copyright (C) 2007 Red Hat, Inc. All rights reserved. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see http://www.gnu.org/licenses/. - */ - -#ifndef H_CPIO -#define H_CPIO - -#include <sys/types.h> - -#include "stubs.h" - -/* Note the CPIO_CHECK_ERRNO bit is set only if errno is valid. These have to - be positive numbers or this setting the high bit stuff is a bad idea. */ -#define CPIOERR_CHECK_ERRNO 0x80000000 - -#define CPIOERR_BAD_MAGIC (2 ) -#define CPIOERR_BAD_HEADER (3 ) -#define CPIOERR_OPEN_FAILED (4 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_CHMOD_FAILED (5 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_CHOWN_FAILED (6 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_WRITE_FAILED (7 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_UTIME_FAILED (8 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_UNLINK_FAILED (9 | CPIOERR_CHECK_ERRNO) - -#define CPIOERR_SYMLINK_FAILED (11 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_STAT_FAILED (12 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_MKDIR_FAILED (13 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_MKNOD_FAILED (14 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_MKFIFO_FAILED (15 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_LINK_FAILED (16 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_READLINK_FAILED (17 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_READ_FAILED (18 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_COPY_FAILED (19 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_INTERNAL (20 ) -#define CPIOERR_HDR_SIZE (21 ) -#define CPIOERR_UNKNOWN_FILETYPE (22 ) - - -/* Don't think this behaves just like standard cpio. It's pretty close, but - it has some behaviors which are more to RPM's liking. I tried to document - them inline in cpio.c, but I may have missed some. */ - -#define CPIO_MAP_PATH (1 << 0) -#define CPIO_MAP_MODE (1 << 1) -#define CPIO_MAP_UID (1 << 2) -#define CPIO_MAP_GID (1 << 3) -#define CPIO_FOLLOW_SYMLINKS (1 << 4) /* only for building */ - -struct cpioFileMapping { - char * archivePath; - char * fsPath; - mode_t finalMode; - uid_t finalUid; - gid_t finalGid; - int mapFlags; -}; - -/* on cpio building, only "file" is filled in */ -struct cpioCallbackInfo { - char * file; - long fileSize; /* total file size */ - long fileComplete; /* amount of file unpacked */ - long bytesProcessed; /* bytes in archive read */ -}; - -typedef void (*cpioCallback)(struct cpioCallbackInfo * filespec, void * data); - -/* If no mappings are passed, this installs everything! If one is passed - it should be sorted according to cpioFileMapCmp() and only files included - in the map are installed. Files are installed relative to the current - directory unless a mapping is given which specifies an absolute - directory. The mode mapping is only used for the permission bits, not - for the file type. The owner/group mappings are ignored for the nonroot - user. If *failedFile is non-NULL on return, it should be free()d. */ -int myCpioInstallArchive(gzFile stream, struct cpioFileMapping * mappings, - int numMappings, cpioCallback cb, void * cbData, - const char ** failedFile); -int myCpioFilterArchive(gzFile inStream, gzFile outStream, char ** pattern); - -/* This is designed to be qsort/bsearch compatible */ -int myCpioFileMapCmp(const void * a, const void * b); - -const char *myCpioStrerror(int rc); - -int installCpioFile(gzFile fd, char * cpioName, char * outName, int inWin); - -#endif diff --git a/pyanaconda/isys/lang.c b/pyanaconda/isys/lang.c index b6e2a36..19b98ea 100644 --- a/pyanaconda/isys/lang.c +++ b/pyanaconda/isys/lang.c @@ -33,12 +33,12 @@ #define NR_KEYS 128 #endif
+#include <zlib.h> + #include "linux/kd.h"
-#include "cpio.h" #include "isys.h" #include "lang.h" -#include "stubs.h"
int isysLoadFont(void) { unsigned char font[65536]; diff --git a/pyanaconda/isys/lang.h b/pyanaconda/isys/lang.h index a08adbd..a83778a 100644 --- a/pyanaconda/isys/lang.h +++ b/pyanaconda/isys/lang.h @@ -20,7 +20,7 @@ #ifndef ISYS_LANG_H #define ISYS_LANG_H
-#include "stubs.h" +#include <zlib.h>
/* define ask johnsonm@redhat.com where this came from */ #define KMAP_MAGIC 0x8B39C07F diff --git a/pyanaconda/isys/stubs.h b/pyanaconda/isys/stubs.h deleted file mode 100644 index 40ecb22..0000000 --- a/pyanaconda/isys/stubs.h +++ /dev/null @@ -1,44 +0,0 @@ -/* - * stubs.h - * - * Copyright (C) 2007 Red Hat, Inc. All rights reserved. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see http://www.gnu.org/licenses/. - */ - -/* we use gzlib when linked against dietlibc, but otherwise, we should use - zlib. it would make more sense to do the defines in the other direction, - but that causes symbol wackiness because both gunzip_open and gzip_open in - gzlib are gzopen from zlib -*/ - -#ifndef ISYS_STUB -#define ISYS_STUB - -#ifndef GZLIB -#include <zlib.h> - -#define gunzip_open(x) gzopen(x, "r") -#define gunzip_dopen gzdopen(x, "r") -#define gunzip_close gzclose -#define gunzip_read gzread -#define gzip_write gzwrite -#define gzip_open(x, y, z) gzopen(x, "w") - -#else -#include "gzlib/gzlib.h" - -#endif - -#endif diff --git a/pyanaconda/isys/uncpio.c b/pyanaconda/isys/uncpio.c deleted file mode 100644 index 0481ff0..0000000 --- a/pyanaconda/isys/uncpio.c +++ /dev/null @@ -1,797 +0,0 @@ -/* - * uncpio.c - * - * Copyright (C) 2007 Red Hat, Inc. All rights reserved. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see http://www.gnu.org/licenses/. - */ - -#define HAVE_ALLOCA_H 1 -#define MAJOR_IN_SYSMACROS 1 - -#if HAVE_ALLOCA_H -# include <alloca.h> -#endif - -#define _(foo) (foo) - -#include <errno.h> -#include <fcntl.h> -#include <fnmatch.h> -#include <stdio.h> -#include <stdlib.h> -#include <string.h> -#include <sys/types.h> -#include <sys/stat.h> -#include <unistd.h> -#include <utime.h> - -#include "cpio.h" -#include "stubs.h" -#include "log.h" - -#if MAJOR_IN_SYSMACROS -#include <sys/sysmacros.h> -#elif MAJOR_IN_MKDEV -#include <sys/mkdev.h> -#endif - -#define CPIO_NEWC_MAGIC "070701" -#define CPIO_CRC_MAGIC "070702" -#define TRAILER "TRAILER!!!" - -/* FIXME: We don't translate between cpio and system mode bits! These - should both be the same, but really odd things are going to happen if - that's not true! */ - -/* We need to maintain our oun file pointer to allow padding */ -struct ourfd { - gzFile fd; - size_t pos; -}; - -struct hardLink { - struct hardLink * next; - char ** files; /* there are nlink of these, used by install */ - int * fileMaps; /* used by build */ - dev_t dev; - ino_t inode; - int nlink; - int linksLeft; - int createdPath; - struct stat sb; -}; - -struct cpioCrcPhysicalHeader { - char magic[6]; - char inode[8]; - char mode[8]; - char uid[8]; - char gid[8]; - char nlink[8]; - char mtime[8]; - char filesize[8]; - char devMajor[8]; - char devMinor[8]; - char rdevMajor[8]; - char rdevMinor[8]; - char namesize[8]; - char checksum[8]; /* ignored !! */ -}; - -#define PHYS_HDR_SIZE 110 /* don't depend on sizeof(struct) */ - -struct cpioHeader { - ino_t inode; - mode_t mode; - uid_t uid; - gid_t gid; - int nlink; - time_t mtime; - unsigned long size; - dev_t dev, rdev; - char * path; -}; - -static inline off_t ourread(struct ourfd * thefd, void * buf, size_t size) { - off_t i; - - i = gunzip_read(thefd->fd, buf, size); - thefd->pos += i; - - return i; -} - -static inline void padinfd(struct ourfd * fd, int modulo) { - int buf[10]; - int amount; - - amount = (modulo - fd->pos % modulo) % modulo; - ourread(fd, buf, amount); -} - -static inline int padoutfd(struct ourfd * fd, size_t * where, int modulo) { - /*static int buf[10] = { '\0', '\0', '\0', '\0', '\0', - '\0', '\0', '\0', '\0', '\0' };*/ - int amount; - static int buf[512]; - - amount = (modulo - *where % modulo) % modulo; - *where += amount; - - if (gzip_write(fd->fd, buf, amount) != amount) - return CPIOERR_WRITE_FAILED; - - return 0; -} - -static int strntoul(const char * str, char ** endptr, int base, int num) { - char * buf, * end; - unsigned long ret; - - buf = alloca(num + 1); - strncpy(buf, str, num); - buf[num] = '\0'; - - ret = strtoul(buf, &end, base); - if (*end) - *endptr = (char *)(str + (end - buf)); /* XXX discards const */ - else - *endptr = ""; - - return strtoul(buf, endptr, base); -} - -#define GET_NUM_FIELD(phys, log) \ - log = strntoul(phys, &end, 16, sizeof(phys)); \ - if (*end) return CPIOERR_BAD_HEADER; -#define SET_NUM_FIELD(phys, val, space) \ - sprintf(space, "%8.8lx", (unsigned long) (val)); \ - memcpy(phys, space, 8); - -static int getNextHeader(struct ourfd * fd, struct cpioHeader * chPtr, - struct cpioCrcPhysicalHeader * physHeaderPtr) { - struct cpioCrcPhysicalHeader physHeader; - int nameSize; - char * end; - int major, minor; - - if (ourread(fd, &physHeader, PHYS_HDR_SIZE) != PHYS_HDR_SIZE) - return CPIOERR_READ_FAILED; - - if (physHeaderPtr) - memcpy(physHeaderPtr, &physHeader, PHYS_HDR_SIZE); - - if (strncmp(CPIO_CRC_MAGIC, physHeader.magic, strlen(CPIO_CRC_MAGIC)) && - strncmp(CPIO_NEWC_MAGIC, physHeader.magic, strlen(CPIO_NEWC_MAGIC))) - return CPIOERR_BAD_MAGIC; - - GET_NUM_FIELD(physHeader.inode, chPtr->inode); - GET_NUM_FIELD(physHeader.mode, chPtr->mode); - GET_NUM_FIELD(physHeader.uid, chPtr->uid); - GET_NUM_FIELD(physHeader.gid, chPtr->gid); - GET_NUM_FIELD(physHeader.nlink, chPtr->nlink); - GET_NUM_FIELD(physHeader.mtime, chPtr->mtime); - GET_NUM_FIELD(physHeader.filesize, chPtr->size); - - GET_NUM_FIELD(physHeader.devMajor, major); - GET_NUM_FIELD(physHeader.devMinor, minor); - chPtr->dev = makedev(major, minor); - - GET_NUM_FIELD(physHeader.rdevMajor, major); - GET_NUM_FIELD(physHeader.rdevMinor, minor); - chPtr->rdev = makedev(major, minor); - - GET_NUM_FIELD(physHeader.namesize, nameSize); - - chPtr->path = malloc(nameSize + 1); - if (ourread(fd, chPtr->path, nameSize) != nameSize) { - free(chPtr->path); - return CPIOERR_BAD_HEADER; - } - - /* this is unecessary chPtr->path[nameSize] = '\0'; */ - - padinfd(fd, 4); - - return 0; -} - -int myCpioFileMapCmp(const void * a, const void * b) { - const struct cpioFileMapping * first = a; - const struct cpioFileMapping * second = b; - - return (strcmp(first->archivePath, second->archivePath)); -} - -/* This could trash files in the path! I'm not sure that's a good thing */ -static int createDirectory(char * path, mode_t perms) { - struct stat sb; - int dounlink; - - if (!lstat(path, &sb)) { - if (S_ISDIR(sb.st_mode)) { - return 0; - } else if (S_ISLNK(sb.st_mode)) { - if (stat(path, &sb)) { - if (errno != ENOENT) - return CPIOERR_STAT_FAILED; - dounlink = 1; - } else { - if (S_ISDIR(sb.st_mode)) - return 0; - dounlink = 1; - } - } else { - dounlink = 1; - } - - if (dounlink && unlink(path)) { - return CPIOERR_UNLINK_FAILED; - } - } - - if (mkdir(path, 000)) - return CPIOERR_MKDIR_FAILED; - - if (chmod(path, perms)) - return CPIOERR_CHMOD_FAILED; - - return 0; -} - -static int setInfo(struct cpioHeader * hdr) { - int rc = 0; - struct utimbuf stamp; - - stamp.actime = hdr->mtime; - stamp.modtime = hdr->mtime; - - if (!S_ISLNK(hdr->mode)) { - if (!getuid() && chown(hdr->path, hdr->uid, hdr->gid)) - rc = CPIOERR_CHOWN_FAILED; - if (!rc && chmod(hdr->path, hdr->mode & 07777)) - rc = CPIOERR_CHMOD_FAILED; - if (!rc && utime(hdr->path, &stamp)) - rc = CPIOERR_UTIME_FAILED; - } else { -# if ! CHOWN_FOLLOWS_SYMLINK - if (!getuid() && !rc && lchown(hdr->path, hdr->uid, hdr->gid)) - rc = CPIOERR_CHOWN_FAILED; -# endif - } - - return rc; -} - -static int checkDirectory(char * filename) { - static char * lastDir = NULL; - static int lastDirLength = 0; - static int lastDirAlloced = 0; - int length = strlen(filename); - char * buf; - char * chptr; - int rc = 0; - - buf = alloca(length + 1); - strcpy(buf, filename); - - for (chptr = buf + length - 1; chptr > buf; chptr--) { - if (*chptr == '/') break; - } - - if (chptr == buf) return 0; /* /filename - no directories */ - - *chptr = '\0'; /* buffer is now just directories */ - - length = strlen(buf); - if (lastDirLength == length && !strcmp(buf, lastDir)) return 0; - - if (lastDirAlloced < (length + 1)) { - lastDirAlloced = length + 100; - lastDir = realloc(lastDir, lastDirAlloced); - } - - strcpy(lastDir, buf); - lastDirLength = length; - - for (chptr = buf + 1; *chptr; chptr++) { - if (*chptr == '/') { - *chptr = '\0'; - rc = createDirectory(buf, 0755); - *chptr = '/'; - if (rc) return rc; - } - } - rc = createDirectory(buf, 0755); - - return rc; -} - -static int expandRegular(struct ourfd * fd, struct cpioHeader * hdr, - cpioCallback cb, void * cbData) { - int out; - char buf[8192]; - int bytesRead; - unsigned long left = hdr->size; - int rc = 0; - struct cpioCallbackInfo cbInfo; - struct stat sb; - - if (!lstat(hdr->path, &sb)) - if (unlink(hdr->path)) - return CPIOERR_UNLINK_FAILED; - - out = open(hdr->path, O_CREAT | O_WRONLY, 0); - if (out < 0) - return CPIOERR_OPEN_FAILED; - - cbInfo.file = hdr->path; - cbInfo.fileSize = hdr->size; - - while (left) { - bytesRead = ourread(fd, buf, left < sizeof(buf) ? left : sizeof(buf)); - if (bytesRead <= 0) { - rc = CPIOERR_READ_FAILED; - break; - } - - if (write(out, buf, bytesRead) != bytesRead) { - rc = CPIOERR_COPY_FAILED; - break; - } - - left -= bytesRead; - - /* don't call this with fileSize == fileComplete */ - if (!rc && cb && left) { - cbInfo.fileComplete = hdr->size - left; - cbInfo.bytesProcessed = fd->pos; - cb(&cbInfo, cbData); - } - } - - close(out); - - return rc; -} - -static int expandSymlink(struct ourfd * fd, struct cpioHeader * hdr) { - char buf[2048], buf2[2048]; - struct stat sb; - int len; - - if ((hdr->size + 1)> sizeof(buf)) - return CPIOERR_INTERNAL; - - if (ourread(fd, buf, hdr->size) != hdr->size) - return CPIOERR_READ_FAILED; - - buf[hdr->size] = '\0'; - - if (!lstat(hdr->path, &sb)) { - if (S_ISLNK(sb.st_mode)) { - len = readlink(hdr->path, buf2, sizeof(buf2) - 1); - if (len > 0) { - buf2[len] = '\0'; - if (!strcmp(buf, buf2)) return 0; - } - } - - if (unlink(hdr->path)) - return CPIOERR_UNLINK_FAILED; - } - - if (symlink(buf, hdr->path) < 0) - return CPIOERR_SYMLINK_FAILED; - - return 0; -} - -static int expandFifo(struct ourfd * fd, struct cpioHeader * hdr) { - struct stat sb; - - if (!lstat(hdr->path, &sb)) { - if (S_ISFIFO(sb.st_mode)) return 0; - - if (unlink(hdr->path)) - return CPIOERR_UNLINK_FAILED; - } - - if (mkfifo(hdr->path, 0)) - return CPIOERR_MKFIFO_FAILED; - - return 0; -} - -static int expandDevice(struct ourfd * fd, struct cpioHeader * hdr) { - struct stat sb; - - if (!lstat(hdr->path, &sb)) { - if ((S_ISCHR(sb.st_mode) || S_ISBLK(sb.st_mode)) && - (sb.st_rdev == hdr->rdev)) - return 0; - if (unlink(hdr->path)) - return CPIOERR_UNLINK_FAILED; - } - - if (mknod(hdr->path, hdr->mode & (~0777), hdr->rdev)) - return CPIOERR_MKNOD_FAILED; - - return 0; -} - -static void freeLink(struct hardLink * li) { - int i; - - for (i = 0; i < li->nlink; i++) { - if (li->files[i]) free(li->files[i]); - } - free(li->files); -} - -static int createLinks(struct hardLink * li, const char ** failedFile) { - int i; - struct stat sb; - - for (i = 0; i < li->nlink; i++) { - if (i == li->createdPath) continue; - if (!li->files[i]) continue; - - if (!lstat(li->files[i], &sb)) { - if (unlink(li->files[i])) { - *failedFile = strdup(li->files[i]); - return CPIOERR_UNLINK_FAILED; - } - } - - if (link(li->files[li->createdPath], li->files[i])) { - *failedFile = strdup(li->files[i]); - return CPIOERR_LINK_FAILED; - } - - free(li->files[i]); - li->files[i] = NULL; - li->linksLeft--; - } - - return 0; -} - -static int eatBytes(struct ourfd * fd, unsigned long amount) { - char buf[4096]; - unsigned long bite; - - while (amount) { - bite = (amount > sizeof(buf)) ? sizeof(buf) : amount; - if (ourread(fd, buf, bite) != bite) - return CPIOERR_READ_FAILED; - amount -= bite; - } - - return 0; -} - -int myCpioInstallArchive(gzFile stream, struct cpioFileMapping * mappings, - int numMappings, cpioCallback cb, void * cbData, - const char ** failedFile) { - struct cpioHeader ch; - struct ourfd fd; - int rc = 0; - int linkNum = 0; - struct cpioFileMapping * map = NULL; - struct cpioFileMapping needle; - mode_t cpioMode; - int olderr; - struct cpioCallbackInfo cbInfo; - struct hardLink * links = NULL; - struct hardLink * li = NULL; - - fd.fd = stream; - fd.pos = 0; - - *failedFile = NULL; - - do { - if ((rc = getNextHeader(&fd, &ch, NULL))) { - logMessage( WARNING, "error %d reading header: %s\n", rc, - myCpioStrerror(rc)); - return CPIOERR_BAD_HEADER; - } - - if (!strcmp(ch.path, TRAILER)) { - free(ch.path); - break; - } - - if (mappings) { - needle.archivePath = ch.path; - map = bsearch(&needle, mappings, numMappings, sizeof(needle), - myCpioFileMapCmp); - } - - if (mappings && !map) { - eatBytes(&fd, ch.size); - } else { - cpioMode = ch.mode; - - if (map) { - if (map->mapFlags & CPIO_MAP_PATH) { - free(ch.path); - ch.path = strdup(map->fsPath); - } - - if (map->mapFlags & CPIO_MAP_MODE) - ch.mode = map->finalMode; - if (map->mapFlags & CPIO_MAP_UID) - ch.uid = map->finalUid; - if (map->mapFlags & CPIO_MAP_GID) - ch.gid = map->finalGid; - } - - /* This won't get hard linked symlinks right, but I can't seem - to create those anyway */ - - if (S_ISREG(ch.mode) && ch.nlink > 1) { - li = links; - for (li = links; li; li = li->next) { - if (li->inode == ch.inode && li->dev == ch.dev) break; - } - - if (!li) { - li = malloc(sizeof(*li)); - li->inode = ch.inode; - li->dev = ch.dev; - li->nlink = ch.nlink; - li->linksLeft = ch.nlink; - li->createdPath = -1; - li->files = calloc(sizeof(char *), li->nlink); - li->next = links; - links = li; - } - - for (linkNum = 0; linkNum < li->nlink; linkNum++) - if (!li->files[linkNum]) break; - li->files[linkNum] = strdup(ch.path); - } - - if ((ch.nlink > 1) && S_ISREG(ch.mode) && !ch.size && - li->createdPath == -1) { - /* defer file creation */ - } else if ((ch.nlink > 1) && S_ISREG(ch.mode) && - (li->createdPath != -1)) { - createLinks(li, failedFile); - - /* this only happens for cpio archives which contain - hardlinks w/ the contents of each hardlink being - listed (intead of the data being given just once. This - shouldn't happen, but I've made it happen w/ buggy - code, so what the heck? GNU cpio handles this well fwiw */ - if (ch.size) eatBytes(&fd, ch.size); - } else { - rc = checkDirectory(ch.path); - - if (!rc) { - if (S_ISREG(ch.mode)) - rc = expandRegular(&fd, &ch, cb, cbData); - else if (S_ISDIR(ch.mode)) - rc = createDirectory(ch.path, 000); - else if (S_ISLNK(ch.mode)) - rc = expandSymlink(&fd, &ch); - else if (S_ISFIFO(ch.mode)) - rc = expandFifo(&fd, &ch); - else if (S_ISCHR(ch.mode) || S_ISBLK(ch.mode)) - rc = expandDevice(&fd, &ch); - else if (S_ISSOCK(ch.mode)) { - /* this mimicks cpio but probably isnt' right */ - rc = expandFifo(&fd, &ch); - } else { - rc = CPIOERR_INTERNAL; - } - } - - if (!rc) - rc = setInfo(&ch); - - if (S_ISREG(ch.mode) && ch.nlink > 1) { - li->createdPath = linkNum; - li->linksLeft--; - rc = createLinks(li, failedFile); - } - } - - if (rc && !*failedFile) { - *failedFile = strdup(ch.path); - - olderr = errno; - unlink(ch.path); - errno = olderr; - } - } - - padinfd(&fd, 4); - - if (!rc && cb) { - cbInfo.file = ch.path; - cbInfo.fileSize = ch.size; - cbInfo.fileComplete = ch.size; - cbInfo.bytesProcessed = fd.pos; - cb(&cbInfo, cbData); - } - - free(ch.path); - } while (1 && !rc); - - li = links; - while (li && !rc) { - if (li->linksLeft) { - if (li->createdPath == -1) - rc = CPIOERR_INTERNAL; - else - rc = createLinks(li, failedFile); - } - - freeLink(li); - - links = li; - li = li->next; - free(links); - links = li; - } - - li = links; - /* if an error got us here links will still be eating some memory */ - while (li) { - freeLink(li); - links = li; - li = li->next; - free(links); - } - - return rc; -} - -const char * myCpioStrerror(int rc) -{ - static char msg[256]; - char *s; - int l, myerrno = errno; - - strcpy(msg, "cpio: "); - switch (rc) { - default: - s = msg + strlen(msg); - sprintf(s, "(error 0x%x)", rc); - s = NULL; - break; - case CPIOERR_BAD_MAGIC: s = "Bad magic"; break; - case CPIOERR_BAD_HEADER: s = "Bad header"; break; - case CPIOERR_OPEN_FAILED: s = "open"; break; - case CPIOERR_CHMOD_FAILED: s = "chmod"; break; - case CPIOERR_CHOWN_FAILED: s = "chown"; break; - case CPIOERR_WRITE_FAILED: s = "write"; break; - case CPIOERR_UTIME_FAILED: s = "utime"; break; - case CPIOERR_UNLINK_FAILED: s = "unlink"; break; - case CPIOERR_SYMLINK_FAILED: s = "symlink"; break; - case CPIOERR_STAT_FAILED: s = "stat"; break; - case CPIOERR_MKDIR_FAILED: s = "mkdir"; break; - case CPIOERR_MKNOD_FAILED: s = "mknod"; break; - case CPIOERR_MKFIFO_FAILED: s = "mkfifo"; break; - case CPIOERR_LINK_FAILED: s = "link"; break; - case CPIOERR_READLINK_FAILED: s = "readlink"; break; - case CPIOERR_READ_FAILED: s = "read"; break; - case CPIOERR_COPY_FAILED: s = "copy"; break; - case CPIOERR_INTERNAL: s = "Internal error"; break; - case CPIOERR_HDR_SIZE: s = "Header size too big";break; - case CPIOERR_UNKNOWN_FILETYPE: s = "Unknown file type";break; - } - - l = sizeof(msg) - strlen(msg) - 1; - if (s != NULL) { - if (l > 0) strncat(msg, s, l); - l -= strlen(s); - } - if (rc & CPIOERR_CHECK_ERRNO) { - s = " failed - "; - if (l > 0) strncat(msg, s, l); - l -= strlen(s); - if (l > 0) strncat(msg, strerror(myerrno), l); - } - return msg; -} - -static int copyFile(struct ourfd * inFd, struct ourfd * outFd, - struct cpioHeader * chp, struct cpioCrcPhysicalHeader * pHdr) { - char buf[8192]; - int amount; - size_t size = chp->size; - - amount = strlen(chp->path) + 1; - memcpy(pHdr->magic, CPIO_NEWC_MAGIC, sizeof(pHdr->magic)); - - gzip_write(outFd->fd, pHdr, PHYS_HDR_SIZE); - gzip_write(outFd->fd, chp->path, amount); - - outFd->pos += PHYS_HDR_SIZE + amount; - - padoutfd(outFd, &outFd->pos, 4); - - while (size) { - amount = ourread(inFd, buf, size > sizeof(buf) ? sizeof(buf) : size); - gzip_write(outFd->fd, buf, amount); - size -= amount; - } - - outFd->pos += chp->size; - - padoutfd(outFd, &outFd->pos, 4); - - return 0; -} - -int myCpioFilterArchive(gzFile inStream, gzFile outStream, char ** patterns) { - struct ourfd inFd, outFd; - char ** aPattern; - struct cpioHeader ch; - int rc; - struct cpioCrcPhysicalHeader pHeader; - - inFd.fd = inStream; - inFd.pos = 0; - outFd.fd = outStream; - outFd.pos = 0; - - do { - if ((rc = getNextHeader(&inFd, &ch, &pHeader))) { - logMessage( WARNING, "error %d reading header: %s\n", rc, - myCpioStrerror(rc)); - return CPIOERR_BAD_HEADER; - } - - if (!strcmp(ch.path, TRAILER)) { - free(ch.path); - break; - } - - for (aPattern = patterns; *aPattern; aPattern++) - if (!fnmatch(*aPattern, ch.path, FNM_PATHNAME | FNM_PERIOD)) - break; - - if (!*aPattern) - eatBytes(&inFd, ch.size); - else - copyFile(&inFd, &outFd, &ch, &pHeader); - - padinfd(&inFd, 4); - - free(ch.path); - } while (1 && !rc); - - memset(&pHeader, '0', sizeof(pHeader)); - memcpy(pHeader.magic, CPIO_NEWC_MAGIC, sizeof(pHeader.magic)); - memcpy(pHeader.nlink, "00000001", 8); - memcpy(pHeader.namesize, "0000000b", 8); - gzip_write(outFd.fd, &pHeader, PHYS_HDR_SIZE); - gzip_write(outFd.fd, "TRAILER!!!", 11); - - outFd.pos += PHYS_HDR_SIZE + 11; - - if ((rc = padoutfd(&outFd, &outFd.pos, 4))) - return rc; - - if ((rc = padoutfd(&outFd, &outFd.pos, 512))) - return rc; - - return 0; -}
Ack.
-- Martin Sivák msivak@redhat.com Red Hat Czech Anaconda team / Brno, CZ
----- "David Cantrell" dcantrell@redhat.com wrote:
The only place this code is still used is in loader. Loader is now using libarchive to unpack cpio streams and zlib to uncompress them, so we do not need these functions anymore.
pyanaconda/isys/Makefile.am | 2 +- pyanaconda/isys/cpio.c | 46 --- pyanaconda/isys/cpio.h | 102 ------ pyanaconda/isys/lang.c | 4 +- pyanaconda/isys/lang.h | 2 +- pyanaconda/isys/stubs.h | 44 --- pyanaconda/isys/uncpio.c | 797
7 files changed, 4 insertions(+), 993 deletions(-) delete mode 100644 pyanaconda/isys/cpio.c delete mode 100644 pyanaconda/isys/cpio.h delete mode 100644 pyanaconda/isys/stubs.h delete mode 100644 pyanaconda/isys/uncpio.c
diff --git a/pyanaconda/isys/Makefile.am b/pyanaconda/isys/Makefile.am index 2b3130c..3d521d7 100644 --- a/pyanaconda/isys/Makefile.am +++ b/pyanaconda/isys/Makefile.am @@ -19,7 +19,7 @@
pkgpyexecdir = $(pyexecdir)/py$(PACKAGE_NAME)
-ISYS_SRCS = devices.c imount.c cpio.c uncpio.c lang.c \ +ISYS_SRCS = devices.c imount.c lang.c \ isofs.c linkdetect.c vio.c ethtool.c eddsupport.c iface.c \ auditd.c log.c mem.c
diff --git a/pyanaconda/isys/cpio.c b/pyanaconda/isys/cpio.c deleted file mode 100644 index fd83605..0000000 --- a/pyanaconda/isys/cpio.c +++ /dev/null @@ -1,46 +0,0 @@ -/*
- cpio.c
- Copyright (C) 2007 Red Hat, Inc. All rights reserved.
- This program is free software; you can redistribute it and/or
modify
- it under the terms of the GNU General Public License as published
by
- the Free Software Foundation; either version 2 of the License, or
- (at your option) any later version.
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
- You should have received a copy of the GNU General Public License
- along with this program. If not, see
- */
-#include <fcntl.h> -#include <stdio.h> -#include <stdlib.h> -#include <unistd.h>
-#include "cpio.h"
-int installCpioFile(gzFile fd, char * cpioName, char * outName, int inWin) {
- struct cpioFileMapping map;
- int rc;
- const char * failedFile;
- if (outName) {
- map.archivePath = cpioName;
- map.fsPath = outName;
- map.mapFlags = CPIO_MAP_PATH;
- }
- rc = myCpioInstallArchive(fd, outName ? &map : NULL, 1, NULL,
NULL,
&failedFile);- if (rc || access(outName, R_OK)) {
- return -1;
- }
- return 0;
-} diff --git a/pyanaconda/isys/cpio.h b/pyanaconda/isys/cpio.h deleted file mode 100644 index 4cbb7c0..0000000 --- a/pyanaconda/isys/cpio.h +++ /dev/null @@ -1,102 +0,0 @@ -/*
- cpio.h
- Copyright (C) 2007 Red Hat, Inc. All rights reserved.
- This program is free software; you can redistribute it and/or
modify
- it under the terms of the GNU General Public License as published
by
- the Free Software Foundation; either version 2 of the License, or
- (at your option) any later version.
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
- You should have received a copy of the GNU General Public License
- along with this program. If not, see
- */
-#ifndef H_CPIO -#define H_CPIO
-#include <sys/types.h>
-#include "stubs.h"
-/* Note the CPIO_CHECK_ERRNO bit is set only if errno is valid. These have to
- be positive numbers or this setting the high bit stuff is a bad
idea. */ -#define CPIOERR_CHECK_ERRNO 0x80000000
-#define CPIOERR_BAD_MAGIC (2 ) -#define CPIOERR_BAD_HEADER (3 ) -#define CPIOERR_OPEN_FAILED (4 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_CHMOD_FAILED (5 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_CHOWN_FAILED (6 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_WRITE_FAILED (7 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_UTIME_FAILED (8 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_UNLINK_FAILED (9 | CPIOERR_CHECK_ERRNO)
-#define CPIOERR_SYMLINK_FAILED (11 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_STAT_FAILED (12 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_MKDIR_FAILED (13 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_MKNOD_FAILED (14 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_MKFIFO_FAILED (15 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_LINK_FAILED (16 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_READLINK_FAILED (17 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_READ_FAILED (18 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_COPY_FAILED (19 | CPIOERR_CHECK_ERRNO) -#define CPIOERR_INTERNAL (20 ) -#define CPIOERR_HDR_SIZE (21 ) -#define CPIOERR_UNKNOWN_FILETYPE (22 )
-/* Don't think this behaves just like standard cpio. It's pretty close, but
- it has some behaviors which are more to RPM's liking. I tried to
document
- them inline in cpio.c, but I may have missed some. */
-#define CPIO_MAP_PATH (1 << 0) -#define CPIO_MAP_MODE (1 << 1) -#define CPIO_MAP_UID (1 << 2) -#define CPIO_MAP_GID (1 << 3) -#define CPIO_FOLLOW_SYMLINKS (1 << 4) /* only for building */
-struct cpioFileMapping {
- char * archivePath;
- char * fsPath;
- mode_t finalMode;
- uid_t finalUid;
- gid_t finalGid;
- int mapFlags;
-};
-/* on cpio building, only "file" is filled in */ -struct cpioCallbackInfo {
- char * file;
- long fileSize; /* total file size */
- long fileComplete; /* amount of file unpacked */
- long bytesProcessed; /* bytes in archive read */
-};
-typedef void (*cpioCallback)(struct cpioCallbackInfo * filespec, void
- data);
-/* If no mappings are passed, this installs everything! If one is passed
- it should be sorted according to cpioFileMapCmp() and only files
included
- in the map are installed. Files are installed relative to the
current
- directory unless a mapping is given which specifies an absolute
- directory. The mode mapping is only used for the permission bits,
not
- for the file type. The owner/group mappings are ignored for the
nonroot
- user. If *failedFile is non-NULL on return, it should be free()d.
*/ -int myCpioInstallArchive(gzFile stream, struct cpioFileMapping * mappings,
int numMappings, cpioCallback cb, void * cbData,const char ** failedFile);-int myCpioFilterArchive(gzFile inStream, gzFile outStream, char ** pattern);
-/* This is designed to be qsort/bsearch compatible */ -int myCpioFileMapCmp(const void * a, const void * b);
-const char *myCpioStrerror(int rc);
-int installCpioFile(gzFile fd, char * cpioName, char * outName, int inWin);
-#endif diff --git a/pyanaconda/isys/lang.c b/pyanaconda/isys/lang.c index b6e2a36..19b98ea 100644 --- a/pyanaconda/isys/lang.c +++ b/pyanaconda/isys/lang.c @@ -33,12 +33,12 @@ #define NR_KEYS 128 #endif
+#include <zlib.h>
#include "linux/kd.h"
-#include "cpio.h" #include "isys.h" #include "lang.h" -#include "stubs.h"
int isysLoadFont(void) { unsigned char font[65536]; diff --git a/pyanaconda/isys/lang.h b/pyanaconda/isys/lang.h index a08adbd..a83778a 100644 --- a/pyanaconda/isys/lang.h +++ b/pyanaconda/isys/lang.h @@ -20,7 +20,7 @@ #ifndef ISYS_LANG_H #define ISYS_LANG_H
-#include "stubs.h" +#include <zlib.h>
/* define ask johnsonm@redhat.com where this came from */ #define KMAP_MAGIC 0x8B39C07F diff --git a/pyanaconda/isys/stubs.h b/pyanaconda/isys/stubs.h deleted file mode 100644 index 40ecb22..0000000 --- a/pyanaconda/isys/stubs.h +++ /dev/null @@ -1,44 +0,0 @@ -/*
- stubs.h
- Copyright (C) 2007 Red Hat, Inc. All rights reserved.
- This program is free software; you can redistribute it and/or
modify
- it under the terms of the GNU General Public License as published
by
- the Free Software Foundation; either version 2 of the License, or
- (at your option) any later version.
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
- You should have received a copy of the GNU General Public License
- along with this program. If not, see
- */
-/* we use gzlib when linked against dietlibc, but otherwise, we should use
- zlib. it would make more sense to do the defines in the other
direction,
- but that causes symbol wackiness because both gunzip_open and
gzip_open in
- gzlib are gzopen from zlib
-*/
-#ifndef ISYS_STUB -#define ISYS_STUB
-#ifndef GZLIB -#include <zlib.h>
-#define gunzip_open(x) gzopen(x, "r") -#define gunzip_dopen gzdopen(x, "r") -#define gunzip_close gzclose -#define gunzip_read gzread -#define gzip_write gzwrite -#define gzip_open(x, y, z) gzopen(x, "w")
-#else -#include "gzlib/gzlib.h"
-#endif
-#endif diff --git a/pyanaconda/isys/uncpio.c b/pyanaconda/isys/uncpio.c deleted file mode 100644 index 0481ff0..0000000 --- a/pyanaconda/isys/uncpio.c +++ /dev/null @@ -1,797 +0,0 @@ -/*
- uncpio.c
- Copyright (C) 2007 Red Hat, Inc. All rights reserved.
- This program is free software; you can redistribute it and/or
modify
- it under the terms of the GNU General Public License as published
by
- the Free Software Foundation; either version 2 of the License, or
- (at your option) any later version.
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
- You should have received a copy of the GNU General Public License
- along with this program. If not, see
- */
-#define HAVE_ALLOCA_H 1 -#define MAJOR_IN_SYSMACROS 1
-#if HAVE_ALLOCA_H -# include <alloca.h> -#endif
-#define _(foo) (foo)
-#include <errno.h> -#include <fcntl.h> -#include <fnmatch.h> -#include <stdio.h> -#include <stdlib.h> -#include <string.h> -#include <sys/types.h> -#include <sys/stat.h> -#include <unistd.h> -#include <utime.h>
-#include "cpio.h" -#include "stubs.h" -#include "log.h"
-#if MAJOR_IN_SYSMACROS -#include <sys/sysmacros.h> -#elif MAJOR_IN_MKDEV -#include <sys/mkdev.h> -#endif
-#define CPIO_NEWC_MAGIC "070701" -#define CPIO_CRC_MAGIC "070702" -#define TRAILER "TRAILER!!!"
-/* FIXME: We don't translate between cpio and system mode bits! These
- should both be the same, but really odd things are going to happen
if
- that's not true! */
-/* We need to maintain our oun file pointer to allow padding */ -struct ourfd {
- gzFile fd;
- size_t pos;
-};
-struct hardLink {
- struct hardLink * next;
- char ** files; /* there are nlink of these, used by
install */
- int * fileMaps; /* used by build */
- dev_t dev;
- ino_t inode;
- int nlink;
- int linksLeft;
- int createdPath;
- struct stat sb;
-};
-struct cpioCrcPhysicalHeader {
- char magic[6];
- char inode[8];
- char mode[8];
- char uid[8];
- char gid[8];
- char nlink[8];
- char mtime[8];
- char filesize[8];
- char devMajor[8];
- char devMinor[8];
- char rdevMajor[8];
- char rdevMinor[8];
- char namesize[8];
- char checksum[8]; /* ignored !! */
-};
-#define PHYS_HDR_SIZE 110 /* don't depend on sizeof(struct) */
-struct cpioHeader {
- ino_t inode;
- mode_t mode;
- uid_t uid;
- gid_t gid;
- int nlink;
- time_t mtime;
- unsigned long size;
- dev_t dev, rdev;
- char * path;
-};
-static inline off_t ourread(struct ourfd * thefd, void * buf, size_t size) {
- off_t i;
- i = gunzip_read(thefd->fd, buf, size);
- thefd->pos += i;
- return i;
-}
-static inline void padinfd(struct ourfd * fd, int modulo) {
- int buf[10];
- int amount;
- amount = (modulo - fd->pos % modulo) % modulo;
- ourread(fd, buf, amount);
-}
-static inline int padoutfd(struct ourfd * fd, size_t * where, int modulo) {
- /*static int buf[10] = { '\0', '\0', '\0', '\0', '\0',
'\0', '\0', '\0', '\0', '\0' };*/- int amount;
- static int buf[512];
- amount = (modulo - *where % modulo) % modulo;
- *where += amount;
- if (gzip_write(fd->fd, buf, amount) != amount)
return CPIOERR_WRITE_FAILED;- return 0;
-}
-static int strntoul(const char * str, char ** endptr, int base, int num) {
- char * buf, * end;
- unsigned long ret;
- buf = alloca(num + 1);
- strncpy(buf, str, num);
- buf[num] = '\0';
- ret = strtoul(buf, &end, base);
- if (*end)
*endptr = (char *)(str + (end - buf)); /* XXX discards const*/
- else
*endptr = "";- return strtoul(buf, endptr, base);
-}
-#define GET_NUM_FIELD(phys, log) \
log = strntoul(phys, &end, 16, sizeof(phys)); \if (*end) return CPIOERR_BAD_HEADER;-#define SET_NUM_FIELD(phys, val, space) \
sprintf(space, "%8.8lx", (unsigned long) (val)); \memcpy(phys, space, 8);-static int getNextHeader(struct ourfd * fd, struct cpioHeader * chPtr,
struct cpioCrcPhysicalHeader *physHeaderPtr) {
- struct cpioCrcPhysicalHeader physHeader;
- int nameSize;
- char * end;
- int major, minor;
- if (ourread(fd, &physHeader, PHYS_HDR_SIZE) != PHYS_HDR_SIZE)
return CPIOERR_READ_FAILED;- if (physHeaderPtr)
memcpy(physHeaderPtr, &physHeader, PHYS_HDR_SIZE);- if (strncmp(CPIO_CRC_MAGIC, physHeader.magic,
strlen(CPIO_CRC_MAGIC)) &&
strncmp(CPIO_NEWC_MAGIC, physHeader.magic,strlen(CPIO_NEWC_MAGIC)))
return CPIOERR_BAD_MAGIC;- GET_NUM_FIELD(physHeader.inode, chPtr->inode);
- GET_NUM_FIELD(physHeader.mode, chPtr->mode);
- GET_NUM_FIELD(physHeader.uid, chPtr->uid);
- GET_NUM_FIELD(physHeader.gid, chPtr->gid);
- GET_NUM_FIELD(physHeader.nlink, chPtr->nlink);
- GET_NUM_FIELD(physHeader.mtime, chPtr->mtime);
- GET_NUM_FIELD(physHeader.filesize, chPtr->size);
- GET_NUM_FIELD(physHeader.devMajor, major);
- GET_NUM_FIELD(physHeader.devMinor, minor);
- chPtr->dev = makedev(major, minor);
- GET_NUM_FIELD(physHeader.rdevMajor, major);
- GET_NUM_FIELD(physHeader.rdevMinor, minor);
- chPtr->rdev = makedev(major, minor);
- GET_NUM_FIELD(physHeader.namesize, nameSize);
- chPtr->path = malloc(nameSize + 1);
- if (ourread(fd, chPtr->path, nameSize) != nameSize) {
free(chPtr->path);return CPIOERR_BAD_HEADER;- }
- /* this is unecessary chPtr->path[nameSize] = '\0'; */
- padinfd(fd, 4);
- return 0;
-}
-int myCpioFileMapCmp(const void * a, const void * b) {
- const struct cpioFileMapping * first = a;
- const struct cpioFileMapping * second = b;
- return (strcmp(first->archivePath, second->archivePath));
-}
-/* This could trash files in the path! I'm not sure that's a good thing */ -static int createDirectory(char * path, mode_t perms) {
- struct stat sb;
- int dounlink;
- if (!lstat(path, &sb)) {
if (S_ISDIR(sb.st_mode)) {return 0;} else if (S_ISLNK(sb.st_mode)) {if (stat(path, &sb)) {if (errno != ENOENT)return CPIOERR_STAT_FAILED;dounlink = 1;} else {if (S_ISDIR(sb.st_mode))return 0;dounlink = 1;}} else {dounlink = 1;}if (dounlink && unlink(path)) {return CPIOERR_UNLINK_FAILED;}- }
- if (mkdir(path, 000))
return CPIOERR_MKDIR_FAILED;- if (chmod(path, perms))
return CPIOERR_CHMOD_FAILED;- return 0;
-}
-static int setInfo(struct cpioHeader * hdr) {
- int rc = 0;
- struct utimbuf stamp;
- stamp.actime = hdr->mtime;
- stamp.modtime = hdr->mtime;
- if (!S_ISLNK(hdr->mode)) {
if (!getuid() && chown(hdr->path, hdr->uid, hdr->gid))rc = CPIOERR_CHOWN_FAILED;if (!rc && chmod(hdr->path, hdr->mode & 07777))rc = CPIOERR_CHMOD_FAILED;if (!rc && utime(hdr->path, &stamp))rc = CPIOERR_UTIME_FAILED;- } else {
-# if ! CHOWN_FOLLOWS_SYMLINK
if (!getuid() && !rc && lchown(hdr->path, hdr->uid,hdr->gid))
rc = CPIOERR_CHOWN_FAILED;-# endif
- }
- return rc;
-}
-static int checkDirectory(char * filename) {
- static char * lastDir = NULL;
- static int lastDirLength = 0;
- static int lastDirAlloced = 0;
- int length = strlen(filename);
- char * buf;
- char * chptr;
- int rc = 0;
- buf = alloca(length + 1);
- strcpy(buf, filename);
- for (chptr = buf + length - 1; chptr > buf; chptr--) {
if (*chptr == '/') break;- }
- if (chptr == buf) return 0; /* /filename - no directories */
- *chptr = '\0'; /* buffer is now just directories
*/
- length = strlen(buf);
- if (lastDirLength == length && !strcmp(buf, lastDir)) return 0;
- if (lastDirAlloced < (length + 1)) {
lastDirAlloced = length + 100;lastDir = realloc(lastDir, lastDirAlloced);- }
- strcpy(lastDir, buf);
- lastDirLength = length;
- for (chptr = buf + 1; *chptr; chptr++) {
if (*chptr == '/') {*chptr = '\0';rc = createDirectory(buf, 0755);*chptr = '/';if (rc) return rc;}- }
- rc = createDirectory(buf, 0755);
- return rc;
-}
-static int expandRegular(struct ourfd * fd, struct cpioHeader * hdr,
cpioCallback cb, void * cbData) {- int out;
- char buf[8192];
- int bytesRead;
- unsigned long left = hdr->size;
- int rc = 0;
- struct cpioCallbackInfo cbInfo;
- struct stat sb;
- if (!lstat(hdr->path, &sb))
if (unlink(hdr->path))return CPIOERR_UNLINK_FAILED;- out = open(hdr->path, O_CREAT | O_WRONLY, 0);
- if (out < 0)
return CPIOERR_OPEN_FAILED;- cbInfo.file = hdr->path;
- cbInfo.fileSize = hdr->size;
- while (left) {
bytesRead = ourread(fd, buf, left < sizeof(buf) ? left :sizeof(buf));
if (bytesRead <= 0) {rc = CPIOERR_READ_FAILED;break;}if (write(out, buf, bytesRead) != bytesRead) {rc = CPIOERR_COPY_FAILED;break;}left -= bytesRead;/* don't call this with fileSize == fileComplete */if (!rc && cb && left) {cbInfo.fileComplete = hdr->size - left;cbInfo.bytesProcessed = fd->pos;cb(&cbInfo, cbData);}- }
- close(out);
- return rc;
-}
-static int expandSymlink(struct ourfd * fd, struct cpioHeader * hdr) {
- char buf[2048], buf2[2048];
- struct stat sb;
- int len;
- if ((hdr->size + 1)> sizeof(buf))
return CPIOERR_INTERNAL;- if (ourread(fd, buf, hdr->size) != hdr->size)
return CPIOERR_READ_FAILED;- buf[hdr->size] = '\0';
- if (!lstat(hdr->path, &sb)) {
if (S_ISLNK(sb.st_mode)) {len = readlink(hdr->path, buf2, sizeof(buf2) - 1);if (len > 0) {buf2[len] = '\0';if (!strcmp(buf, buf2)) return 0;}}if (unlink(hdr->path))return CPIOERR_UNLINK_FAILED;- }
- if (symlink(buf, hdr->path) < 0)
return CPIOERR_SYMLINK_FAILED;- return 0;
-}
-static int expandFifo(struct ourfd * fd, struct cpioHeader * hdr) {
- struct stat sb;
- if (!lstat(hdr->path, &sb)) {
if (S_ISFIFO(sb.st_mode)) return 0;if (unlink(hdr->path))return CPIOERR_UNLINK_FAILED;- }
- if (mkfifo(hdr->path, 0))
return CPIOERR_MKFIFO_FAILED;- return 0;
-}
-static int expandDevice(struct ourfd * fd, struct cpioHeader * hdr) {
- struct stat sb;
- if (!lstat(hdr->path, &sb)) {
if ((S_ISCHR(sb.st_mode) || S_ISBLK(sb.st_mode)) &&(sb.st_rdev == hdr->rdev))return 0;if (unlink(hdr->path))return CPIOERR_UNLINK_FAILED;- }
- if (mknod(hdr->path, hdr->mode & (~0777), hdr->rdev))
return CPIOERR_MKNOD_FAILED;- return 0;
-}
-static void freeLink(struct hardLink * li) {
- int i;
- for (i = 0; i < li->nlink; i++) {
if (li->files[i]) free(li->files[i]);- }
- free(li->files);
-}
-static int createLinks(struct hardLink * li, const char ** failedFile) {
- int i;
- struct stat sb;
- for (i = 0; i < li->nlink; i++) {
if (i == li->createdPath) continue;if (!li->files[i]) continue;if (!lstat(li->files[i], &sb)) {if (unlink(li->files[i])) {*failedFile = strdup(li->files[i]);return CPIOERR_UNLINK_FAILED;}}if (link(li->files[li->createdPath], li->files[i])) {*failedFile = strdup(li->files[i]);return CPIOERR_LINK_FAILED;}free(li->files[i]);li->files[i] = NULL;li->linksLeft--;- }
- return 0;
-}
-static int eatBytes(struct ourfd * fd, unsigned long amount) {
- char buf[4096];
- unsigned long bite;
- while (amount) {
bite = (amount > sizeof(buf)) ? sizeof(buf) : amount;if (ourread(fd, buf, bite) != bite)return CPIOERR_READ_FAILED;amount -= bite;- }
- return 0;
-}
-int myCpioInstallArchive(gzFile stream, struct cpioFileMapping * mappings,
int numMappings, cpioCallback cb, void *cbData,
const char ** failedFile) {- struct cpioHeader ch;
- struct ourfd fd;
- int rc = 0;
- int linkNum = 0;
- struct cpioFileMapping * map = NULL;
- struct cpioFileMapping needle;
- mode_t cpioMode;
- int olderr;
- struct cpioCallbackInfo cbInfo;
- struct hardLink * links = NULL;
- struct hardLink * li = NULL;
- fd.fd = stream;
- fd.pos = 0;
- *failedFile = NULL;
- do {
if ((rc = getNextHeader(&fd, &ch, NULL))) {logMessage( WARNING, "error %d reading header: %s\n",rc,
myCpioStrerror(rc));return CPIOERR_BAD_HEADER;}if (!strcmp(ch.path, TRAILER)) {free(ch.path);break;}if (mappings) {needle.archivePath = ch.path;map = bsearch(&needle, mappings, numMappings,sizeof(needle),
myCpioFileMapCmp);}if (mappings && !map) {eatBytes(&fd, ch.size);} else {cpioMode = ch.mode;if (map) {if (map->mapFlags & CPIO_MAP_PATH) {free(ch.path);ch.path = strdup(map->fsPath);}if (map->mapFlags & CPIO_MAP_MODE)ch.mode = map->finalMode;if (map->mapFlags & CPIO_MAP_UID)ch.uid = map->finalUid;if (map->mapFlags & CPIO_MAP_GID)ch.gid = map->finalGid;}/* This won't get hard linked symlinks right, but I can'tseem
to create those anyway */if (S_ISREG(ch.mode) && ch.nlink > 1) {li = links;for (li = links; li; li = li->next) {if (li->inode == ch.inode && li->dev == ch.dev)break;
}if (!li) {li = malloc(sizeof(*li));li->inode = ch.inode;li->dev = ch.dev;li->nlink = ch.nlink;li->linksLeft = ch.nlink;li->createdPath = -1;li->files = calloc(sizeof(char *), li->nlink);li->next = links;links = li;}for (linkNum = 0; linkNum < li->nlink; linkNum++)if (!li->files[linkNum]) break;li->files[linkNum] = strdup(ch.path);}if ((ch.nlink > 1) && S_ISREG(ch.mode) && !ch.size &&li->createdPath == -1) {/* defer file creation */} else if ((ch.nlink > 1) && S_ISREG(ch.mode) &&(li->createdPath != -1)) {createLinks(li, failedFile);/* this only happens for cpio archives which containhardlinks w/ the contents of each hardlink beinglisted (intead of the data being given just once.This
shouldn't happen, but I've made it happen w/buggy
code, so what the heck? GNU cpio handles this wellfwiw */
if (ch.size) eatBytes(&fd, ch.size);} else {rc = checkDirectory(ch.path);if (!rc) {if (S_ISREG(ch.mode))rc = expandRegular(&fd, &ch, cb, cbData);else if (S_ISDIR(ch.mode))rc = createDirectory(ch.path, 000);else if (S_ISLNK(ch.mode))rc = expandSymlink(&fd, &ch);else if (S_ISFIFO(ch.mode))rc = expandFifo(&fd, &ch);else if (S_ISCHR(ch.mode) || S_ISBLK(ch.mode))rc = expandDevice(&fd, &ch);else if (S_ISSOCK(ch.mode)) {/* this mimicks cpio but probably isnt' right*/
rc = expandFifo(&fd, &ch);} else {rc = CPIOERR_INTERNAL;}}if (!rc)rc = setInfo(&ch);if (S_ISREG(ch.mode) && ch.nlink > 1) {li->createdPath = linkNum;li->linksLeft--;rc = createLinks(li, failedFile);}}if (rc && !*failedFile) {*failedFile = strdup(ch.path);olderr = errno;unlink(ch.path);errno = olderr;}}padinfd(&fd, 4);if (!rc && cb) {cbInfo.file = ch.path;cbInfo.fileSize = ch.size;cbInfo.fileComplete = ch.size;cbInfo.bytesProcessed = fd.pos;cb(&cbInfo, cbData);}free(ch.path);- } while (1 && !rc);
- li = links;
- while (li && !rc) {
if (li->linksLeft) {if (li->createdPath == -1)rc = CPIOERR_INTERNAL;elserc = createLinks(li, failedFile);}freeLink(li);links = li;li = li->next;free(links);links = li;- }
- li = links;
- /* if an error got us here links will still be eating some memory
*/
- while (li) {
freeLink(li);links = li;li = li->next;free(links);- }
- return rc;
-}
-const char * myCpioStrerror(int rc) -{
- static char msg[256];
- char *s;
- int l, myerrno = errno;
- strcpy(msg, "cpio: ");
- switch (rc) {
- default:
s = msg + strlen(msg);sprintf(s, "(error 0x%x)", rc);s = NULL;break;- case CPIOERR_BAD_MAGIC: s = "Bad magic";
break;
- case CPIOERR_BAD_HEADER: s = "Bad header";
break;
- case CPIOERR_OPEN_FAILED: s = "open";
break;
- case CPIOERR_CHMOD_FAILED: s = "chmod";
break;
- case CPIOERR_CHOWN_FAILED: s = "chown";
break;
- case CPIOERR_WRITE_FAILED: s = "write";
break;
- case CPIOERR_UTIME_FAILED: s = "utime";
break;
- case CPIOERR_UNLINK_FAILED: s = "unlink";
break;
- case CPIOERR_SYMLINK_FAILED: s = "symlink";
break;
- case CPIOERR_STAT_FAILED: s = "stat";
break;
- case CPIOERR_MKDIR_FAILED: s = "mkdir";
break;
- case CPIOERR_MKNOD_FAILED: s = "mknod";
break;
- case CPIOERR_MKFIFO_FAILED: s = "mkfifo";
break;
- case CPIOERR_LINK_FAILED: s = "link";
break;
- case CPIOERR_READLINK_FAILED: s = "readlink";
break;
- case CPIOERR_READ_FAILED: s = "read";
break;
- case CPIOERR_COPY_FAILED: s = "copy";
break;
- case CPIOERR_INTERNAL: s = "Internal error";
break;
- case CPIOERR_HDR_SIZE: s = "Header size too
big";break;
- case CPIOERR_UNKNOWN_FILETYPE: s = "Unknown file
type";break;
- }
- l = sizeof(msg) - strlen(msg) - 1;
- if (s != NULL) {
if (l > 0) strncat(msg, s, l);l -= strlen(s);- }
- if (rc & CPIOERR_CHECK_ERRNO) {
s = " failed - ";if (l > 0) strncat(msg, s, l);l -= strlen(s);if (l > 0) strncat(msg, strerror(myerrno), l);- }
- return msg;
-}
-static int copyFile(struct ourfd * inFd, struct ourfd * outFd,
struct cpioHeader * chp, struct cpioCrcPhysicalHeader *pHdr) {
- char buf[8192];
- int amount;
- size_t size = chp->size;
- amount = strlen(chp->path) + 1;
- memcpy(pHdr->magic, CPIO_NEWC_MAGIC, sizeof(pHdr->magic));
- gzip_write(outFd->fd, pHdr, PHYS_HDR_SIZE);
- gzip_write(outFd->fd, chp->path, amount);
- outFd->pos += PHYS_HDR_SIZE + amount;
- padoutfd(outFd, &outFd->pos, 4);
- while (size) {
amount = ourread(inFd, buf, size > sizeof(buf) ? sizeof(buf): size);
gzip_write(outFd->fd, buf, amount);size -= amount;- }
- outFd->pos += chp->size;
- padoutfd(outFd, &outFd->pos, 4);
- return 0;
-}
-int myCpioFilterArchive(gzFile inStream, gzFile outStream, char ** patterns) {
- struct ourfd inFd, outFd;
- char ** aPattern;
- struct cpioHeader ch;
- int rc;
- struct cpioCrcPhysicalHeader pHeader;
- inFd.fd = inStream;
- inFd.pos = 0;
- outFd.fd = outStream;
- outFd.pos = 0;
- do {
if ((rc = getNextHeader(&inFd, &ch, &pHeader))) {logMessage( WARNING, "error %d reading header: %s\n",rc,
myCpioStrerror(rc));return CPIOERR_BAD_HEADER;}if (!strcmp(ch.path, TRAILER)) {free(ch.path);break;}for (aPattern = patterns; *aPattern; aPattern++)if (!fnmatch(*aPattern, ch.path, FNM_PATHNAME |FNM_PERIOD))
break;if (!*aPattern)eatBytes(&inFd, ch.size);elsecopyFile(&inFd, &outFd, &ch, &pHeader);padinfd(&inFd, 4);free(ch.path);- } while (1 && !rc);
- memset(&pHeader, '0', sizeof(pHeader));
- memcpy(pHeader.magic, CPIO_NEWC_MAGIC, sizeof(pHeader.magic));
- memcpy(pHeader.nlink, "00000001", 8);
- memcpy(pHeader.namesize, "0000000b", 8);
- gzip_write(outFd.fd, &pHeader, PHYS_HDR_SIZE);
- gzip_write(outFd.fd, "TRAILER!!!", 11);
- outFd.pos += PHYS_HDR_SIZE + 11;
- if ((rc = padoutfd(&outFd, &outFd.pos, 4)))
return rc;- if ((rc = padoutfd(&outFd, &outFd.pos, 512)))
return rc;- return 0;
-}
1.7.2.3
Anaconda-devel-list mailing list Anaconda-devel-list@redhat.com https://www.redhat.com/mailman/listinfo/anaconda-devel-list
The stubs.h header file does not exist anymore. Replace gunzip_* macro usage with the real zlib function names. --- loader/kbd.c | 17 ++++++++--------- loader/lang.c | 6 ++---- loader/loader.c | 1 - pyanaconda/isys/lang.c | 38 +++++++++++++++++++------------------- 4 files changed, 29 insertions(+), 33 deletions(-)
diff --git a/loader/kbd.c b/loader/kbd.c index c943be6..34cb29f 100644 --- a/loader/kbd.c +++ b/loader/kbd.c @@ -34,7 +34,6 @@ #include "lang.h" #include "windows.h"
-#include "../pyanaconda/isys/stubs.h" #include "../pyanaconda/isys/lang.h" #include "../pyanaconda/isys/log.h"
@@ -79,15 +78,15 @@ int chooseKeyboard(struct loaderData_s * loaderData, char ** kbdtypep) { if (!defkbd) defkbd = "us";
- f = gunzip_open("/etc/keymaps.gz"); + f = gzopen("/etc/keymaps.gz", "r"); if (!f) { errorWindow("cannot open /etc/keymaps.gz: %s"); return LOADER_ERROR; }
- if (gunzip_read(f, &hdr, sizeof(hdr)) != sizeof(hdr)) { + if (gzread(f, &hdr, sizeof(hdr)) != sizeof(hdr)) { errorWindow("failed to read keymaps header: %s"); - gunzip_close(f); + gzclose(f); return LOADER_ERROR; }
@@ -95,9 +94,9 @@ int chooseKeyboard(struct loaderData_s * loaderData, char ** kbdtypep) {
i = hdr.numEntries * sizeof(*infoTable); infoTable = alloca(i); - if (gunzip_read(f, infoTable, i) != i) { + if (gzread(f, infoTable, i) != i) { errorWindow("failed to read keymap information: %s"); - gunzip_close(f); + gzclose(f); return LOADER_ERROR; }
@@ -128,10 +127,10 @@ int chooseKeyboard(struct loaderData_s * loaderData, char ** kbdtypep) { rc = 0;
for (i = 0; i < num; i++) { - if (gunzip_read(f, buf, infoTable[i].size) != infoTable[i].size) { + if (gzread(f, buf, infoTable[i].size) != infoTable[i].size) { logMessage(ERROR, "error reading %d bytes from file: %m", infoTable[i].size); - gunzip_close(f); + gzclose(f); rc = LOADER_ERROR; } } @@ -145,7 +144,7 @@ int chooseKeyboard(struct loaderData_s * loaderData, char ** kbdtypep) { if (rc != 0) rc = LOADER_ERROR; else - gunzip_close(f); + gzclose(f);
loaderData->kbd = strdup(infoTable[num].name);
diff --git a/loader/lang.c b/loader/lang.c index 0bb351e..035fb75 100644 --- a/loader/lang.c +++ b/loader/lang.c @@ -40,8 +40,6 @@ #include "loadermisc.h" #include "windows.h"
-#include "../pyanaconda/isys/stubs.h" -#include "../pyanaconda/isys/cpio.h" #include "../pyanaconda/isys/lang.h" #include "../pyanaconda/isys/isys.h" #include "../pyanaconda/isys/log.h" @@ -161,7 +159,7 @@ void loadLanguage (char * file) { sprintf(filename, "/etc/loader.tr"); }
- stream = gunzip_open(file); + stream = gzopen(file, "r");
if (!stream) { newtWinMessage("Error", "OK", "Translation for %s is not available. " @@ -172,7 +170,7 @@ void loadLanguage (char * file) { sprintf(filename, "%s.tr", key);
rc = installCpioFile(stream, filename, "/tmp/translation", 1); - gunzip_close(stream); + gzclose(stream);
if (rc || access("/tmp/translation", R_OK)) { newtWinMessage("Error", "OK", "Cannot get translation file %s.\n", diff --git a/loader/loader.c b/loader/loader.c index f9d5483..88d7a7a 100644 --- a/loader/loader.c +++ b/loader/loader.c @@ -96,7 +96,6 @@
#include "../pyanaconda/isys/imount.h" #include "../pyanaconda/isys/isys.h" -#include "../pyanaconda/isys/stubs.h" #include "../pyanaconda/isys/lang.h" #include "../pyanaconda/isys/eddsupport.h" #include "../pyanaconda/isys/log.h" diff --git a/pyanaconda/isys/lang.c b/pyanaconda/isys/lang.c index 19b98ea..0fa3d3c 100644 --- a/pyanaconda/isys/lang.c +++ b/pyanaconda/isys/lang.c @@ -53,17 +53,17 @@ int isysLoadFont(void) { #if defined (__s390__) || defined (__s390x__) return 0; #endif - stream = gunzip_open("/etc/screenfont.gz"); + stream = gzopen("/etc/screenfont.gz", "r"); if (!stream) return -EACCES;
- gunzip_read(stream, &cfo, sizeof(cfo)); - gunzip_read(stream, font, sizeof(font)); - gunzip_read(stream, map, sizeof(map)); - gunzip_read(stream, &d.entry_ct, sizeof(d.entry_ct)); + gzread(stream, &cfo, sizeof(cfo)); + gzread(stream, font, sizeof(font)); + gzread(stream, map, sizeof(map)); + gzread(stream, &d.entry_ct, sizeof(d.entry_ct)); d.entries = desc; - gunzip_read(stream, desc, d.entry_ct * sizeof(desc[0])); - gunzip_close(stream); + gzread(stream, desc, d.entry_ct * sizeof(desc[0])); + gzclose(stream);
cfo.data = font; cfo.op = KD_FONT_OP_SET; @@ -119,12 +119,12 @@ int loadKeymap(gzFile stream) { if (major(sb.st_rdev) == 3 || major(sb.st_rdev) == 136) return 0;
- if (gunzip_read(stream, &magic, sizeof(magic)) != sizeof(magic)) + if (gzread(stream, &magic, sizeof(magic)) != sizeof(magic)) return -EIO;
if (magic != KMAP_MAGIC) return -EINVAL;
- if (gunzip_read(stream, keymaps, sizeof(keymaps)) != sizeof(keymaps)) + if (gzread(stream, keymaps, sizeof(keymaps)) != sizeof(keymaps)) return -EINVAL;
console = open("/dev/tty0", O_RDWR); @@ -134,7 +134,7 @@ int loadKeymap(gzFile stream) { for (kmap = 0; kmap < MAX_NR_KEYMAPS; kmap++) { if (!keymaps[kmap]) continue;
- if (gunzip_read(stream, keymap, sizeof(keymap)) != sizeof(keymap)) { + if (gzread(stream, keymap, sizeof(keymap)) != sizeof(keymap)) { close(console); return -EIO; } @@ -166,18 +166,18 @@ int isysLoadKeymap(char * keymap) { char buf[16384]; /* I hope this is big enough */ int i;
- f = gunzip_open("/etc/keymaps.gz"); + f = gzopen("/etc/keymaps.gz", "r"); if (!f) return -EACCES;
- if (gunzip_read(f, &hdr, sizeof(hdr)) != sizeof(hdr)) { - gunzip_close(f); + if (gzread(f, &hdr, sizeof(hdr)) != sizeof(hdr)) { + gzclose(f); return -EINVAL; }
i = hdr.numEntries * sizeof(*infoTable); infoTable = alloca(i); - if (gunzip_read(f, infoTable, i) != i) { - gunzip_close(f); + if (gzread(f, infoTable, i) != i) { + gzclose(f); return -EIO; }
@@ -188,20 +188,20 @@ int isysLoadKeymap(char * keymap) { }
if (num == -1) { - gunzip_close(f); + gzclose(f); return -ENOENT; }
for (i = 0; i < num; i++) { - if (gunzip_read(f, buf, infoTable[i].size) != infoTable[i].size) { - gunzip_close(f); + if (gzread(f, buf, infoTable[i].size) != infoTable[i].size) { + gzclose(f); return -EIO; } }
rc = loadKeymap(f);
- gunzip_close(f); + gzclose(f);
return rc; }
Ack. This looks good.
-- Martin Sivák msivak@redhat.com Red Hat Czech Anaconda team / Brno, CZ
----- "David Cantrell" dcantrell@redhat.com wrote:
The stubs.h header file does not exist anymore. Replace gunzip_* macro usage with the real zlib function names.
loader/kbd.c | 17 ++++++++--------- loader/lang.c | 6 ++---- loader/loader.c | 1 - pyanaconda/isys/lang.c | 38 +++++++++++++++++++------------------- 4 files changed, 29 insertions(+), 33 deletions(-)
diff --git a/loader/kbd.c b/loader/kbd.c index c943be6..34cb29f 100644 --- a/loader/kbd.c +++ b/loader/kbd.c @@ -34,7 +34,6 @@ #include "lang.h" #include "windows.h"
-#include "../pyanaconda/isys/stubs.h" #include "../pyanaconda/isys/lang.h" #include "../pyanaconda/isys/log.h"
@@ -79,15 +78,15 @@ int chooseKeyboard(struct loaderData_s * loaderData, char ** kbdtypep) { if (!defkbd) defkbd = "us";
- f = gunzip_open("/etc/keymaps.gz");
- f = gzopen("/etc/keymaps.gz", "r"); if (!f) { errorWindow("cannot open /etc/keymaps.gz: %s"); return LOADER_ERROR; }
- if (gunzip_read(f, &hdr, sizeof(hdr)) != sizeof(hdr)) {
- if (gzread(f, &hdr, sizeof(hdr)) != sizeof(hdr)) { errorWindow("failed to read keymaps header: %s");
- gunzip_close(f);
- gzclose(f); return LOADER_ERROR; }
@@ -95,9 +94,9 @@ int chooseKeyboard(struct loaderData_s * loaderData, char ** kbdtypep) {
i = hdr.numEntries * sizeof(*infoTable); infoTable = alloca(i);
- if (gunzip_read(f, infoTable, i) != i) {
- if (gzread(f, infoTable, i) != i) { errorWindow("failed to read keymap information: %s");
- gunzip_close(f);
- gzclose(f); return LOADER_ERROR; }
@@ -128,10 +127,10 @@ int chooseKeyboard(struct loaderData_s * loaderData, char ** kbdtypep) { rc = 0;
for (i = 0; i < num; i++) {
- if (gunzip_read(f, buf, infoTable[i].size) != infoTable[i].size) {
- if (gzread(f, buf, infoTable[i].size) != infoTable[i].size) { logMessage(ERROR, "error reading %d bytes from file: %m", infoTable[i].size);
gunzip_close(f);
} }gzclose(f); rc = LOADER_ERROR;@@ -145,7 +144,7 @@ int chooseKeyboard(struct loaderData_s * loaderData, char ** kbdtypep) { if (rc != 0) rc = LOADER_ERROR; else
gunzip_close(f);
gzclose(f);loaderData->kbd = strdup(infoTable[num].name);
diff --git a/loader/lang.c b/loader/lang.c index 0bb351e..035fb75 100644 --- a/loader/lang.c +++ b/loader/lang.c @@ -40,8 +40,6 @@ #include "loadermisc.h" #include "windows.h"
-#include "../pyanaconda/isys/stubs.h" -#include "../pyanaconda/isys/cpio.h" #include "../pyanaconda/isys/lang.h" #include "../pyanaconda/isys/isys.h" #include "../pyanaconda/isys/log.h" @@ -161,7 +159,7 @@ void loadLanguage (char * file) { sprintf(filename, "/etc/loader.tr"); }
- stream = gunzip_open(file);
stream = gzopen(file, "r");
if (!stream) { newtWinMessage("Error", "OK", "Translation for %s is not
available. " @@ -172,7 +170,7 @@ void loadLanguage (char * file) { sprintf(filename, "%s.tr", key);
rc = installCpioFile(stream, filename, "/tmp/translation", 1);
- gunzip_close(stream);
gzclose(stream);
if (rc || access("/tmp/translation", R_OK)) { newtWinMessage("Error", "OK", "Cannot get translation file
%s.\n", diff --git a/loader/loader.c b/loader/loader.c index f9d5483..88d7a7a 100644 --- a/loader/loader.c +++ b/loader/loader.c @@ -96,7 +96,6 @@
#include "../pyanaconda/isys/imount.h" #include "../pyanaconda/isys/isys.h" -#include "../pyanaconda/isys/stubs.h" #include "../pyanaconda/isys/lang.h" #include "../pyanaconda/isys/eddsupport.h" #include "../pyanaconda/isys/log.h" diff --git a/pyanaconda/isys/lang.c b/pyanaconda/isys/lang.c index 19b98ea..0fa3d3c 100644 --- a/pyanaconda/isys/lang.c +++ b/pyanaconda/isys/lang.c @@ -53,17 +53,17 @@ int isysLoadFont(void) { #if defined (__s390__) || defined (__s390x__) return 0; #endif
- stream = gunzip_open("/etc/screenfont.gz");
- stream = gzopen("/etc/screenfont.gz", "r"); if (!stream) return -EACCES;
- gunzip_read(stream, &cfo, sizeof(cfo));
- gunzip_read(stream, font, sizeof(font));
- gunzip_read(stream, map, sizeof(map));
- gunzip_read(stream, &d.entry_ct, sizeof(d.entry_ct));
- gzread(stream, &cfo, sizeof(cfo));
- gzread(stream, font, sizeof(font));
- gzread(stream, map, sizeof(map));
- gzread(stream, &d.entry_ct, sizeof(d.entry_ct)); d.entries = desc;
- gunzip_read(stream, desc, d.entry_ct * sizeof(desc[0]));
- gunzip_close(stream);
gzread(stream, desc, d.entry_ct * sizeof(desc[0]));
gzclose(stream);
cfo.data = font; cfo.op = KD_FONT_OP_SET;
@@ -119,12 +119,12 @@ int loadKeymap(gzFile stream) { if (major(sb.st_rdev) == 3 || major(sb.st_rdev) == 136) return 0;
- if (gunzip_read(stream, &magic, sizeof(magic)) != sizeof(magic))
if (gzread(stream, &magic, sizeof(magic)) != sizeof(magic)) return -EIO;
if (magic != KMAP_MAGIC) return -EINVAL;
- if (gunzip_read(stream, keymaps, sizeof(keymaps)) !=
sizeof(keymaps))
if (gzread(stream, keymaps, sizeof(keymaps)) != sizeof(keymaps)) return -EINVAL;
console = open("/dev/tty0", O_RDWR);
@@ -134,7 +134,7 @@ int loadKeymap(gzFile stream) { for (kmap = 0; kmap < MAX_NR_KEYMAPS; kmap++) { if (!keymaps[kmap]) continue;
- if (gunzip_read(stream, keymap, sizeof(keymap)) != sizeof(keymap))
{
- if (gzread(stream, keymap, sizeof(keymap)) != sizeof(keymap)) { close(console); return -EIO; }
@@ -166,18 +166,18 @@ int isysLoadKeymap(char * keymap) { char buf[16384]; /* I hope this is big enough */ int i;
- f = gunzip_open("/etc/keymaps.gz");
- f = gzopen("/etc/keymaps.gz", "r"); if (!f) return -EACCES;
- if (gunzip_read(f, &hdr, sizeof(hdr)) != sizeof(hdr)) {
- gunzip_close(f);
if (gzread(f, &hdr, sizeof(hdr)) != sizeof(hdr)) {
gzclose(f); return -EINVAL; }
i = hdr.numEntries * sizeof(*infoTable); infoTable = alloca(i);
- if (gunzip_read(f, infoTable, i) != i) {
- gunzip_close(f);
- if (gzread(f, infoTable, i) != i) {
- gzclose(f); return -EIO; }
@@ -188,20 +188,20 @@ int isysLoadKeymap(char * keymap) { }
if (num == -1) {
- gunzip_close(f);
gzclose(f); return -ENOENT; }
for (i = 0; i < num; i++) {
- if (gunzip_read(f, buf, infoTable[i].size) != infoTable[i].size) {
gunzip_close(f);
if (gzread(f, buf, infoTable[i].size) != infoTable[i].size) {
gzclose(f); return -EIO;} }
rc = loadKeymap(f);
- gunzip_close(f);
gzclose(f);
return rc;
}
1.7.2.3
Anaconda-devel-list mailing list Anaconda-devel-list@redhat.com https://www.redhat.com/mailman/listinfo/anaconda-devel-list
Replace uses of mkdirChain() with g_mkdir_with_parents() and remove the existing mkdirChain() code from isys/imount.* --- loader/driverdisk.c | 15 +++++++++--- loader/loader.c | 6 +++- loader/method.c | 6 +++- pyanaconda/isys/imount.c | 52 +-------------------------------------------- pyanaconda/isys/imount.h | 1 - 5 files changed, 21 insertions(+), 59 deletions(-)
diff --git a/loader/driverdisk.c b/loader/driverdisk.c index 2688c82..9b4c710 100644 --- a/loader/driverdisk.c +++ b/loader/driverdisk.c @@ -265,9 +265,15 @@ static int loadDriverDisk(struct loaderData_s *loaderData, char *mntpt) { logMessage(DEBUGLVL, "Kernel version: %s", kernelver);
sprintf(file, DD_RPMDIR_TEMPLATE, disknum); - mkdirChain(file); - mkdirChain(DD_MODULES); - mkdirChain(DD_FIRMWARE); + + if (g_mkdir_with_parents(file, 0755) == -1) + logMessage(ERROR, "mkdir error on %s: %m", file); + + if (g_mkdir_with_parents(DD_MODULES, 0755) == -1) + logMessage(ERROR, "mkdir error on %s: %m", DD_MODULES); + + if (g_mkdir_with_parents(DD_FIRMWARE, 0755) == -1) + logMessage(ERROR, "mkdir error on %s: %m", DD_FIRMWARE);
if (!FL_CMDLINE(flags)) { startNewt(); @@ -293,7 +299,8 @@ static int loadDriverDisk(struct loaderData_s *loaderData, char *mntpt) {
/* ensure updates directory exists */ sprintf(file, "/lib/modules/%s/updates", kernelver); - mkdirChain(file); + if (g_mkdir_with_parents(file, 0755) == -1) + logMessage(ERROR, "mkdir error on %s: %m", file);
/* make sure driver update are referenced from system module dir but from a different subdir, initrd overlays use the main diff --git a/loader/loader.c b/loader/loader.c index 88d7a7a..50daeb0 100644 --- a/loader/loader.c +++ b/loader/loader.c @@ -2146,8 +2146,10 @@ int main(int argc, char ** argv) {
/* make sure /tmp/updates exists so that magic in anaconda to */ /* symlink rhpl/ will work */ - if (access("/tmp/updates", F_OK)) - mkdirChain("/tmp/updates"); + if (access("/tmp/updates", F_OK)) { + if (g_mkdir_with_parents("/tmp/updates", 0755) == -1) + logMessage(ERROR, "mkdir error on /tmp/updates: %m"); + }
add_fw_search_dir(&loaderData, "/tmp/updates/firmware"); add_fw_search_dir(&loaderData, "/tmp/product/firmware"); diff --git a/loader/method.c b/loader/method.c index 844048f..d84a2e8 100644 --- a/loader/method.c +++ b/loader/method.c @@ -313,8 +313,10 @@ int unpackCpioBall(char * ballPath, char * rootDir) { if (access(ballPath, R_OK)) return 1;
- if (access(rootDir, R_OK)) - mkdirChain(rootDir); + if (access(rootDir, R_OK)) { + if (g_mkdir_with_parents(rootDir, 0755) == -1) + logMessage(ERROR, "mkdir error on %s: %m", rootDir); + }
buf = (char *)malloc(PATH_MAX); cwd = getcwd(buf, PATH_MAX); diff --git a/pyanaconda/isys/imount.c b/pyanaconda/isys/imount.c index ed0f5a7..39265a0 100644 --- a/pyanaconda/isys/imount.c +++ b/pyanaconda/isys/imount.c @@ -27,14 +27,13 @@ #include <sys/types.h> #include <sys/wait.h> #include <unistd.h> +#include <glib.h>
#include "imount.h" #include "log.h"
#define _(foo) foo
-static int mkdirIfNone(char * directory); - static int readFD(int fd, char **buf) { char *p; size_t size = 4096; @@ -88,7 +87,7 @@ int mountCommandWrapper(int mode, char *dev, char *where, char *fs, case IMOUNT_MODE_MOUNT: case IMOUNT_MODE_BIND: cmd = "/bin/mount"; - if (mkdirChain(where)) + if (g_mkdir_with_parents(where, 0755)) return IMOUNT_ERR_ERRNO; break; case IMOUNT_MODE_UMOUNT: @@ -264,31 +263,6 @@ int doPwUmount(char *where, char **err) { NULL, where, NULL, NULL, err); }
-int mkdirChain(char * origChain) { - char * chain; - char * chptr; - - chain = alloca(strlen(origChain) + 1); - strcpy(chain, origChain); - chptr = chain; - - while ((chptr = strchr(chptr, '/'))) { - *chptr = '\0'; - if (mkdirIfNone(chain)) { - *chptr = '/'; - return IMOUNT_ERR_ERRNO; - } - - *chptr = '/'; - chptr++; - } - - if (mkdirIfNone(chain)) - return IMOUNT_ERR_ERRNO; - - return 0; -} - /* Returns true iff it is possible that the mount command that have returned * 'errno' might succeed at a later time (think e.g. not yet initialized USB * device, etc.) */ @@ -304,25 +278,3 @@ int mountMightSucceedLater(int mountRc) } return rc; } - -static int mkdirIfNone(char * directory) { - int rc, mkerr; - char * chptr; - - /* If the file exists it *better* be a directory -- I'm not going to - actually check or anything */ - if (!access(directory, X_OK)) return 0; - - /* if the path is '/' we get ENOFILE not found" from mkdir, rather - then EEXIST which is weird */ - for (chptr = directory; *chptr; chptr++) - if (*chptr != '/') break; - if (!*chptr) return 0; - - rc = mkdir(directory, 0755); - mkerr = errno; - - if (!rc || mkerr == EEXIST) return 0; - - return IMOUNT_ERR_ERRNO; -} diff --git a/pyanaconda/isys/imount.h b/pyanaconda/isys/imount.h index d1b7cf3..3ce6387 100644 --- a/pyanaconda/isys/imount.h +++ b/pyanaconda/isys/imount.h @@ -44,7 +44,6 @@ int doBindMount(char* path, char *where, char **err); int doPwMount(char *dev, char *where, char *fs, char *options, char **err); int doPwUmount(char *where, char **err); -int mkdirChain(char * origChain); int mountMightSucceedLater(int mountRc);
#endif
Ack.
-- Martin Sivák msivak@redhat.com Red Hat Czech Anaconda team / Brno, CZ
----- "David Cantrell" dcantrell@redhat.com wrote:
Replace uses of mkdirChain() with g_mkdir_with_parents() and remove the existing mkdirChain() code from isys/imount.*
loader/driverdisk.c | 15 +++++++++--- loader/loader.c | 6 +++- loader/method.c | 6 +++- pyanaconda/isys/imount.c | 52 +-------------------------------------------- pyanaconda/isys/imount.h | 1 - 5 files changed, 21 insertions(+), 59 deletions(-)
diff --git a/loader/driverdisk.c b/loader/driverdisk.c index 2688c82..9b4c710 100644 --- a/loader/driverdisk.c +++ b/loader/driverdisk.c @@ -265,9 +265,15 @@ static int loadDriverDisk(struct loaderData_s *loaderData, char *mntpt) { logMessage(DEBUGLVL, "Kernel version: %s", kernelver);
sprintf(file, DD_RPMDIR_TEMPLATE, disknum);
- mkdirChain(file);
- mkdirChain(DD_MODULES);
- mkdirChain(DD_FIRMWARE);
if (g_mkdir_with_parents(file, 0755) == -1)
logMessage(ERROR, "mkdir error on %s: %m", file);if (g_mkdir_with_parents(DD_MODULES, 0755) == -1)
logMessage(ERROR, "mkdir error on %s: %m", DD_MODULES);if (g_mkdir_with_parents(DD_FIRMWARE, 0755) == -1)
logMessage(ERROR, "mkdir error on %s: %m", DD_FIRMWARE);if (!FL_CMDLINE(flags)) { startNewt();
@@ -293,7 +299,8 @@ static int loadDriverDisk(struct loaderData_s *loaderData, char *mntpt) {
/* ensure updates directory exists */ sprintf(file, "/lib/modules/%s/updates", kernelver);
- mkdirChain(file);
if (g_mkdir_with_parents(file, 0755) == -1)
logMessage(ERROR, "mkdir error on %s: %m", file);/* make sure driver update are referenced from system module dir but from a different subdir, initrd overlays use the main
diff --git a/loader/loader.c b/loader/loader.c index 88d7a7a..50daeb0 100644 --- a/loader/loader.c +++ b/loader/loader.c @@ -2146,8 +2146,10 @@ int main(int argc, char ** argv) {
/* make sure /tmp/updates exists so that magic in anaconda to */ /* symlink rhpl/ will work */
- if (access("/tmp/updates", F_OK))
mkdirChain("/tmp/updates");
if (access("/tmp/updates", F_OK)) {
if (g_mkdir_with_parents("/tmp/updates", 0755) == -1)logMessage(ERROR, "mkdir error on /tmp/updates: %m");}
add_fw_search_dir(&loaderData, "/tmp/updates/firmware"); add_fw_search_dir(&loaderData, "/tmp/product/firmware");
diff --git a/loader/method.c b/loader/method.c index 844048f..d84a2e8 100644 --- a/loader/method.c +++ b/loader/method.c @@ -313,8 +313,10 @@ int unpackCpioBall(char * ballPath, char * rootDir) { if (access(ballPath, R_OK)) return 1;
- if (access(rootDir, R_OK))
mkdirChain(rootDir);
if (access(rootDir, R_OK)) {
if (g_mkdir_with_parents(rootDir, 0755) == -1)logMessage(ERROR, "mkdir error on %s: %m", rootDir);}
buf = (char *)malloc(PATH_MAX); cwd = getcwd(buf, PATH_MAX);
diff --git a/pyanaconda/isys/imount.c b/pyanaconda/isys/imount.c index ed0f5a7..39265a0 100644 --- a/pyanaconda/isys/imount.c +++ b/pyanaconda/isys/imount.c @@ -27,14 +27,13 @@ #include <sys/types.h> #include <sys/wait.h> #include <unistd.h> +#include <glib.h>
#include "imount.h" #include "log.h"
#define _(foo) foo
-static int mkdirIfNone(char * directory);
static int readFD(int fd, char **buf) { char *p; size_t size = 4096; @@ -88,7 +87,7 @@ int mountCommandWrapper(int mode, char *dev, char *where, char *fs, case IMOUNT_MODE_MOUNT: case IMOUNT_MODE_BIND: cmd = "/bin/mount";
if (mkdirChain(where))
case IMOUNT_MODE_UMOUNT:if (g_mkdir_with_parents(where, 0755)) return IMOUNT_ERR_ERRNO; break;@@ -264,31 +263,6 @@ int doPwUmount(char *where, char **err) { NULL, where, NULL, NULL, err); }
-int mkdirChain(char * origChain) {
- char * chain;
- char * chptr;
- chain = alloca(strlen(origChain) + 1);
- strcpy(chain, origChain);
- chptr = chain;
- while ((chptr = strchr(chptr, '/'))) {
- *chptr = '\0';
- if (mkdirIfNone(chain)) {
*chptr = '/';return IMOUNT_ERR_ERRNO;- }
- *chptr = '/';
- chptr++;
- }
- if (mkdirIfNone(chain))
- return IMOUNT_ERR_ERRNO;
- return 0;
-}
/* Returns true iff it is possible that the mount command that have returned
- 'errno' might succeed at a later time (think e.g. not yet
initialized USB
- device, etc.) */
@@ -304,25 +278,3 @@ int mountMightSucceedLater(int mountRc) } return rc; }
-static int mkdirIfNone(char * directory) {
- int rc, mkerr;
- char * chptr;
- /* If the file exists it *better* be a directory -- I'm not going
to
actually check or anything */- if (!access(directory, X_OK)) return 0;
- /* if the path is '/' we get ENOFILE not found" from mkdir,
rather
then EEXIST which is weird */- for (chptr = directory; *chptr; chptr++)
if (*chptr != '/') break;- if (!*chptr) return 0;
- rc = mkdir(directory, 0755);
- mkerr = errno;
- if (!rc || mkerr == EEXIST) return 0;
- return IMOUNT_ERR_ERRNO;
-} diff --git a/pyanaconda/isys/imount.h b/pyanaconda/isys/imount.h index d1b7cf3..3ce6387 100644 --- a/pyanaconda/isys/imount.h +++ b/pyanaconda/isys/imount.h @@ -44,7 +44,6 @@ int doBindMount(char* path, char *where, char **err); int doPwMount(char *dev, char *where, char *fs, char *options, char **err); int doPwUmount(char *where, char **err); -int mkdirChain(char * origChain); int mountMightSucceedLater(int mountRc);
#endif
1.7.2.3
Anaconda-devel-list mailing list Anaconda-devel-list@redhat.com https://www.redhat.com/mailman/listinfo/anaconda-devel-list
Ack,
just one comment:
On 11/02/2010 09:44 PM, David Cantrell wrote:
- if (g_mkdir_with_parents(file, 0755) == -1)
logMessage(ERROR, "mkdir error on %s: %m", file);- if (g_mkdir_with_parents(DD_MODULES, 0755) == -1)
logMessage(ERROR, "mkdir error on %s: %m", DD_MODULES);
Maybe we should have a function to call instead of g_mkdir_with_parents that would both call g_mkdir_with_parents() and then do the logging. Would save us some lines and ifs.
Ales
Created some helper functions for loader's interaction with libarchive. There are 3 functions currently:
1) A function to initialize a new archive object 2) A function to extract all archive members to a specific destination (if NULL, extract to current directory) 3) A function wrapping #1 and #2 to extract a compressed archive file --- loader/Makefile.am | 3 +- loader/unpack.c | 132 ++++++++++++++++++++++++++++++++++++++++++++++++++++ loader/unpack.h | 31 ++++++++++++ 3 files changed, 165 insertions(+), 1 deletions(-) create mode 100644 loader/unpack.c create mode 100644 loader/unpack.h
diff --git a/loader/Makefile.am b/loader/Makefile.am index a11b569..336c442 100644 --- a/loader/Makefile.am +++ b/loader/Makefile.am @@ -53,7 +53,8 @@ loader_SOURCES = loader.c copy.c moduleinfo.c loadermisc.c \ selinux.c mediacheck.c kickstart.c driverselect.c \ getparts.c dirbrowser.c fwloader.c ibft.c hardware.c \ method.c cdinstall.c hdinstall.c nfsinstall.c \ - urlinstall.c net.c urls.c rpmextract.c readvars.c + urlinstall.c net.c urls.c rpmextract.c readvars.c \ + unpack.c
init_CFLAGS = $(COMMON_CFLAGS) $(GLIB_CFLAGS) init_LDADD = $(GLIB_LIBS) $(top_srcdir)/pyanaconda/isys/libisys.la diff --git a/loader/unpack.c b/loader/unpack.c new file mode 100644 index 0000000..0721a2e --- /dev/null +++ b/loader/unpack.c @@ -0,0 +1,132 @@ +/* + * unpack.c - libarchive helper functions + * + * Copyright (C) 2010 Red Hat, Inc. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see http://www.gnu.org/licenses/. + * + * Author(s): David Cantrell dcantrell@redhat.com + */ + +#include <limits.h> +#include <unistd.h> + +#include <archive.h> +#include <archive_entry.h> +#include <glib.h> + +#include "../pyanaconda/isys/log.h" + +/* + * Initialize libarchive object for unpacking an archive file. + * Args: + * struct archive **a The archive object to use. + * Returns: ARCHIVE_OK on success, ARCHIVE_* on failure + */ +int unpack_init(struct archive **a) { + int r = ARCHIVE_OK; + + if ((*a = archive_read_new()) == NULL) + return ARCHIVE_FATAL; + + if ((r = archive_read_support_compression_all(*a)) != ARCHIVE_OK) + return r; + + if ((r = archive_read_support_format_all(*a)) != ARCHIVE_OK) + return r; + + return r; +} + +/* + * Extract all of the archive members of the specified archive + * object. If dest is not NULL, extract archive members to that + * directory. If dest is not NULL and does not exist as a directory, + * create it first. + */ +void unpack_members(struct archive *a, char *dest) { + int restore = 0; + char prevcwd[PATH_MAX]; + struct archive_entry *e = NULL; + + if (getcwd(prevcwd, PATH_MAX) == NULL) + logMessage(ERROR, "unable to getcwd() (%s:%d): %m", __func__, + __LINE__); + else + restore = 1; + + if (dest != NULL && access(dest, R_OK|W_OK|X_OK)) { + if (g_mkdir_with_parents(dest, 0755) == -1) + logMessage(ERROR, "unable to mkdir %s (%s:%d): %m", + dest, __func__, __LINE__); + } else if (chdir(dest) == -1) { + logMessage(ERROR, "unable to chdir %s (%s:%d): %m", + dest, __func__, __LINE__); + } + + while (archive_read_next_header(a, &e) == ARCHIVE_OK) { + if (archive_read_extract(a, e, 0) != ARCHIVE_OK) + logMessage(ERROR, "error unpacking %s (%s:%d): %s", + archive_entry_pathname(e), __func__, __LINE__, + archive_error_string(a)); + } + + if (restore && chdir(prevcwd) == -1) + logMessage(ERROR, "unable to chdir %s (%s:%d): %m", + dest, __func__, __LINE__); + + return; +} + +/* + * Extract an archive (optionally compressed). + * Args: + * filename Full path to archive to unpack. + * dest Directory to unpack in, or NULL for current dir. + * Returns ARCHIVE_OK on success, or appropriate ARCHIVE_* value + * on failure (see /usr/include/archive.h). + */ +int unpack_archive_file(char *filename, char *dest) { + int rc = 0; + struct archive *a = NULL; + + if (filename == NULL || access(filename, R_OK) == -1) { + logMessage(ERROR, "unable to read %s (%s:%d): %m", + filename, __func__, __LINE__); + return ARCHIVE_FATAL; + } + + if ((rc = unpack_init(&a)) != ARCHIVE_OK) { + logMessage(ERROR, "unable to initialize libarchive"); + return rc; + } + + rc = archive_read_open_filename(a, filename, + ARCHIVE_DEFAULT_BYTES_PER_BLOCK); + if (rc != ARCHIVE_OK) { + logMessage(ERROR, "error opening %s (%s:%d): %s", + filename, __func__, __LINE__, + archive_error_string(a)); + return rc; + } + + unpack_members(a, dest); + + if ((rc = archive_read_finish(a)) != ARCHIVE_OK) + logMessage(ERROR, "error closing %s (%s:%d): %s", + filename, __func__, __LINE__, + archive_error_string(a)); + + return rc; +} diff --git a/loader/unpack.h b/loader/unpack.h new file mode 100644 index 0000000..c8c1b5e --- /dev/null +++ b/loader/unpack.h @@ -0,0 +1,31 @@ +/* + * unpack.h - libarchive helper functions + * + * Copyright (C) 2010 Red Hat, Inc. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see http://www.gnu.org/licenses/. + * + * Author(s): David Cantrell dcantrell@redhat.com + */ + +#ifndef UNPACK_H +#define UNPACK_H + +#include <archive.h> + +int unpack_init(struct archive **); +void unpack_members(struct archive *, char *); +int unpack_archive_file(char *, char *); + +#endif
Do we need the old mappings for unpacking only listed files with specific set of permissions? If not, this is Ack. This was the only question I was thinking about when playing with this a month ago..
-- Martin Sivák msivak@redhat.com Red Hat Czech Anaconda team / Brno, CZ
----- "David Cantrell" dcantrell@redhat.com wrote:
Created some helper functions for loader's interaction with libarchive. There are 3 functions currently:
- A function to initialize a new archive object
- A function to extract all archive members to a specific destination (if NULL, extract to current directory)
- A function wrapping #1 and #2 to extract a compressed archive file
loader/Makefile.am | 3 +- loader/unpack.c | 132 ++++++++++++++++++++++++++++++++++++++++++++++++++++ loader/unpack.h | 31 ++++++++++++ 3 files changed, 165 insertions(+), 1 deletions(-) create mode 100644 loader/unpack.c create mode 100644 loader/unpack.h
diff --git a/loader/Makefile.am b/loader/Makefile.am index a11b569..336c442 100644 --- a/loader/Makefile.am +++ b/loader/Makefile.am @@ -53,7 +53,8 @@ loader_SOURCES = loader.c copy.c moduleinfo.c loadermisc.c \ selinux.c mediacheck.c kickstart.c driverselect.c \ getparts.c dirbrowser.c fwloader.c ibft.c hardware.c \ method.c cdinstall.c hdinstall.c nfsinstall.c \
urlinstall.c net.c urls.c rpmextract.creadvars.c
urlinstall.c net.c urls.c rpmextract.creadvars.c \
unpack.cinit_CFLAGS = $(COMMON_CFLAGS) $(GLIB_CFLAGS) init_LDADD = $(GLIB_LIBS) $(top_srcdir)/pyanaconda/isys/libisys.la diff --git a/loader/unpack.c b/loader/unpack.c new file mode 100644 index 0000000..0721a2e --- /dev/null +++ b/loader/unpack.c @@ -0,0 +1,132 @@ +/*
- unpack.c - libarchive helper functions
- Copyright (C) 2010 Red Hat, Inc.
- This program is free software; you can redistribute it and/or
modify
- it under the terms of the GNU General Public License as published
by
- the Free Software Foundation; either version 2 of the License, or
- (at your option) any later version.
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
- You should have received a copy of the GNU General Public License
- along with this program. If not, see
- Author(s): David Cantrell dcantrell@redhat.com
- */
+#include <limits.h> +#include <unistd.h>
+#include <archive.h> +#include <archive_entry.h> +#include <glib.h>
+#include "../pyanaconda/isys/log.h"
+/*
- Initialize libarchive object for unpacking an archive file.
- Args:
struct archive **a The archive object to use.
- Returns: ARCHIVE_OK on success, ARCHIVE_* on failure
- */
+int unpack_init(struct archive **a) {
- int r = ARCHIVE_OK;
- if ((*a = archive_read_new()) == NULL)
return ARCHIVE_FATAL;- if ((r = archive_read_support_compression_all(*a)) !=
ARCHIVE_OK)
return r;- if ((r = archive_read_support_format_all(*a)) != ARCHIVE_OK)
return r;- return r;
+}
+/*
- Extract all of the archive members of the specified archive
- object. If dest is not NULL, extract archive members to that
- directory. If dest is not NULL and does not exist as a
directory,
- create it first.
- */
+void unpack_members(struct archive *a, char *dest) {
- int restore = 0;
- char prevcwd[PATH_MAX];
- struct archive_entry *e = NULL;
- if (getcwd(prevcwd, PATH_MAX) == NULL)
logMessage(ERROR, "unable to getcwd() (%s:%d): %m",__func__,
__LINE__);
- else
restore = 1;- if (dest != NULL && access(dest, R_OK|W_OK|X_OK)) {
if (g_mkdir_with_parents(dest, 0755) == -1)logMessage(ERROR, "unable to mkdir %s (%s:%d): %m",dest, __func__, __LINE__);- } else if (chdir(dest) == -1) {
logMessage(ERROR, "unable to chdir %s (%s:%d): %m",dest, __func__, __LINE__);- }
- while (archive_read_next_header(a, &e) == ARCHIVE_OK) {
if (archive_read_extract(a, e, 0) != ARCHIVE_OK)logMessage(ERROR, "error unpacking %s (%s:%d): %s",archive_entry_pathname(e), __func__,__LINE__,
archive_error_string(a));- }
- if (restore && chdir(prevcwd) == -1)
logMessage(ERROR, "unable to chdir %s (%s:%d): %m",dest, __func__, __LINE__);- return;
+}
+/*
- Extract an archive (optionally compressed).
- Args:
filename Full path to archive to unpack.
dest Directory to unpack in, or NULL for currentdir.
- Returns ARCHIVE_OK on success, or appropriate ARCHIVE_* value
- on failure (see /usr/include/archive.h).
- */
+int unpack_archive_file(char *filename, char *dest) {
- int rc = 0;
- struct archive *a = NULL;
- if (filename == NULL || access(filename, R_OK) == -1) {
logMessage(ERROR, "unable to read %s (%s:%d): %m",filename, __func__, __LINE__);return ARCHIVE_FATAL;- }
- if ((rc = unpack_init(&a)) != ARCHIVE_OK) {
logMessage(ERROR, "unable to initialize libarchive");return rc;- }
- rc = archive_read_open_filename(a, filename,
ARCHIVE_DEFAULT_BYTES_PER_BLOCK);
- if (rc != ARCHIVE_OK) {
logMessage(ERROR, "error opening %s (%s:%d): %s",filename, __func__, __LINE__,archive_error_string(a));return rc;- }
- unpack_members(a, dest);
- if ((rc = archive_read_finish(a)) != ARCHIVE_OK)
logMessage(ERROR, "error closing %s (%s:%d): %s",filename, __func__, __LINE__,archive_error_string(a));- return rc;
+} diff --git a/loader/unpack.h b/loader/unpack.h new file mode 100644 index 0000000..c8c1b5e --- /dev/null +++ b/loader/unpack.h @@ -0,0 +1,31 @@ +/*
- unpack.h - libarchive helper functions
- Copyright (C) 2010 Red Hat, Inc.
- This program is free software; you can redistribute it and/or
modify
- it under the terms of the GNU General Public License as published
by
- the Free Software Foundation; either version 2 of the License, or
- (at your option) any later version.
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
- You should have received a copy of the GNU General Public License
- along with this program. If not, see
- Author(s): David Cantrell dcantrell@redhat.com
- */
+#ifndef UNPACK_H +#define UNPACK_H
+#include <archive.h>
+int unpack_init(struct archive **); +void unpack_members(struct archive *, char *); +int unpack_archive_file(char *, char *);
+#endif
1.7.2.3
Anaconda-devel-list mailing list Anaconda-devel-list@redhat.com https://www.redhat.com/mailman/listinfo/anaconda-devel-list
+void unpack_members(struct archive *a, char *dest) {
- int restore = 0;
- char prevcwd[PATH_MAX];
- struct archive_entry *e = NULL;
- if (getcwd(prevcwd, PATH_MAX) == NULL)
logMessage(ERROR, "unable to getcwd() (%s:%d): %m", __func__,__LINE__);- else
restore = 1;- if (dest != NULL && access(dest, R_OK|W_OK|X_OK)) {
if (g_mkdir_with_parents(dest, 0755) == -1)logMessage(ERROR, "unable to mkdir %s (%s:%d): %m",dest, __func__, __LINE__);- } else if (chdir(dest) == -1) {
logMessage(ERROR, "unable to chdir %s (%s:%d): %m",dest, __func__, __LINE__);- }
If either of these things fail, you should return instead of blasting the archive members into wherever the current directory may be. Perhaps unpack_members should return a value to indicate this.
- Chris
Simplify the archive extraction loop in explodeRPM() by using the unpack.c helper functions. Add a new parameter to explodeRPM, the destination to unpack the archive to. This was previously handled by dlabelUnpackRPMDir() directly, but it made more sense to me to move it in to the libarchive unpack helper. --- loader/driverdisk.c | 24 +----------- loader/rpmextract.c | 106 ++++----------------------------------------------- loader/rpmextract.h | 3 +- 3 files changed, 11 insertions(+), 122 deletions(-)
diff --git a/loader/driverdisk.c b/loader/driverdisk.c index 9b4c710..c56f3e5 100644 --- a/loader/driverdisk.c +++ b/loader/driverdisk.c @@ -145,24 +145,9 @@ int globErrFunc(const char *epath, int eerrno)
int dlabelUnpackRPMDir(char* rpmdir, char* destination, char *kernelver) { - char *oldcwd; char *globpattern; int rc = 0;
- /* get current working directory */ - oldcwd = getcwd(NULL, 0); - if (!oldcwd) { - logMessage(ERROR, "getcwd() failed: %m"); - return 1; - } - - /* set the cwd to destination */ - if (chdir(destination)) { - logMessage(ERROR, "We weren't able to CWD to "%s": %m", destination); - free(oldcwd); - return 1; - } - checked_asprintf(&globpattern, "%s/*.rpm", rpmdir); glob_t globres; char** globitem; @@ -170,7 +155,7 @@ int dlabelUnpackRPMDir(char* rpmdir, char* destination, char *kernelver) /* iterate over all rpm files */ globitem = globres.gl_pathv; while (globres.gl_pathc>0 && globitem != NULL && *globitem != NULL) { - explodeRPM(*globitem, dlabelFilter, dlabelProvides, NULL, kernelver); + explodeRPM(*globitem, dlabelFilter, dlabelProvides, NULL, kernelver, destination); globitem++; } globfree(&globres); @@ -178,13 +163,6 @@ int dlabelUnpackRPMDir(char* rpmdir, char* destination, char *kernelver) } free(globpattern);
- /* restore CWD */ - if (chdir(oldcwd)) { - logMessage(WARNING, "We weren't able to restore CWD to "%s": %m", oldcwd); - } - - /* cleanup */ - free(oldcwd); return rc; }
diff --git a/loader/rpmextract.c b/loader/rpmextract.c index de803b8..3c8f564 100644 --- a/loader/rpmextract.c +++ b/loader/rpmextract.c @@ -38,6 +38,7 @@
#include "loader.h" #include "rpmextract.h" +#include "unpack.h"
#include "../pyanaconda/isys/log.h"
@@ -93,7 +94,8 @@ int explodeRPM(const char *source, filterfunc filter, dependencyfunc provides, dependencyfunc deps, - void* userptr) + void* userptr, + char *destination) { char buffer[BUFFERSIZE+1]; /* make space for trailing \0 */ FD_t fdi; @@ -102,7 +104,6 @@ int explodeRPM(const char *source, rpmRC rc; FD_t gzdi; struct archive *cpio; - struct archive_entry *cpio_entry; struct cpio_mydata cpio_mydata;
rpmts ts; @@ -235,17 +236,15 @@ int explodeRPM(const char *source, return EXIT_FAILURE; }
+ cpio_mydata.gzdi = gzdi; + cpio_mydata.buffer = buffer; + /* initialize cpio decompressor */ - cpio = archive_read_new(); - if (cpio==NULL) { + if (unpack_init(&cpio) != ARCHIVE_OK) { Fclose(gzdi); return -1; }
- cpio_mydata.gzdi = gzdi; - cpio_mydata.buffer = buffer; - archive_read_support_compression_all(cpio); - archive_read_support_format_all(cpio); rc = archive_read_open(cpio, &cpio_mydata, NULL, rpm_myread, rpm_myclose);
/* check the status of archive_open */ @@ -255,96 +254,7 @@ int explodeRPM(const char *source, }
/* read all files in cpio archive */ - while ((rc = archive_read_next_header(cpio, &cpio_entry)) == ARCHIVE_OK){ - const struct stat *fstat; - int64_t fsize; - const char* filename; - int needskip = 1; /* do we need to read the data to get to the next header? */ - int offset = 0; - int towrite = 0; - - filename = archive_entry_pathname(cpio_entry); - fstat = archive_entry_stat(cpio_entry); - fsize = archive_entry_size(cpio_entry); - - /* Strip leading slashes */ - while (filename[offset] == '/') - offset+=1; - - /* Strip leading ./ */ - while (filename[offset] == '.' && filename[offset+1] == '/') - offset+=2; - - /* Other file type - we do not care except special cases */ - if (!S_ISREG(fstat->st_mode)) - towrite = 1; - else - towrite = 2; - - if (filter && filter(filename+offset, fstat, userptr)) { - /* filter this file */ - towrite = 0; - } - - /* Create directories */ - char* dirname = strdup(filename+offset); - - /* If the dup fails, let's hope the dirs already exist */ - if (dirname){ - char* dirptr = dirname; - while (dirptr && *dirptr) { - dirptr = strchr(dirptr, '/'); - if (dirptr) { - *dirptr = 0; - mkdir(dirname, 0700); - *dirptr = '/'; - dirptr++; - } - } - free(dirname); - } - - /* Regular file */ - if (towrite>=2) { - FILE *fdout = fopen(filename+offset, "w"); - - if (fdout==NULL){ - rc = 33; - break; - } - - rc = archive_read_data_into_fd(cpio, fileno(fdout)); - if (rc!=ARCHIVE_OK) { - /* XXX We didn't get the file.. well.. */ - needskip = 0; - } else { - needskip = 0; - } - - fclose(fdout); - } - - /* symlink, we assume that the path contained in symlink - * is shorter than BUFFERSIZE */ - while (towrite && S_ISLNK(fstat->st_mode)) { - char symlinkbuffer[BUFFERSIZE-1]; - - needskip = 0; - if ((rc = archive_read_data(cpio, symlinkbuffer, fsize))!=ARCHIVE_OK) { - /* XXX We didn't get the file.. well.. */ - break; - } - - if (symlink(buffer, filename+offset)) { - logMessage(ERROR, "Failed to create symlink %s -> %s", filename+offset, buffer); - } - - break; - } - - if(needskip) - archive_read_data_skip(cpio); - } + unpack_members(cpio, destination);
rc = archive_read_finish(cpio); /* Also closes the RPM stream using callback */
diff --git a/loader/rpmextract.h b/loader/rpmextract.h index 20a5cc8..976047c 100644 --- a/loader/rpmextract.h +++ b/loader/rpmextract.h @@ -38,7 +38,8 @@ int explodeRPM(const char* file, filterfunc filter, dependencyfunc provides, dependencyfunc deps, - void* userptr); + void* userptr, + char *destination);
#endif
You removed the functionality of my filterfunc here. It was ment to prevent unpacking files which might overwrite something. It shouldn't happen with the current DD code, so I think we should be good here. But it might be a good idea to delete the agrument from the header too..
-- Martin Sivák msivak@redhat.com Red Hat Czech Anaconda team / Brno, CZ
----- "David Cantrell" dcantrell@redhat.com wrote:
Simplify the archive extraction loop in explodeRPM() by using the unpack.c helper functions. Add a new parameter to explodeRPM, the destination to unpack the archive to. This was previously handled by dlabelUnpackRPMDir() directly, but it made more sense to me to move it in to the libarchive unpack helper.
loader/driverdisk.c | 24 +----------- loader/rpmextract.c | 106 ++++----------------------------------------------- loader/rpmextract.h | 3 +- 3 files changed, 11 insertions(+), 122 deletions(-)
diff --git a/loader/driverdisk.c b/loader/driverdisk.c index 9b4c710..c56f3e5 100644 --- a/loader/driverdisk.c +++ b/loader/driverdisk.c @@ -145,24 +145,9 @@ int globErrFunc(const char *epath, int eerrno)
int dlabelUnpackRPMDir(char* rpmdir, char* destination, char *kernelver) {
char *oldcwd; char *globpattern; int rc = 0;
/* get current working directory */
oldcwd = getcwd(NULL, 0);
if (!oldcwd) {
logMessage(ERROR, "getcwd() failed: %m");return 1;}
/* set the cwd to destination */
if (chdir(destination)) {
logMessage(ERROR, "We weren't able to CWD to \"%s\": %m",destination);
free(oldcwd);return 1;- }
- checked_asprintf(&globpattern, "%s/*.rpm", rpmdir); glob_t globres; char** globitem;
@@ -170,7 +155,7 @@ int dlabelUnpackRPMDir(char* rpmdir, char* destination, char *kernelver) /* iterate over all rpm files */ globitem = globres.gl_pathv; while (globres.gl_pathc>0 && globitem != NULL && *globitem != NULL) {
explodeRPM(*globitem, dlabelFilter, dlabelProvides, NULL,kernelver);
explodeRPM(*globitem, dlabelFilter, dlabelProvides, NULL,kernelver, destination); globitem++; } globfree(&globres); @@ -178,13 +163,6 @@ int dlabelUnpackRPMDir(char* rpmdir, char* destination, char *kernelver) } free(globpattern);
- /* restore CWD */
- if (chdir(oldcwd)) {
logMessage(WARNING, "We weren't able to restore CWD to"%s": %m", oldcwd);
- }
- /* cleanup */
- free(oldcwd); return rc;
}
diff --git a/loader/rpmextract.c b/loader/rpmextract.c index de803b8..3c8f564 100644 --- a/loader/rpmextract.c +++ b/loader/rpmextract.c @@ -38,6 +38,7 @@
#include "loader.h" #include "rpmextract.h" +#include "unpack.h"
#include "../pyanaconda/isys/log.h"
@@ -93,7 +94,8 @@ int explodeRPM(const char *source, filterfunc filter, dependencyfunc provides, dependencyfunc deps,
void* userptr)
void* userptr,char *destination){ char buffer[BUFFERSIZE+1]; /* make space for trailing \0 */ FD_t fdi; @@ -102,7 +104,6 @@ int explodeRPM(const char *source, rpmRC rc; FD_t gzdi; struct archive *cpio;
struct archive_entry *cpio_entry; struct cpio_mydata cpio_mydata;
rpmts ts;
@@ -235,17 +236,15 @@ int explodeRPM(const char *source, return EXIT_FAILURE; }
- cpio_mydata.gzdi = gzdi;
- cpio_mydata.buffer = buffer;
- /* initialize cpio decompressor */
- cpio = archive_read_new();
- if (cpio==NULL) {
- if (unpack_init(&cpio) != ARCHIVE_OK) { Fclose(gzdi); return -1; }
- cpio_mydata.gzdi = gzdi;
- cpio_mydata.buffer = buffer;
- archive_read_support_compression_all(cpio);
- archive_read_support_format_all(cpio); rc = archive_read_open(cpio, &cpio_mydata, NULL, rpm_myread,
rpm_myclose);
/* check the status of archive_open */@@ -255,96 +254,7 @@ int explodeRPM(const char *source, }
/* read all files in cpio archive */
- while ((rc = archive_read_next_header(cpio, &cpio_entry)) ==
ARCHIVE_OK){
const struct stat *fstat;int64_t fsize;const char* filename;int needskip = 1; /* do we need to read the data to get tothe next header? */
int offset = 0;int towrite = 0;filename = archive_entry_pathname(cpio_entry);fstat = archive_entry_stat(cpio_entry);fsize = archive_entry_size(cpio_entry);/* Strip leading slashes */while (filename[offset] == '/')offset+=1;/* Strip leading ./ */while (filename[offset] == '.' && filename[offset+1] == '/')offset+=2;/* Other file type - we do not care except special cases */if (!S_ISREG(fstat->st_mode))towrite = 1;elsetowrite = 2;if (filter && filter(filename+offset, fstat, userptr)) {/* filter this file */towrite = 0;}/* Create directories */char* dirname = strdup(filename+offset);/* If the dup fails, let's hope the dirs already exist */if (dirname){char* dirptr = dirname;while (dirptr && *dirptr) {dirptr = strchr(dirptr, '/');if (dirptr) {*dirptr = 0;mkdir(dirname, 0700);*dirptr = '/';dirptr++;}}free(dirname);}/* Regular file */if (towrite>=2) {FILE *fdout = fopen(filename+offset, "w");if (fdout==NULL){rc = 33;break;}rc = archive_read_data_into_fd(cpio, fileno(fdout));if (rc!=ARCHIVE_OK) {/* XXX We didn't get the file.. well.. */needskip = 0;} else {needskip = 0;}fclose(fdout);}/* symlink, we assume that the path contained in symlink* is shorter than BUFFERSIZE */while (towrite && S_ISLNK(fstat->st_mode)) {char symlinkbuffer[BUFFERSIZE-1];needskip = 0;if ((rc = archive_read_data(cpio, symlinkbuffer,fsize))!=ARCHIVE_OK) {
/* XXX We didn't get the file.. well.. */break;}if (symlink(buffer, filename+offset)) {logMessage(ERROR, "Failed to create symlink %s ->%s", filename+offset, buffer);
}break;}if(needskip)archive_read_data_skip(cpio);- }
unpack_members(cpio, destination);
rc = archive_read_finish(cpio); /* Also closes the RPM stream
using callback */
diff --git a/loader/rpmextract.h b/loader/rpmextract.h index 20a5cc8..976047c 100644 --- a/loader/rpmextract.h +++ b/loader/rpmextract.h @@ -38,7 +38,8 @@ int explodeRPM(const char* file, filterfunc filter, dependencyfunc provides, dependencyfunc deps,
void* userptr);
void* userptr,char *destination);#endif
-- 1.7.2.3
Anaconda-devel-list mailing list Anaconda-devel-list@redhat.com https://www.redhat.com/mailman/listinfo/anaconda-devel-list
--- loader/lang.c | 12 ++++-------- loader/method.c | 4 ++-- loader/urlinstall.c | 3 ++- 3 files changed, 8 insertions(+), 11 deletions(-)
diff --git a/loader/lang.c b/loader/lang.c index 035fb75..4f230dc 100644 --- a/loader/lang.c +++ b/loader/lang.c @@ -39,6 +39,7 @@ #include "lang.h" #include "loadermisc.h" #include "windows.h" +#include "unpack.h"
#include "../pyanaconda/isys/lang.h" #include "../pyanaconda/isys/isys.h" @@ -141,7 +142,6 @@ int getLangInfo(struct langInfo ** langs) {
void loadLanguage (char * file) { char filename[200]; - gzFile stream; int fd, hash, rc; char * key = getenv("LANGKEY");
@@ -159,20 +159,16 @@ void loadLanguage (char * file) { sprintf(filename, "/etc/loader.tr"); }
- stream = gzopen(file, "r"); - - if (!stream) { + if (access(file, R_OK) == -1) { newtWinMessage("Error", "OK", "Translation for %s is not available. " "The Installation will proceed in English.", key); return ; }
sprintf(filename, "%s.tr", key); + rc = unpack_archive_file(filename, "/tmp/translation");
- rc = installCpioFile(stream, filename, "/tmp/translation", 1); - gzclose(stream); - - if (rc || access("/tmp/translation", R_OK)) { + if (rc != ARCHIVE_OK || access("/tmp/translation", R_OK) == -1) { newtWinMessage("Error", "OK", "Cannot get translation file %s.\n", filename); return; diff --git a/loader/method.c b/loader/method.c index d84a2e8..0173f5a 100644 --- a/loader/method.c +++ b/loader/method.c @@ -44,10 +44,10 @@ #include "lang.h" #include "mediacheck.h" #include "method.h" +#include "unpack.h"
#include "../pyanaconda/isys/imount.h" #include "../pyanaconda/isys/isys.h" -#include "../pyanaconda/isys/cpio.h" #include "../pyanaconda/isys/log.h"
#include "devt.h" @@ -345,7 +345,7 @@ void copyUpdatesImg(char * path) { umount("/tmp/update-disk"); unlink("/tmp/update-disk"); } else { - unpackCpioBall(path, "/tmp/updates"); + unpack_archive_file(path, "/tmp/updates"); } } } diff --git a/loader/urlinstall.c b/loader/urlinstall.c index 0998198..80285cd 100644 --- a/loader/urlinstall.c +++ b/loader/urlinstall.c @@ -47,6 +47,7 @@ #include "cdinstall.h" #include "urls.h" #include "windows.h" +#include "unpack.h"
/* boot flags */ extern uint64_t flags; @@ -177,7 +178,7 @@ int loadUrlImages(struct loaderData_s *loaderData) { unlink("/tmp/updates-disk.img"); unlink("/tmp/update-disk"); } else if (!access("/tmp/updates-disk.img", R_OK)) { - unpackCpioBall("/tmp/updates-disk.img", "/tmp/updates"); + unpack_archive_file("/tmp/updates-disk.img", "/tmp/updates"); unlink("/tmp/updates-disk.img"); }
--- loader/method.c | 36 ------------------------------------ loader/method.h | 1 - 2 files changed, 0 insertions(+), 37 deletions(-)
diff --git a/loader/method.c b/loader/method.c index 0173f5a..1cb826e 100644 --- a/loader/method.c +++ b/loader/method.c @@ -301,42 +301,6 @@ static void copyErrorFn (char *msg) { newtWinMessage(_("Error"), _("OK"), _(msg)); }
-/* - * unpack a gzipped cpio ball into a tree rooted at rootDir - * returns 0 on success, 1 on failure - */ -int unpackCpioBall(char * ballPath, char * rootDir) { - gzFile fd; - char *buf, *cwd; - int rc = 1; - - if (access(ballPath, R_OK)) - return 1; - - if (access(rootDir, R_OK)) { - if (g_mkdir_with_parents(rootDir, 0755) == -1) - logMessage(ERROR, "mkdir error on %s: %m", rootDir); - } - - buf = (char *)malloc(PATH_MAX); - cwd = getcwd(buf, PATH_MAX); - if ((rc = chdir(rootDir)) == 0) { - fd = gunzip_open(ballPath); - if (fd) { - if (!installCpioFile(fd, NULL, NULL, 0)) { - logMessage(INFO, "copied contents of %s into %s", ballPath, - rootDir); - rc = chdir(cwd); - return 0; - } - gunzip_close(fd); - } - rc = chdir(cwd); - } - - return 1; -} - void copyUpdatesImg(char * path) { if (!access(path, R_OK)) { if (!doPwMount(path, "/tmp/update-disk", "auto", "ro", NULL)) { diff --git a/loader/method.h b/loader/method.h index 0de8914..6218343 100644 --- a/loader/method.h +++ b/loader/method.h @@ -45,7 +45,6 @@ void queryIsoMediaCheck(char * isoDir);
int getFileFromBlockDevice(char *device, char *path, char * dest);
-int unpackCpioBall(char * ballPath, char * rootDir); void copyUpdatesImg(char * path); void copyProductImg(char * path);
anaconda-devel@lists.fedoraproject.org