From 9e6dc0e00ec028a14812ba36fc781fb6e121bb3b Mon Sep 17 00:00:00 2001 From: jbj Date: Fri, 20 Sep 2002 21:26:16 +0000 Subject: [PATCH] - eliminate myftw, use Fts(3) instead. CVS patchset: 5730 CVS date: 2002/09/20 21:26:16 --- CHANGES | 1 + build/Makefile.am | 4 +- build/files.c | 129 +++++++++++++------ build/myftw.c | 253 -------------------------------------- build/myftw.h | 32 ----- lib/rpmds.h | 1 + scripts/find-debuginfo.sh | 2 +- tools/javadeps.c | 6 +- 8 files changed, 97 insertions(+), 331 deletions(-) delete mode 100644 build/myftw.c delete mode 100644 build/myftw.h diff --git a/CHANGES b/CHANGES index 0f263edba..1238d6fc8 100644 --- a/CHANGES +++ b/CHANGES @@ -4,6 +4,7 @@ - unify cachesize configuration, with (or without) a dbenv. - comments regarding unsupported (yet) db-4.1.17 functionality. - update to db-4.1.24 final. + - eliminate myftw, use Fts(3) instead. 4.0.4 -> 4.1: - loosely wire beecrypt library into rpm. diff --git a/build/Makefile.am b/build/Makefile.am index 75e2d103b..98cfb6053 100644 --- a/build/Makefile.am +++ b/build/Makefile.am @@ -14,11 +14,11 @@ LIBS = pkgincdir = $(pkgincludedir) pkginc_HEADERS = rpmbuild.h rpmspec.h -noinst_HEADERS = buildio.h myftw.h +noinst_HEADERS = buildio.h lib_LTLIBRARIES = librpmbuild.la librpmbuild_la_SOURCES = \ - build.c expression.c files.c misc.c myftw.c names.c pack.c \ + build.c expression.c files.c misc.c names.c pack.c \ parseBuildInstallClean.c parseChangelog.c parseDescription.c \ parseFiles.c parsePreamble.c parsePrep.c parseReqs.c parseScript.c \ parseSpec.c poptBT.c reqprov.c spec.c diff --git a/build/files.c b/build/files.c index fb87d5833..06fecb1f9 100644 --- a/build/files.c +++ b/build/files.c @@ -12,6 +12,8 @@ #include /* getOutputFrom() */ #include +#include + #include #include "cpio.h" @@ -24,7 +26,6 @@ #include "buildio.h" -#include "myftw.h" #include "legacy.h" /* XXX domd5, expandFileList, compressFileList */ #include "misc.h" #include "debug.h" @@ -70,23 +71,28 @@ typedef struct FileListRec_s { #define fl_size fl_st.st_size #define fl_mtime fl_st.st_mtime -/*@only@*/ const char * diskURL; /* get file from here */ -/*@only@*/ const char * fileURL; /* filename in cpio archive */ -/*@observer@*/ const char * uname; -/*@observer@*/ const char * gname; +/*@only@*/ + const char *diskURL; /* get file from here */ +/*@only@*/ + const char *fileURL; /* filename in cpio archive */ +/*@observer@*/ + const char *uname; +/*@observer@*/ + const char *gname; unsigned flags; specdFlags specdFlags; /* which attributes have been explicitly specified. */ unsigned verifyFlags; -/*@only@*/ const char *langs; /* XXX locales separated with | */ +/*@only@*/ + const char *langs; /* XXX locales separated with | */ } * FileListRec; /** */ typedef struct AttrRec_s { - const char * ar_fmodestr; - const char * ar_dmodestr; - const char * ar_user; - const char * ar_group; + const char *ar_fmodestr; + const char *ar_dmodestr; + const char *ar_user; + const char *ar_group; mode_t ar_fmode; mode_t ar_dmode; } * AttrRec; @@ -106,8 +112,10 @@ static int check_fileListLen = 0; * Package file tree walk data. */ typedef struct FileList_s { -/*@only@*/ const char * buildRootURL; -/*@only@*/ const char * prefix; +/*@only@*/ + const char * buildRootURL; +/*@only@*/ + const char * prefix; int fileCount; int totalFileSize; @@ -131,14 +139,16 @@ typedef struct FileList_s { specdFlags defSpecdFlags; int defVerifyFlags; int nLangs; -/*@only@*/ /*@null@*/ const char ** currentLangs; +/*@only@*/ /*@null@*/ + const char ** currentLangs; /* Hard coded limit of MAXDOCDIR docdirs. */ /* If you break it you are doing something wrong. */ const char * docDirs[MAXDOCDIR]; int docDirCount; -/*@only@*/ FileListRec fileList; +/*@only@*/ + FileListRec fileList; int fileListRecsAlloced; int fileListRecsUsed; } * FileList; @@ -1503,6 +1513,10 @@ static /*@null@*/ FileListRec freeFileList(/*@only@*/ FileListRec fileList, } /*@=boundswrite@*/ +/* forward ref */ +static int recurseDir(FileList fl, const char * diskURL) + /*@*/; + /** * Add a file to the package manifest. * @param fl package file tree walk data @@ -1595,16 +1609,7 @@ static int addFile(FileList fl, const char * diskURL, } if ((! fl->isDir) && S_ISDIR(statp->st_mode)) { - /* We use our own ftw() call, because ftw() uses stat() */ - /* instead of lstat(), which causes it to follow symlinks! */ - /* It also has better callback support. */ - - fl->inFtw = 1; /* Flag to indicate file has buildRootURL prefixed */ - fl->isDir = 1; /* Keep it from following myftw() again */ - (void) myftw(diskURL, 16, (myftwFunc) addFile, fl); - fl->isDir = 0; - fl->inFtw = 0; - return 0; + return recurseDir(fl, diskURL); } fileMode = statp->st_mode; @@ -1629,30 +1634,17 @@ static int addFile(FileList fl, const char * diskURL, fileGname = getGname(fileGid); } -#if 0 /* XXX this looks dumb to me */ - if (! (fileUname && fileGname)) { - rpmError(RPMERR_BADSPEC, _("Bad owner/group: %s\n"), diskName); - fl->processingFailed = 1; - return RPMERR_BADSPEC; - } -#else /* Default user/group to builder's user/group */ if (fileUname == NULL) fileUname = getUname(getuid()); if (fileGname == NULL) fileGname = getGname(getgid()); -#endif -#ifdef DYING /* XXX duplicates with %exclude, use psm.c output instead. */ - rpmMessage(RPMMESS_DEBUG, _("File%5d: %07o %s.%s\t %s\n"), fl->fileCount, - (unsigned)fileMode, fileUname, fileGname, fileURL); -#endif - /* S_XXX macro must be consistent with type in find call at check-files script */ if (check_fileList && S_ISREG(fileMode)) { - appendStringBuf(check_fileList, diskURL); - appendStringBuf(check_fileList, "\n"); - check_fileListLen += strlen(diskURL) + 1; + appendStringBuf(check_fileList, diskURL); + appendStringBuf(check_fileList, "\n"); + check_fileListLen += strlen(diskURL) + 1; } /* Add to the file list */ @@ -1735,6 +1727,63 @@ static int addFile(FileList fl, const char * diskURL, } /*@=boundswrite@*/ +/** + * Add directory (and all of its files) to the package manifest. + * @param fl package file tree walk data + * @param diskURL path to file + * @param statp file stat (possibly NULL) + * @return 0 on success + */ +static int recurseDir(FileList fl, const char * diskURL) + /*@*/ +{ + char * ftsSet[2]; + FTS * ftsp; + FTSENT * fts; + int ftsOpts = (FTS_COMFOLLOW | FTS_NOCHDIR | FTS_PHYSICAL); + int rc = RPMERR_BADSPEC; + + fl->inFtw = 1; /* Flag to indicate file has buildRootURL prefixed */ + fl->isDir = 1; /* Keep it from following myftw() again */ + + ftsSet[0] = (char *) diskURL; + ftsSet[1] = NULL; + ftsp = Fts_open(ftsSet, ftsOpts, NULL); + while ((fts = Fts_read(ftsp)) != NULL) { + switch (fts->fts_info) { + case FTS_D: /* preorder directory */ + case FTS_F: /* regular file */ + case FTS_SL: /* symbolic link */ + case FTS_SLNONE: /* symbolic link without target */ + case FTS_DEFAULT: /* none of the above */ + rc = addFile(fl, fts->fts_accpath, fts->fts_statp); + break; + case FTS_DOT: /* dot or dot-dot */ + case FTS_DP: /* postorder directory */ + rc = 0; + break; + case FTS_NS: /* stat(2) failed */ + case FTS_DNR: /* unreadable directory */ + case FTS_ERR: /* error; errno is set */ + case FTS_DC: /* directory that causes cycles */ + case FTS_NSOK: /* no stat(2) requested */ + case FTS_INIT: /* initialized only */ + case FTS_W: /* whiteout object */ + default: + rc = RPMERR_BADSPEC; + break; + } + if (rc) + break; + } + (void) Fts_close(ftsp); + + fl->isDir = 0; + fl->inFtw = 0; + + return rc; +} + /** * Add a file to a binary package. * @param pkg diff --git a/build/myftw.c b/build/myftw.c deleted file mode 100644 index 7c3c71733..000000000 --- a/build/myftw.c +++ /dev/null @@ -1,253 +0,0 @@ -/** \ingroup rpmbuild - * \file build/myftw.c - * Modified ftw() -- uses Lstat() instead of stat(). - */ - -/* Copyright (C) 1992, 1994, 1995 Free Software Foundation, Inc. -This file is part of the GNU C Library. -Contributed by Ian Lance Taylor (ian@airs.com). - -The GNU C Library is free software; you can redistribute it and/or -modify it under the terms of the GNU Library General Public License as -published by the Free Software Foundation; either version 2 of the -License, or (at your option) any later version. - -The GNU C Library 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 -Library General Public License for more details. - -You should have received a copy of the GNU Library General Public -License along with the GNU C Library; see the file COPYING.LIB. If -not, write to the Free Software Foundation, Inc., 675 Mass Ave, -Cambridge, MA 02139, USA. */ - -#include "system.h" - -#include - -#ifndef NAMLEN -#define NAMLEN(a) strlen((a)->d_name) -#endif - -#if !defined(__LCLINT__) -#ifndef PATH_MAX -#ifdef _POSIX_VERSION -#define PATH_MAX _POSIX_PATH_MAX -#else -#ifdef MAXPATHLEN -#define PATH_MAX MAXPATHLEN -#else -#define PATH_MAX 1024 -#endif -#endif -#endif -#endif /* !__LCLINT */ - -#include "myftw.h" -#include "debug.h" - -/* Traverse one level of a directory tree. */ - -/** - */ -/*@-boundswrite@*/ -/*@-nullstate@*/ -static int -myftw_dir (DIR **dirs, int level, int descriptors, - char *dir, size_t len, - myftwFunc func, - void *fl) - /*@globals errno, fileSystem, internalState @*/ - /*@modifies *dirs, *dir, errno, fileSystem, internalState @*/ -{ - int got; - struct dirent *entry; - int d_namlen; - - got = 0; - - errno = 0; - - while ((entry = Readdir (dirs[level])) != NULL) - { - struct stat s; - int flag, retval, newlev = 0; - - ++got; - - if (entry->d_name[0] == '.' - && (entry->d_name [1] == '\0' || - (entry->d_name [2] == '\0' && entry->d_name[1] == '.'))) - { - errno = 0; - continue; - } - - d_namlen = NAMLEN(entry) + 1; - if (d_namlen + len > PATH_MAX) - { -#ifdef ENAMETOOLONG - errno = ENAMETOOLONG; -#else - errno = ENOMEM; -#endif - return -1; - } - - dir[len] = '/'; - memcpy ((void *) (dir + len + 1), (void *) entry->d_name, d_namlen); - - if (Lstat (dir, &s) < 0) - { - /* Following POSIX.1 2.4 ENOENT is returned if the file cannot - * be stat'ed. This can happen for a file returned by Readdir - * if it's an unresolved symbolic link. This should be regarded - * as an forgivable error. -- Uli. */ - if (errno != EACCES && errno != ENOENT) - return -1; - flag = MYFTW_NS; - } - else if (S_ISDIR (s.st_mode)) - { - newlev = (level + 1) % descriptors; - - /*@-unqualifiedtrans@*/ - if (dirs[newlev] != NULL) - (void) Closedir (dirs[newlev]); - /*@=unqualifiedtrans@*/ - - dirs[newlev] = Opendir (dir); - if (dirs[newlev] != NULL) - flag = MYFTW_D; - else - { - if (errno != EACCES) - return -1; - flag = MYFTW_DNR; - } - } - else - flag = MYFTW_F; - - retval = (*func) (fl, dir, &s); - - if (flag == MYFTW_D) - { - if (retval == 0) - retval = myftw_dir (dirs, newlev, descriptors, dir, - d_namlen + len, func, fl); - if (dirs[newlev] != NULL) - { - int save; - - save = errno; - (void) Closedir (dirs[newlev]); - errno = save; - dirs[newlev] = NULL; - } - } - - if (retval != 0) - return retval; - - if (dirs[level] == NULL) - { - int skip; - - dir[len] = '\0'; - dirs[level] = Opendir (dir); - if (dirs[level] == NULL) - return -1; - skip = got; - while (skip-- != 0) - { - errno = 0; - if (Readdir (dirs[level]) == NULL) - return errno == 0 ? 0 : -1; - } - } - - errno = 0; - } - - return errno == 0 ? 0 : -1; -} -/*@=nullstate@*/ -/*@=boundswrite@*/ - -/* Call a function on every element in a directory tree. */ - -/*@-bounds@*/ -int myftw (const char *dir, - int descriptors, - myftwFunc func, - void *fl) -{ - DIR **dirs; - size_t len; - char buf[PATH_MAX + 1]; - struct stat s; - int flag, retval; - int i; - - if (descriptors <= 0) - descriptors = 1; - - /*@access DIR@*/ - dirs = (DIR **) alloca (descriptors * sizeof (*dirs)); - i = descriptors; - while (i-- > 0) - dirs[i] = NULL; - - if (Lstat (dir, &s) < 0) - { - /* Following POSIX.1 2.4 ENOENT is returned if the file cannot - * be stat'ed. This can happen for a file returned by Readdir - * if it's an unresolved symbolic link. This should be regarded - * as an forgivable error. -- Uli. */ - if (errno != EACCES && errno != ENOENT) - return -1; - flag = MYFTW_NS; - } - else if (S_ISDIR (s.st_mode)) - { - dirs[0] = Opendir (dir); - if (dirs[0] != NULL) - flag = MYFTW_D; - else - { - if (errno != EACCES) - return -1; - flag = MYFTW_DNR; - } - } - else - flag = MYFTW_F; - - len = strlen (dir); - memcpy ((void *) buf, (void *) dir, len + 1); - - retval = (*func) (fl, buf, &s); - - if (flag == MYFTW_D) - { -/*@-compdef@*/ /* FIX: *dirs not defined */ - if (retval == 0) - retval = myftw_dir (dirs, 0, descriptors, buf, len, func, fl); - if (dirs[0] != NULL) - { - int save; - - save = errno; - (void) Closedir (dirs[0]); - /*@-mods@*/ - errno = save; - /*@=mods@*/ - } -/*@=compdef@*/ - } - - return retval; -} -/*@=bounds@*/ diff --git a/build/myftw.h b/build/myftw.h deleted file mode 100644 index 2330de100..000000000 --- a/build/myftw.h +++ /dev/null @@ -1,32 +0,0 @@ -#ifndef _H_MYFTW_ -#define _H_MYFTW_ - -/** \ingroup rpmbuild - * \file build/myftw.h - * Portable ftw(3) using lstat() instead of stat(). - */ - -#include - -/* The FLAG argument to the user function passed to ftw. */ -#define MYFTW_F 0 /* Regular file. */ -#define MYFTW_D 1 /* Directory. */ -#define MYFTW_DNR 2 /* Unreadable directory. */ -#define MYFTW_NS 3 /* Unstatable file. */ - -#ifdef __cplusplus -extern "C" { -#endif - -typedef int (*myftwFunc) (void *fl, const char *name, struct stat *statp) - /*@*/; - -int myftw (const char *dir, int descriptors, myftwFunc func, void *fl) - /*@globals fileSystem, internalState @*/ - /*@modifies *fl, fileSystem, internalState @*/; - -#ifdef __cplusplus -} -#endif - -#endif /* _H_MYFTW_ */ diff --git a/lib/rpmds.h b/lib/rpmds.h index ee46e072e..85543f3f4 100644 --- a/lib/rpmds.h +++ b/lib/rpmds.h @@ -232,6 +232,7 @@ int rpmdsNoPromote(/*@null@*/ const rpmds ds) /** * Set "Don't promote Epoch:" flag. * @param ds dependency set + * @param nopromote Should an unspecified Epoch: be treated as Epoch: 0? * @return previous "Don't promote Epoch:" flag */ int rpmdsSetNoPromote(/*@null@*/ rpmds ds, int nopromote) diff --git a/scripts/find-debuginfo.sh b/scripts/find-debuginfo.sh index 33776899d..39ae760f9 100644 --- a/scripts/find-debuginfo.sh +++ b/scripts/find-debuginfo.sh @@ -11,7 +11,7 @@ for f in `find $RPM_BUILD_ROOT -type f \( -perm -0100 -or -perm -0010 -or -perm OUTPUTDIR=${RPM_BUILD_ROOT}/usr/lib/debug${BASEDIR} mkdir -p ${OUTPUTDIR} echo extracting debug info from $f - striptofile -g -u -o $OUTPUTDIR $f || : + /usr/lib/rpm/striptofile -g -u -o $OUTPUTDIR $f || : done find ${RPM_BUILD_ROOT}/usr/lib/debug -type f | sed -n -e "s#^$RPM_BUILD_ROOT#/#p" > $LISTFILE diff --git a/tools/javadeps.c b/tools/javadeps.c index 8ecd177b3..f7a87947b 100644 --- a/tools/javadeps.c +++ b/tools/javadeps.c @@ -257,7 +257,7 @@ usage (void) "assumed to be zero. \n\n" ""); printf("EXAMPLES (Java Keywords): \n\n" - "\t public static final String REVISION = \"$Revision: 2.11 $\";\n" + "\t public static final String REVISION = \"$Revision: 2.12 $\";\n" "\t public static final String EPOCH = \"4\";\n" "\t public static final String REQUIRES = \"RPM_Requires: " "java(gnu.regexp.RE) java(com.ibm.site.util.Options)>=1.5\";\n" @@ -316,8 +316,6 @@ void die(char *format, ...) { is hard since we only know that name when we are done parsing the file, and most errors will occur before that.*/ - va_start(ap, format); - if ( (!FILE_NAME) ) { sprintf (newformat, "\n%s: %s", @@ -333,7 +331,9 @@ void die(char *format, ...) { PROGRAM_NAME, FILE_NAME, CLASS_NAME, format); } + va_start(ap, format); vsprintf (newmsg, newformat, ap); + va_end(ap); /* print error to where it needs to go: stdout, stderr, or syslog