From 3084d0ecb0db75ad1f88d4129ea6ae54ad635f99 Mon Sep 17 00:00:00 2001 From: Marcin Krol Date: Thu, 19 Oct 2017 23:25:36 +0000 Subject: [PATCH] - backport shrink support for macros --- rpm-shrink.patch | 623 +++++++++++++++++++++++++++++++++++++++++++++++ rpm.spec | 4 +- 2 files changed, 626 insertions(+), 1 deletion(-) create mode 100644 rpm-shrink.patch diff --git a/rpm-shrink.patch b/rpm-shrink.patch new file mode 100644 index 0000000..4c02b61 --- /dev/null +++ b/rpm-shrink.patch @@ -0,0 +1,623 @@ +diff -urNp rpm-4.5.orig/rpmio/macro.c rpm-4.5/rpmio/macro.c +--- rpm-4.5.orig/rpmio/macro.c 2017-10-19 22:48:49.000000000 +0000 ++++ rpm-4.5/rpmio/macro.c 2017-10-19 23:16:34.301644733 +0000 +@@ -71,6 +71,7 @@ const char * rpmMacrofiles = MACROFILES; + #endif + + #include ++#include + + #include "debug.h" + +@@ -1200,6 +1201,28 @@ doFoo(MacroBuf mb, int negate, const cha + if ((b = strrchr(buf, '/')) != NULL) + *b = '\0'; + b = buf; ++ } else if (STREQ("shrink", f, fn)) { ++ /* ++ * shrink body by removing all leading and trailing whitespaces and ++ * reducing intermediate whitespaces to a single space character. ++ */ ++ size_t i = 0, j = 0; ++ size_t buflen = strlen(buf); ++ int was_space = 0; ++ while (i < buflen) { ++ if (risspace(buf[i])) { ++ was_space = 1; ++ i++; ++ continue; ++ } else if (was_space) { ++ was_space = 0; ++ if (j > 0) /* remove leading blanks at all */ ++ buf[j++] = ' '; ++ } ++ buf[j++] = buf[i++]; ++ } ++ buf[j] = '\0'; ++ b = buf; + } else if (STREQ("suffix", f, fn)) { + if ((b = strrchr(buf, '.')) != NULL) + b++; +@@ -1549,6 +1572,7 @@ expandMacro(MacroBuf mb) + /* XXX necessary but clunky */ + if (STREQ("basename", f, fn) || + STREQ("dirname", f, fn) || ++ STREQ("shrink", f, fn) || + STREQ("suffix", f, fn) || + STREQ("expand", f, fn) || + STREQ("verbose", f, fn) || +diff -urNp rpm-4.5.orig/rpmio/Makefile.am rpm-4.5/rpmio/Makefile.am +--- rpm-4.5.orig/rpmio/Makefile.am 2017-10-19 22:48:49.000000000 +0000 ++++ rpm-4.5/rpmio/Makefile.am 2017-10-19 23:16:15.212645871 +0000 +@@ -37,7 +37,7 @@ librpmio_la_SOURCES = \ + md2.c md4.c rmd128.c rmd160.c rmd256.c rmd320.c sha224.c \ + salsa10.c salsa20.c tiger.c \ + rpmdav.c rpmhash.c rpmhook.c rpmio.c rpmlog.c rpmlua.c rpmmalloc.c \ +- rpmpgp.c rpmrpc.c rpmsq.c rpmsw.c strcasecmp.c strtolocale.c \ ++ rpmpgp.c rpmrpc.c rpmsq.c rpmstring.c rpmsw.c strcasecmp.c strtolocale.c \ + stubs.c url.c ugid.c rpmuuid.c + librpmio_la_LDFLAGS = -no-undefined -release $(LT_CURRENT).$(LT_REVISION) $(LDFLAGS) \ + @WITH_BEECRYPT_LIB@ \ +diff -urNp rpm-4.5.orig/rpmio/Makefile.in rpm-4.5/rpmio/Makefile.in +--- rpm-4.5.orig/rpmio/Makefile.in 2008-07-09 09:41:32.000000000 +0000 ++++ rpm-4.5/rpmio/Makefile.in 2017-10-19 23:16:15.212645871 +0000 +@@ -68,7 +68,7 @@ am_librpmio_la_OBJECTS = argv.lo digest. + macro.lo mire.lo md2.lo md4.lo rmd128.lo rmd160.lo rmd256.lo \ + rmd320.lo sha224.lo salsa10.lo salsa20.lo tiger.lo rpmdav.lo \ + rpmhash.lo rpmhook.lo rpmio.lo rpmlog.lo rpmlua.lo \ +- rpmmalloc.lo rpmpgp.lo rpmrpc.lo rpmsq.lo rpmsw.lo \ ++ rpmmalloc.lo rpmpgp.lo rpmrpc.lo rpmsq.lo rpmstring.lo rpmsw.lo \ + strcasecmp.lo strtolocale.lo stubs.lo url.lo ugid.lo \ + rpmuuid.lo + librpmio_la_OBJECTS = $(am_librpmio_la_OBJECTS) +diff -urNp rpm-4.5.orig/rpmio/rpmstring.c rpm-4.5/rpmio/rpmstring.c +--- rpm-4.5.orig/rpmio/rpmstring.c 1970-01-01 00:00:00.000000000 +0000 ++++ rpm-4.5/rpmio/rpmstring.c 2017-10-19 23:16:15.212645871 +0000 +@@ -0,0 +1,192 @@ ++/** ++ * \file rpmio/rpmstring.c ++ */ ++ ++#include "system.h" ++ ++#include ++#include ++ ++#include ++#include "debug.h" ++ ++ ++int rstrcasecmp(const char * s1, const char * s2) ++{ ++ const char * p1 = s1; ++ const char * p2 = s2; ++ char c1, c2; ++ ++ if (p1 == p2) ++ return 0; ++ ++ do ++ { ++ c1 = rtolower (*p1++); ++ c2 = rtolower (*p2++); ++ if (c1 == '\0') ++ break; ++ } ++ while (c1 == c2); ++ ++ return (int)(c1 - c2); ++} ++ ++int rstrncasecmp(const char *s1, const char *s2, size_t n) ++{ ++ const char * p1 = s1; ++ const char * p2 = s2; ++ char c1, c2; ++ ++ if (p1 == p2 || n == 0) ++ return 0; ++ ++ do ++ { ++ c1 = rtolower (*p1++); ++ c2 = rtolower (*p2++); ++ if (c1 == '\0' || c1 != c2) ++ break; ++ } while (--n > 0); ++ ++ return (int)(c1 - c2); ++} ++ ++/* ++ * Simple and stupid asprintf() clone. ++ * FIXME: write to work with non-C99 vsnprintf or check for one in configure. ++ */ ++int rasprintf(char **strp, const char *fmt, ...) ++{ ++ int n; ++ va_list ap; ++ char * p = NULL; ++ ++ if (strp == NULL) ++ return -1; ++ ++ va_start(ap, fmt); ++ n = vsnprintf(NULL, 0, fmt, ap); ++ va_end(ap); ++ ++ if (n >= -1) { ++ size_t nb = n + 1; ++ p = xmalloc(nb); ++ va_start(ap, fmt); ++ n = vsnprintf(p, nb, fmt, ap); ++ va_end(ap); ++ } ++ *strp = p; ++ return n; ++} ++ ++/* ++ * Concatenate two strings with dynamically (re)allocated ++ * memory what prevents static buffer overflows by design. ++ * *dest is reallocated to the size of strings to concatenate. ++ * ++ * Note: ++ * 1) char *buf = rstrcat(NULL,"string"); is the same like rstrcat(&buf,"string"); ++ * 2) rstrcat(&buf,NULL) returns buf ++ * 3) rstrcat(NULL,NULL) returns NULL ++ * 4) *dest and src can overlap ++ */ ++char *rstrcat(char **dest, const char *src) ++{ ++ if ( src == NULL ) { ++ return dest != NULL ? *dest : NULL; ++ } ++ ++ if ( dest == NULL ) { ++ return xstrdup(src); ++ } ++ ++ { ++ size_t dest_size = *dest != NULL ? strlen(*dest) : 0; ++ size_t src_size = strlen(src); ++ ++ *dest = xrealloc(*dest, dest_size+src_size+1); /* include '\0' */ ++ memmove(&(*dest)[dest_size], src, src_size+1); ++ } ++ ++ return *dest; ++} ++ ++/* ++ * Concatenate strings with dynamically (re)allocated ++ * memory what prevents static buffer overflows by design. ++ * *dest is reallocated to the size of strings to concatenate. ++ * List of strings has to be NULL terminated. ++ * ++ * Note: ++ * 1) char *buf = rstrscat(NULL,"string",NULL); is the same like rstrscat(&buf,"string",NULL); ++ * 2) rstrscat(&buf,NULL) returns buf ++ * 3) rstrscat(NULL,NULL) returns NULL ++ * 4) *dest and argument strings can overlap ++ */ ++char *rstrscat(char **dest, const char *arg, ...) ++{ ++ va_list ap; ++ size_t arg_size, dst_size; ++ const char *s; ++ char *dst, *p; ++ ++ dst = dest ? *dest : NULL; ++ ++ if ( arg == NULL ) { ++ return dst; ++ } ++ ++ va_start(ap, arg); ++ for (arg_size=0, s=arg; s; s = va_arg(ap, const char *)) ++ arg_size += strlen(s); ++ va_end(ap); ++ ++ dst_size = dst ? strlen(dst) : 0; ++ dst = xrealloc(dst, dst_size+arg_size+1); /* include '\0' */ ++ p = &dst[dst_size]; ++ ++ va_start(ap, arg); ++ for (s = arg; s; s = va_arg(ap, const char *)) { ++ size_t size = strlen(s); ++ memmove(p, s, size); ++ p += size; ++ } ++ va_end(ap); ++ *p = '\0'; ++ ++ if ( dest ) { ++ *dest = dst; ++ } ++ ++ return dst; ++} ++ ++/* ++ * Adapted from OpenBSD, strlcpy() originally developed by ++ * Todd C. Miller ++ */ ++size_t rstrlcpy(char *dest, const char *src, size_t n) ++{ ++ char *d = dest; ++ const char *s = src; ++ size_t len = n; ++ ++ /* Copy as many bytes as will fit */ ++ if (len != 0) { ++ while (--len != 0) { ++ if ((*d++ = *s++) == '\0') ++ break; ++ } ++ } ++ ++ /* Not enough room in dst, add NUL and traverse rest of src */ ++ if (len == 0) { ++ if (n != 0) ++ *d = '\0'; /* NUL-terminate dst */ ++ while (*s++) ++ ; ++ } ++ ++ return s - src - 1; /* count does not include NUL */ ++} +diff -urNp rpm-4.5.orig/rpmio/rpmstring.h rpm-4.5/rpmio/rpmstring.h +--- rpm-4.5.orig/rpmio/rpmstring.h 1970-01-01 00:00:00.000000000 +0000 ++++ rpm-4.5/rpmio/rpmstring.h 2017-10-19 23:16:15.212645871 +0000 +@@ -0,0 +1,187 @@ ++#ifndef _RPMSTRING_H_ ++#define _RPMSTRING_H_ ++ ++/** \ingroup rpmstring ++ * \file rpmio/rpmstring.h ++ * String manipulation helper functions ++ */ ++ ++#include ++#include ++ ++#include ++ ++#ifdef __cplusplus ++extern "C" { ++#endif ++ ++/** \ingroup rpmstring ++ * Locale insensitive islower(3) ++ */ ++RPM_GNUC_CONST ++static inline int rislower(int c) { ++ return (c >= 'a' && c <= 'z'); ++} ++ ++/** \ingroup rpmstring ++ * Locale insensitive isupper(3) ++ */ ++RPM_GNUC_CONST ++static inline int risupper(int c) { ++ return (c >= 'A' && c <= 'Z'); ++} ++ ++/** \ingroup rpmstring ++ * Locale insensitive isalpha(3) ++ */ ++RPM_GNUC_CONST ++static inline int risalpha(int c) { ++ return (rislower(c) || risupper(c)); ++} ++ ++/** \ingroup rpmstring ++ * Locale insensitive isdigit(3) ++ */ ++RPM_GNUC_CONST ++static inline int risdigit(int c) { ++ return (c >= '0' && c <= '9'); ++} ++ ++/** \ingroup rpmstring ++ * Locale insensitive isalnum(3) ++ */ ++RPM_GNUC_CONST ++static inline int risalnum(int c) { ++ return (risalpha(c) || risdigit(c)); ++} ++ ++/** \ingroup rpmstring ++ * Locale insensitive isblank(3) ++ */ ++RPM_GNUC_CONST ++static inline int risblank(int c) { ++ return (c == ' ' || c == '\t'); ++} ++ ++/** \ingroup rpmstring ++ * Locale insensitive isspace(3) ++ */ ++RPM_GNUC_CONST ++static inline int risspace(int c) { ++ return (risblank(c) || c == '\n' || c == '\r' || c == '\f' || c == '\v'); ++} ++ ++/** \ingroup rpmstring ++ * Locale insensitive tolower(3) ++ */ ++RPM_GNUC_CONST ++static inline int rtolower(int c) { ++ return ((risupper(c)) ? (c | ('a' - 'A')) : c); ++} ++ ++/** \ingroup rpmstring ++ * Locale insensitive toupper(3) ++ */ ++RPM_GNUC_CONST ++static inline int rtoupper(int c) { ++ return ((rislower(c)) ? (c & ~('a' - 'A')) : c); ++} ++ ++/** ++ * Convert hex to binary nibble. ++ * @param c hex character ++ * @return binary nibble ++ */ ++RPM_GNUC_CONST ++static inline unsigned char rnibble(char c) ++{ ++ if (c >= '0' && c <= '9') ++ return (c - '0'); ++ if (c >= 'a' && c <= 'f') ++ return (c - 'a') + 10; ++ if (c >= 'A' && c <= 'F') ++ return (c - 'A') + 10; ++ return 0; ++} ++ ++/** ++ * Test for string equality ++ * @param s1 string 1 ++ * @param s2 string 2 ++ * @return 0 if strings differ, 1 if equal ++ */ ++static inline int rstreq(const char *s1, const char *s2) ++{ ++ return (strcmp(s1, s2) == 0); ++} ++ ++/** ++ * Test for string equality ++ * @param s1 string 1 ++ * @param s2 string 2 ++ * @param n compare at most n characters ++ * @return 0 if strings differ, 1 if equal ++ */ ++static inline int rstreqn(const char *s1, const char *s2, size_t n) ++{ ++ return (strncmp(s1, s2, n) == 0); ++} ++ ++/** \ingroup rpmstring ++ * Locale insensitive strcasecmp(3). ++ */ ++RPM_GNUC_PURE ++int rstrcasecmp(const char * s1, const char * s2) ; ++ ++/** \ingroup rpmstring ++ * Locale insensitive strncasecmp(3). ++ */ ++RPM_GNUC_PURE ++int rstrncasecmp(const char *s1, const char * s2, size_t n) ; ++ ++/** \ingroup rpmstring ++ * asprintf() clone ++ */ ++int rasprintf(char **strp, const char *fmt, ...) RPM_GNUC_PRINTF(2, 3); ++ ++/** \ingroup rpmstring ++ * Concatenate two strings with dynamically (re)allocated memory. ++ * @param dest pointer to destination string ++ * @param src source string ++ * @return realloc'd dest with src appended ++ */ ++char *rstrcat(char **dest, const char *src); ++ ++/** \ingroup rpmstring ++ * Concatenate multiple strings with dynamically (re)allocated memory. ++ * @param dest pointer to destination string ++ * @param arg NULL terminated list of strings to concatenate ++ * @return realloc'd dest with strings appended ++ */ ++char *rstrscat(char **dest, const char *arg, ...) RPM_GNUC_NULL_TERMINATED; ++ ++/** \ingroup rpmstring ++ * strlcpy() clone: ++ * Copy src to string dest of size n. At most n-1 characters ++ * will be copied. Always zero-terminates (unless n == 0). ++ * Length of src is returned; if retval >= n, truncation occurred. ++ * @param dest destination buffer ++ * @param src string to copy ++ * @param n destination buffer size ++ * @return length of src string ++ */ ++size_t rstrlcpy(char *dest, const char *src, size_t n); ++ ++/** \ingroup rpmstring ++ * String hashing function ++ * @param string string to hash ++ * @return hash id ++ */ ++RPM_GNUC_PURE ++unsigned int rstrhash(const char * string); ++ ++#ifdef __cplusplus ++} ++#endif ++ ++#endif /* _RPMSTRING_H_ */ +diff -urNp rpm-4.5.orig/rpmio/rpmutil.h rpm-4.5/rpmio/rpmutil.h +--- rpm-4.5.orig/rpmio/rpmutil.h 1970-01-01 00:00:00.000000000 +0000 ++++ rpm-4.5/rpmio/rpmutil.h 2017-10-19 23:16:15.213645871 +0000 +@@ -0,0 +1,160 @@ ++#ifndef _RPMUTIL_H ++#define _RPMUTIL_H ++ ++#include ++ ++/** \file rpmio/rpmutil.h ++ * ++ * Miscellaneous utility macros: ++ * - portability wrappers for various gcc extensions like __attribute__() ++ * - ... ++ * ++ * Copied from glib, names replaced to avoid clashing with glib. ++ * ++ */ ++ ++/* Here we provide RPM_GNUC_EXTENSION as an alias for __extension__, ++ * where this is valid. This allows for warningless compilation of ++ * "long long" types even in the presence of '-ansi -pedantic'. ++ */ ++#if __GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ >= 8) ++# define RPM_GNUC_EXTENSION __extension__ ++#else ++# define RPM_GNUC_EXTENSION ++#endif ++ ++/* Provide macros to feature the GCC function attribute. ++ */ ++#if __GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ >= 96) ++#define RPM_GNUC_PURE \ ++ __attribute__((__pure__)) ++#define RPM_GNUC_MALLOC \ ++ __attribute__((__malloc__)) ++#else ++#define RPM_GNUC_PURE ++#define RPM_GNUC_MALLOC ++#endif ++ ++#if (__GNUC__ > 4) || (__GNUC__ == 4 && __GNUC_MINOR__ >= 3) ++#define RPM_GNUC_ALLOC_SIZE(x) __attribute__((__alloc_size__(x))) ++#define RPM_GNUC_ALLOC_SIZE2(x,y) __attribute__((__alloc_size__(x,y))) ++#else ++#define RPM_GNUC_ALLOC_SIZE(x) ++#define RPM_GNUC_ALLOC_SIZE2(x,y) ++#endif ++ ++#if __GNUC__ >= 4 ++#define RPM_GNUC_NULL_TERMINATED __attribute__((__sentinel__)) ++#else ++#define RPM_GNUC_NULL_TERMINATED ++#endif ++ ++#if __GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ > 4) ++#define RPM_GNUC_PRINTF( format_idx, arg_idx ) \ ++ __attribute__((__format__ (__printf__, format_idx, arg_idx))) ++#define RPM_GNUC_SCANF( format_idx, arg_idx ) \ ++ __attribute__((__format__ (__scanf__, format_idx, arg_idx))) ++#define RPM_GNUC_FORMAT( arg_idx ) \ ++ __attribute__((__format_arg__ (arg_idx))) ++#define RPM_GNUC_NORETURN \ ++ __attribute__((__noreturn__)) ++#define RPM_GNUC_CONST \ ++ __attribute__((__const__)) ++#define RPM_GNUC_UNUSED \ ++ __attribute__((__unused__)) ++#define RPM_GNUC_NO_INSTRUMENT \ ++ __attribute__((__no_instrument_function__)) ++#else /* !__GNUC__ */ ++#define RPM_GNUC_PRINTF( format_idx, arg_idx ) ++#define RPM_GNUC_SCANF( format_idx, arg_idx ) ++#define RPM_GNUC_FORMAT( arg_idx ) ++#define RPM_GNUC_NORETURN ++#define RPM_GNUC_CONST ++#define RPM_GNUC_UNUSED ++#define RPM_GNUC_NO_INSTRUMENT ++#endif /* !__GNUC__ */ ++ ++#if __GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ >= 1) ++#define RPM_GNUC_DEPRECATED \ ++ __attribute__((__deprecated__)) ++#else ++#define RPM_GNUC_DEPRECATED ++#endif /* __GNUC__ */ ++ ++#if __GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ >= 3) ++#define RPM_GNUC_MAY_ALIAS __attribute__((may_alias)) ++#define RPM_GNUC_NONNULL( ... ) \ ++ __attribute__((__nonnull__ (__VA_ARGS__))) ++#else ++#define RPM_GNUC_MAY_ALIAS ++#define RPM_GNUC_NONNULL( ... ) ++#endif ++ ++#if __GNUC__ > 3 || (__GNUC__ == 3 && __GNUC_MINOR__ >= 4) ++#define RPM_GNUC_WARN_UNUSED_RESULT \ ++ __attribute__((warn_unused_result)) ++#else ++#define RPM_GNUC_WARN_UNUSED_RESULT ++#endif /* __GNUC__ */ ++ ++#if __GNUC__ >= 4 || (__GNUC__ == 3 && __GNUC_MINOR__ >= 3) ++# define RPM_GNUC_INTERNAL __attribute__((visibility("hidden"))) ++#else ++# define RPM_GNUC_INTERNAL ++#endif ++ ++ ++/* Guard C code in headers, while including them from C++ */ ++#ifdef __cplusplus ++# define RPM_BEGIN_DECLS extern "C" { ++# define RPM_END_DECLS } ++#else ++# define RPM_BEGIN_DECLS ++# define RPM_END_DECLS ++#endif ++ ++#ifdef __cplusplus ++extern "C" { ++#endif ++ ++/* Rpm specific allocators which never return NULL but terminate on failure */ ++RPM_GNUC_MALLOC RPM_GNUC_ALLOC_SIZE(1) ++void * rmalloc(size_t size); ++ ++RPM_GNUC_MALLOC RPM_GNUC_ALLOC_SIZE2(1,2) ++void * rcalloc(size_t nmemb, size_t size); ++ ++RPM_GNUC_ALLOC_SIZE(2) ++void * rrealloc(void *ptr, size_t size); ++ ++char * rstrdup(const char *str); ++ ++/* Rpm specific free() which returns NULL */ ++void * rfree(void *ptr); ++ ++/** \ingroup rpmutil ++ * Memory allocation failure callback prototype. When registered through ++ * rpmSetMemFail(), this gets called if memory allocation through rmalloc() ++ * and friends fails. If the application can somehow recover memory here, ++ * it can return a newly allocated memory block of requested size, otherwise ++ * it must return NULL after performing it's own shutdown deeds or ++ * terminate itself. ++ * @param size Size of allocation request in bytes ++ * @param data User data (or NULL) ++ * @return Allocated memory block of requested size or NULL ++ */ ++typedef void * (*rpmMemFailFunc) (size_t size, void *data); ++ ++/** \ingroup rpmutil ++ * Set memory allocation failure callback. ++ * @param func Allocation failure callback function ++ * @param data User data (or NULL) ++ * @return Previous callback function ++ */ ++rpmMemFailFunc rpmSetMemFail(rpmMemFailFunc func, void *data); ++ ++#ifdef __cplusplus ++} ++#endif ++ ++#endif /* _RPMUTIL_H */ diff --git a/rpm.spec b/rpm.spec index 3282137..3a56c79 100644 --- a/rpm.spec +++ b/rpm.spec @@ -42,7 +42,7 @@ Summary(ru.UTF-8): Менеджер пакетов от RPM Summary(uk.UTF-8): Менеджер пакетів від RPM Name: rpm Version: 4.5 -Release: 79 +Release: 80 License: LGPL Group: Base Source0: %{name}-%{version}.tar.gz @@ -168,6 +168,7 @@ Patch107: %{name}-debugedit-dwarf4.patch Patch108: %{name}-changelog_order_check_nonfatal.patch Patch109: %{name}-installplatform.patch Patch110: %{name}-xz.patch +Patch111: %{name}-shrink.patch URL: http://rpm5.org/ BuildRequires: autoconf >= 2.57 BuildRequires: automake >= 1.4 @@ -788,6 +789,7 @@ install %{SOURCE13} scripts/perl.prov %patch108 -p1 %patch109 -p1 %patch110 -p1 +%patch111 -p1 mv -f po/{sr,sr@Latn}.po rm -rf sqlite zlib popt -- 2.44.0