aboutsummaryrefslogtreecommitdiffstats
path: root/URPM.xs
diff options
context:
space:
mode:
Diffstat (limited to 'URPM.xs')
-rw-r--r--URPM.xs1583
1 files changed, 1050 insertions, 533 deletions
diff --git a/URPM.xs b/URPM.xs
index e4dda2a..04c713a 100644
--- a/URPM.xs
+++ b/URPM.xs
@@ -20,15 +20,15 @@
#include <sys/wait.h>
#include <fcntl.h>
#include <unistd.h>
+#include <zlib.h>
#include <libintl.h>
-// fix compiling (error: conflicting types for ‘fflush’):
#undef Fflush
#undef Mkdir
#undef Stat
#undef Fstat
-static inline void *_free(const void * p) {
+static inline void *_free(const void * p) {
if (p != NULL) free((void *)p);
return NULL;
}
@@ -99,6 +99,11 @@ typedef struct s_Package* URPM__Package;
#define FILTER_MODE_ALL_FILES 0
#define FILTER_MODE_CONF_FILES 2
+/* promote epoch sense should be :
+ 0 for compability with old packages
+ 1 for rpm 4.2 and better new approach. */
+#define PROMOTE_EPOCH_SENSE 1
+
static ssize_t write_nocheck(int fd, const void *buf, size_t count) {
return write(fd, buf, count);
}
@@ -108,34 +113,11 @@ static const void* unused_variable(const void *p) {
static int rpmError_callback_data;
-static int rpmError_callback() {
+int rpmError_callback() {
write_nocheck(rpmError_callback_data, rpmlogMessage(), strlen(rpmlogMessage()));
return RPMLOG_DEFAULT;
}
-static inline int _run_cb_while_traversing(SV *callback, Header header) {
- dSP;
- URPM__Package pkg = calloc(1, sizeof(struct s_Package));
-
- pkg->flag = FLAG_ID_INVALID | FLAG_NO_HEADER_FREE;
- pkg->h = header;
-
- PUSHMARK(SP);
- mXPUSHs(sv_setref_pv(newSVpvs(""), "URPM::Package", pkg));
- PUTBACK;
-
- int count = call_sv(callback, G_SCALAR);
-
- SPAGAIN;
- pkg->h = NULL; /* avoid using it anymore, in case it has been copied inside callback */
- return count;
-}
-
-static inline void _header_free(URPM__Package pkg) {
- if (pkg->h && !(pkg->flag & FLAG_NO_HEADER_FREE))
- pkg->h = headerFree(pkg->h);
-}
-
static int rpm_codeset_is_utf8 = 0;
static SV*
@@ -150,8 +132,6 @@ static void
get_fullname_parts(URPM__Package pkg, char **name, char **version, char **release, char **arch, char **eos) {
char *_version = NULL, *_release = NULL, *_arch = NULL, *_eos = NULL;
- if (!pkg->info)
- return;
if ((_eos = strchr(pkg->info, '@')) != NULL) {
*_eos = 0; /* mark end of string to enable searching backwards */
if ((_arch = strrchr(pkg->info, '.')) != NULL) {
@@ -174,7 +154,7 @@ get_fullname_parts(URPM__Package pkg, char **name, char **version, char **releas
}
static char *
-get_name(const Header header, rpmTag tag) {
+get_name(Header header, int32_t tag) {
struct rpmtd_s val;
headerGet(header, tag, &val, HEADERGET_MINMEM);
@@ -182,13 +162,8 @@ get_name(const Header header, rpmTag tag) {
return name ? name : "";
}
-static char*
-get_arch(const Header header) {
- return headerIsEntry(header, RPMTAG_SOURCERPM) ? get_name(header, RPMTAG_ARCH) : "src";
-}
-
static int
-get_int(const Header header, rpmTag tag) {
+get_int(Header header, int32_t tag) {
struct rpmtd_s val;
headerGet(header, tag, &val, HEADERGET_DEFAULT);
@@ -202,24 +177,21 @@ get_filesize(const Header h) {
}
static int
-print_list_entry(char *buff, int sz, const char *name, rpmsenseFlags flags, const char *evr) {
+print_list_entry(char *buff, int sz, const char *name, uint32_t flags, const char *evr) {
int len = strlen(name);
char *p = buff;
- if (len >= sz || !strncmp(name, "rpmlib(", 7))
- return -1;
+ if (len >= sz || !strncmp(name, "rpmlib(", 7)) return -1;
memcpy(p, name, len); p += len;
if (flags & (RPMSENSE_PREREQ|RPMSENSE_SCRIPT_PREUN|RPMSENSE_SCRIPT_PRE|RPMSENSE_SCRIPT_POSTUN|RPMSENSE_SCRIPT_POST)) {
- if (p - buff + 3 >= sz)
- return -1;
+ if (p - buff + 3 >= sz) return -1;
memcpy(p, "[*]", 4); p += 3;
}
if (evr != NULL) {
len = strlen(evr);
if (len > 0) {
- if (p - buff + 6 + len >= sz)
- return -1;
+ if (p - buff + 6 + len >= sz) return -1;
*p++ = '[';
if (flags & RPMSENSE_LESS) *p++ = '<';
if (flags & RPMSENSE_GREATER) *p++ = '>';
@@ -236,35 +208,85 @@ print_list_entry(char *buff, int sz, const char *name, rpmsenseFlags flags, cons
}
static int
-ranges_overlap(rpmsenseFlags aflags, char *sa, rpmsenseFlags bflags, char *sb) {
+ranges_overlap(uint32_t aflags, char *sa, uint32_t bflags, char *sb, int b_nopromote) {
if (!aflags || !bflags)
return 1; /* really faster to test it there instead of later */
else {
- int res;
+ int sense = 0;
char *eosa = strchr(sa, ']');
char *eosb = strchr(sb, ']');
- rpmds dsa, dsb;
+ char *ea, *va, *ra, *eb, *vb, *rb;
if (eosa) *eosa = 0;
if (eosb) *eosb = 0;
-
- dsa = rpmdsSingle(RPMTAG_REQUIRENAME, "", sa, aflags);
- dsb = rpmdsSingle(RPMTAG_REQUIRENAME, "", sb, bflags);
- res = rpmdsCompare(dsa, dsb);
- rpmdsFree(dsa);
- rpmdsFree(dsb);
-
+ /* parse sa as an [epoch:]version[-release] */
+ for (ea = sa; *sa >= '0' && *sa <= '9'; ++sa);
+ if (*sa == ':') {
+ *sa++ = 0; /* ea could be an empty string (should be interpreted as 0) */
+ va = sa;
+ } else {
+ va = ea; /* no epoch */
+ ea = NULL;
+ }
+ if ((ra = strrchr(sa, '-'))) *ra++ = 0;
+ /* parse sb as an [epoch:]version[-release] */
+ for (eb = sb; *sb >= '0' && *sb <= '9'; ++sb);
+ if (*sb == ':') {
+ *sb++ = 0; /* ea could be an empty string (should be interpreted as 0) */
+ vb = sb;
+ } else {
+ vb = eb; /* no epoch */
+ eb = NULL;
+ }
+ if ((rb = strrchr(sb, '-'))) *rb++ = 0;
+ /* now compare epoch */
+ if (ea && eb)
+ sense = rpmvercmp(*ea ? ea : "0", *eb ? eb : "0");
+ else if (ea && *ea && atol(ea) > 0)
+ sense = b_nopromote ? 1 : 0;
+ else if (eb && *eb && atol(eb) > 0)
+ sense = -1;
+ /* now compare version and release if epoch has not been enough */
+ if (sense == 0) {
+ sense = rpmvercmp(va, vb);
+ if (sense == 0 && ra && *ra && rb && *rb)
+ sense = rpmvercmp(ra, rb);
+ }
+ /* restore all character that have been modified inline */
+ if (rb) rb[-1] = '-';
+ if (ra) ra[-1] = '-';
+ if (eb) vb[-1] = ':';
+ if (ea) va[-1] = ':';
if (eosb) *eosb = ']';
if (eosa) *eosa = ']';
-
- return res;
+ /* finish the overlap computation */
+ if (sense < 0 && ((aflags & RPMSENSE_GREATER) || (bflags & RPMSENSE_LESS)))
+ return 1;
+ else if (sense > 0 && ((aflags & RPMSENSE_LESS) || (bflags & RPMSENSE_GREATER)))
+ return 1;
+ else if (sense == 0 && (((aflags & RPMSENSE_EQUAL) && (bflags & RPMSENSE_EQUAL)) ||
+ ((aflags & RPMSENSE_LESS) && (bflags & RPMSENSE_LESS)) ||
+ ((aflags & RPMSENSE_GREATER) && (bflags & RPMSENSE_GREATER))))
+ return 1;
+ else
+ return 0;
}
}
-typedef int (*callback_list_str)(char *s, int slen, const char *name, const rpmsenseFlags flags, const char *evr, void *param);
+static int has_old_suggests;
+int32_t is_old_suggests(int32_t flags) {
+ int is = flags & RPMSENSE_MISSINGOK;
+ if (is) has_old_suggests = is;
+ return is;
+}
+int32_t is_not_old_suggests(int32_t flags) {
+ return !is_old_suggests(flags);
+}
+
+typedef int (*callback_list_str)(char *s, int slen, const char *name, const uint32_t flags, const char *evr, void *param);
static int
-callback_list_str_xpush(char *s, int slen, const char *name, rpmsenseFlags flags, const char *evr, __attribute__((unused)) void *param) {
+callback_list_str_xpush(char *s, int slen, const char *name, uint32_t flags, const char *evr, __attribute__((unused)) void *param) {
dSP;
if (s)
mXPUSHs(newSVpv(s, slen));
@@ -279,11 +301,26 @@ callback_list_str_xpush(char *s, int slen, const char *name, rpmsenseFlags flags
return 0;
}
static int
-callback_list_str_xpush_requires(char *s, int slen, const char *name, const rpmsenseFlags flags, const char *evr, __attribute__((unused)) void *param) {
+callback_list_str_xpush_requires(char *s, int slen, const char *name, const uint32_t flags, const char *evr, __attribute__((unused)) void *param) {
dSP;
if (s)
mXPUSHs(newSVpv(s, slen));
- else {
+ else if (is_not_old_suggests(flags)) {
+ char buff[4096];
+ int len = print_list_entry(buff, sizeof(buff)-1, name, flags, evr);
+ if (len >= 0)
+ mXPUSHs(newSVpv(buff, len));
+ }
+ PUTBACK;
+ /* returning zero indicates to continue processing */
+ return 0;
+}
+static int
+callback_list_str_xpush_old_suggests(char *s, int slen, const char *name, uint32_t flags, const char *evr, __attribute__((unused)) void *param) {
+ dSP;
+ if (s)
+ mXPUSHs(newSVpv(s, slen));
+ else if (is_old_suggests(flags)) {
char buff[4096];
int len = print_list_entry(buff, sizeof(buff)-1, name, flags, evr);
if (len >= 0)
@@ -295,14 +332,15 @@ callback_list_str_xpush_requires(char *s, int slen, const char *name, const rpms
}
struct cb_overlap_s {
- rpmsenseFlags flags;
- int direction; /* indicate to compare the above at left or right to the iteration element */
char *name;
+ int32_t flags;
char *evr;
+ int direction; /* indicate to compare the above at left or right to the iteration element */
+ int b_nopromote;
};
static int
-callback_list_str_overlap(char *s, int slen, const char *name, rpmsenseFlags flags, const char *evr, void *param) {
+callback_list_str_overlap(char *s, int slen, const char *name, uint32_t flags, const char *evr, void *param) {
struct cb_overlap_s *os = (struct cb_overlap_s *)param;
int result = 0;
char *eos = NULL;
@@ -312,11 +350,7 @@ callback_list_str_overlap(char *s, int slen, const char *name, rpmsenseFlags fla
/* we need to extract name, flags and evr from a full sense information, store result in local copy */
if (s) {
- if (slen) {
- eos = s + slen;
- eosc = *eos;
- *eos = 0;
- }
+ if (slen) { eos = s + slen; eosc = *eos; *eos = 0; }
name = s;
while (*s && *s != ' ' && *s != '[' && *s != '<' && *s != '>' && *s != '=') ++s;
if (*s) {
@@ -335,17 +369,14 @@ callback_list_str_overlap(char *s, int slen, const char *name, rpmsenseFlags fla
}
/* mark end of name */
- if (eon) {
- eonc = *eon;
- *eon = 0;
- }
+ if (eon) { eonc = *eon; *eon = 0; }
/* names should be equal, else it will not overlap */
if (!strcmp(name, os->name)) {
/* perform overlap according to direction needed, negative for left */
if (os->direction < 0)
- result = ranges_overlap(os->flags, os->evr, flags, (char *) evr);
+ result = ranges_overlap(os->flags, os->evr, flags, (char *) evr, os->b_nopromote);
else
- result = ranges_overlap(flags, (char *) evr, os->flags, os->evr);
+ result = ranges_overlap(flags, (char *) evr, os->flags, os->evr, os->b_nopromote);
}
/* fprintf(stderr, "cb_list_str_overlap result=%d, os->direction=%d, os->name=%s, os->evr=%s, name=%s, evr=%s\n",
@@ -359,7 +390,7 @@ callback_list_str_overlap(char *s, int slen, const char *name, rpmsenseFlags fla
}
static int
-return_list_str(char *s, const Header header, rpmTag tag_name, rpmTag tag_flags, rpmTag tag_version, callback_list_str f, void *param) {
+return_list_str(char *s, Header header, int32_t tag_name, int32_t tag_flags, int32_t tag_version, callback_list_str f, void *param) {
int count = 0;
if (s != NULL) {
@@ -367,29 +398,23 @@ return_list_str(char *s, const Header header, rpmTag tag_name, rpmTag tag_flags,
if (tag_flags && tag_version) {
while(ps != NULL) {
++count;
- if (f(s, ps-s, NULL, 0, NULL, param))
- return -count;
+ if (f(s, ps-s, NULL, 0, NULL, param)) return -count;
s = ps + 1; ps = strchr(s, '@');
}
++count;
- if (f(s, 0, NULL, 0, NULL, param))
- return -count;
+ if (f(s, 0, NULL, 0, NULL, param)) return -count;
} else {
char *eos;
while(ps != NULL) {
*ps = 0; eos = strchr(s, '['); if (!eos) eos = strchr(s, ' ');
++count;
- if (f(s, eos ? eos-s : ps-s, NULL, 0, NULL, param)) {
- *ps = '@';
- return -count;
- }
+ if (f(s, eos ? eos-s : ps-s, NULL, 0, NULL, param)) { *ps = '@'; return -count; }
*ps = '@'; /* restore in memory modified char */
s = ps + 1; ps = strchr(s, '@');
}
eos = strchr(s, '['); if (!eos) eos = strchr(s, ' ');
++count;
- if (f(s, eos ? eos-s : 0, NULL, 0, NULL, param))
- return -count;
+ if (f(s, eos ? eos-s : 0, NULL, 0, NULL, param)) return -count;
}
} else if (header) {
struct rpmtd_s list, flags, list_evr;
@@ -419,20 +444,18 @@ return_list_str(char *s, const Header header, rpmTag tag_name, rpmTag tag_flags,
}
static int
-xpush_simple_list_str(const Header header, rpmTag tag_name) {
+xpush_simple_list_str(Header header, int32_t tag_name) {
dSP;
if (header) {
struct rpmtd_s list;
const char *val;
int size;
- if (!headerGet(header, tag_name, &list, HEADERGET_DEFAULT))
- return 0;
+ if (!headerGet(header, tag_name, &list, HEADERGET_DEFAULT)) return 0;
size = rpmtdCount(&list);
- EXTEND(SP, size);
while ((val = rpmtdNextString(&list))) {
- mPUSHs(newSVpv(val, 0));
+ mXPUSHs(newSVpv(val, 0));
}
rpmtdFreeData(&list);
PUTBACK;
@@ -440,18 +463,33 @@ xpush_simple_list_str(const Header header, rpmTag tag_name) {
} else return 0;
}
-static void
-return_list_number(const Header header, rpmTag tag_name) {
+void
+return_list_int32_t(Header header, int32_t tag_name) {
+ dSP;
+ if (header) {
+ struct rpmtd_s list;
+
+ if (headerGet(header, tag_name, &list, HEADERGET_DEFAULT)) {
+ uint32_t *val;
+ while ((val = rpmtdNextUint32(&list)))
+ mXPUSHs(newSViv(*val));
+ rpmtdFreeData(&list);
+ }
+ }
+ PUTBACK;
+}
+
+void
+return_list_uint_16(Header header, int32_t tag_name) {
dSP;
if (header) {
struct rpmtd_s list;
if (headerGet(header, tag_name, &list, HEADERGET_DEFAULT)) {
int count = rpmtdCount(&list);
int i;
- EXTEND(SP, count);
+ uint16_t *list_ = list.data;
for(i = 0; i < count; i++) {
- rpmtdNext(&list);
- mPUSHs(newSViv(rpmtdGetNumber(&list)));
+ mXPUSHs(newSViv(list_[i]));
}
rpmtdFreeData(&list);
}
@@ -459,37 +497,34 @@ return_list_number(const Header header, rpmTag tag_name) {
PUTBACK;
}
-static void
-return_list_tag_modifier(const Header header, rpmTag tag_name) {
+void
+return_list_tag_modifier(Header header, int32_t tag_name) {
dSP;
int i;
struct rpmtd_s td;
- if (!headerGet(header, tag_name, &td, HEADERGET_DEFAULT))
- return;
+ if (!headerGet(header, tag_name, &td, HEADERGET_DEFAULT)) return;
int count = rpmtdCount(&td);
- rpmtdInit(&td);
+ int32_t *list = td.data;
for (i = 0; i < count; i++) {
char buff[15];
char *s = buff;
- int32_t tag;
- rpmtdNext(&td);
- tag = rpmtdGetNumber(&td);
-
- if (tag_name == RPMTAG_FILEFLAGS) {
- if (tag & RPMFILE_CONFIG) *s++ = 'c';
- if (tag & RPMFILE_DOC) *s++ = 'd';
- if (tag & RPMFILE_GHOST) *s++ = 'g';
- if (tag & RPMFILE_LICENSE) *s++ = 'l';
- if (tag & RPMFILE_MISSINGOK) *s++ = 'm';
- if (tag & RPMFILE_NOREPLACE) *s++ = 'n';
- if (tag & RPMFILE_SPECFILE) *s++ = 'S';
- if (tag & RPMFILE_README) *s++ = 'R';
- if (tag & RPMFILE_EXCLUDE) *s++ = 'e';
- if (tag & RPMFILE_ICON) *s++ = 'i';
- if (tag & RPMFILE_UNPATCHED) *s++ = 'u';
- if (tag & RPMFILE_PUBKEY) *s++ = 'p';
- } else {
+ switch (tag_name) {
+ case RPMTAG_FILEFLAGS:
+ if (list[i] & RPMFILE_CONFIG) *s++ = 'c';
+ if (list[i] & RPMFILE_DOC) *s++ = 'd';
+ if (list[i] & RPMFILE_GHOST) *s++ = 'g';
+ if (list[i] & RPMFILE_LICENSE) *s++ = 'l';
+ if (list[i] & RPMFILE_MISSINGOK) *s++ = 'm';
+ if (list[i] & RPMFILE_NOREPLACE) *s++ = 'n';
+ if (list[i] & RPMFILE_SPECFILE) *s++ = 'S';
+ if (list[i] & RPMFILE_README) *s++ = 'R';
+ if (list[i] & RPMFILE_EXCLUDE) *s++ = 'e';
+ if (list[i] & RPMFILE_ICON) *s++ = 'i';
+ if (list[i] & RPMFILE_UNPATCHED) *s++ = 'u';
+ if (list[i] & RPMFILE_PUBKEY) *s++ = 'p';
+ break;
+ default:
rpmtdFreeData(&td);
return;
}
@@ -500,15 +535,16 @@ return_list_tag_modifier(const Header header, rpmTag tag_name) {
PUTBACK;
}
-static void
-return_list_tag(const URPM__Package pkg, rpmTag tag_name) {
+void
+return_list_tag(URPM__Package pkg, int32_t tag_name) {
dSP;
if (pkg->h != NULL) {
struct rpmtd_s td;
if (headerGet(pkg->h, tag_name, &td, HEADERGET_DEFAULT)) {
+ void *list = td.data;
int32_t count = rpmtdCount(&td);
if (tag_name == RPMTAG_ARCH)
- mXPUSHs(newSVpv(headerIsEntry(pkg->h, RPMTAG_SOURCERPM) ? rpmtdGetString(&td) : "src", 0));
+ mXPUSHs(newSVpv(headerIsEntry(pkg->h, RPMTAG_SOURCERPM) ? (char *) list : "src", 0));
else
switch (rpmtdType(&td)) {
case RPM_NULL_TYPE:
@@ -519,25 +555,27 @@ return_list_tag(const URPM__Package pkg, rpmTag tag_name) {
case RPM_INT32_TYPE:
{
int i;
- EXTEND(SP, count);
+ int *r;
+ r = (int *)list;
for (i=0; i < count; i++) {
- rpmtdNext(&td);
- mPUSHs(newSViv(rpmtdGetNumber(&td)));
+ mXPUSHs(newSViv(r[i]));
}
}
break;
case RPM_STRING_TYPE:
- mPUSHs(newSVpv(rpmtdGetString(&td), 0));
+ mXPUSHs(newSVpv((char *) list, 0));
break;
case RPM_BIN_TYPE:
break;
case RPM_STRING_ARRAY_TYPE:
{
int i;
- EXTEND(SP, count);
- rpmtdInit(&td);
- for (i = 0; i < count; i++)
- mPUSHs(newSVpv(rpmtdNextString(&td), 0));
+ char **s;
+
+ s = (char **)list;
+ for (i = 0; i < count; i++) {
+ mXPUSHs(newSVpv(s[i], 0));
+ }
}
break;
case RPM_I18NSTRING_TYPE:
@@ -583,21 +621,18 @@ return_list_tag(const URPM__Package pkg, rpmTag tag_name) {
case RPMTAG_SUMMARY:
mXPUSHs(newSVpv(pkg->summary, 0));
break;
- default:
- croak("unexpected tag %s", tag_name);
- break;
}
}
PUTBACK;
}
-static void
-return_files(const Header header, int filter_mode) {
+void
+return_files(Header header, int filter_mode) {
dSP;
if (header) {
char buff[4096];
- char *p; const char *s;
+ char *p, *s;
STRLEN len;
unsigned int i;
@@ -617,19 +652,17 @@ return_files(const Header header, int filter_mode) {
char **baseNames = td_baseNames.data;
char **dirNames = td_dirNames.data;
int32_t *dirIndexes = td_dirIndexes.data;
- int is_oldfilenames = !baseNames || !dirNames || !dirIndexes;
- if (is_oldfilenames) {
- if (!headerGet(header, RPMTAG_OLDFILENAMES, &td_list, HEADERGET_DEFAULT))
- return;
- rpmtdInit(&td_list);
+ char **list = NULL;
+ if (!baseNames || !dirNames || !dirIndexes) {
+ if (!headerGet(header, RPMTAG_OLDFILENAMES, &td_list, HEADERGET_DEFAULT)) return;
+ list = td_list.data;
}
- rpm_count_t count = is_oldfilenames ? rpmtdCount(&td_list) : rpmtdCount(&td_baseNames);
- for(i = 0; i < count; i++) {
- if (is_oldfilenames) {
- s = rpmtdNextString(&td_list);
- len = strlen(s);
+ for(i = 0; i < rpmtdCount(&td_baseNames); i++) {
+ if (list) {
+ s = list[i];
+ len = strlen(list[i]);
} else {
len = strlen(dirNames[dirIndexes[i]]);
if (len >= sizeof(buff)) continue;
@@ -648,15 +681,14 @@ return_files(const Header header, int filter_mode) {
mXPUSHs(newSVpv(s, len));
}
- rpmtdFreeData(&td_baseNames);
- rpmtdFreeData(&td_dirNames);
- if (is_oldfilenames)
- rpmtdFreeData(&td_list);
+ free(baseNames);
+ free(dirNames);
+ free(list);
}
PUTBACK;
}
-static void
+void
return_problems(rpmps ps, int translate_message, int raw_message) {
dSP;
if (ps && rpmpsNumProblems(ps) > 0) {
@@ -720,9 +752,9 @@ return_problems(rpmps ps, int translate_message, int raw_message) {
}
static char *
-pack_list(const Header header, rpmTag tag_name, rpmTag tag_flags, rpmTag tag_version) {
+pack_list(Header header, int32_t tag_name, int32_t tag_flags, int32_t tag_version, int32_t (*check_flag)(int32_t)) {
char buff[65536];
- rpmTag *flags = NULL;
+ int32_t *flags = NULL;
char **list_evr = NULL;
unsigned int i;
char *p = buff;
@@ -735,6 +767,7 @@ pack_list(const Header header, rpmTag tag_name, rpmTag tag_flags, rpmTag tag_ver
if (tag_flags && headerGet(header, tag_flags, &td_flags, HEADERGET_DEFAULT)) flags = td_flags.data;
if (tag_version && headerGet(header, tag_version, &td_list_evr, HEADERGET_DEFAULT)) list_evr = td_list_evr.data;
for(i = 0; i < rpmtdCount(&td); i++) {
+ if (check_flag && !check_flag(flags[i])) continue;
int len = print_list_entry(p, sizeof(buff)-(p-buff)-1, list[i], flags ? flags[i] : 0, list_evr ? list_evr[i] : NULL);
if (len < 0) continue;
p += len;
@@ -750,30 +783,35 @@ pack_list(const Header header, rpmTag tag_name, rpmTag tag_flags, rpmTag tag_ver
}
static void
-pack_header(const URPM__Package pkg) {
+pack_header(URPM__Package pkg) {
if (pkg->h) {
if (pkg->info == NULL) {
char buff[1024];
- const char *p = buff;
- const char *nvr = headerGetAsString(pkg->h, RPMTAG_NVR);
- const char *arch = get_arch(pkg->h);
+ char *p = buff;
+ char *name = get_name(pkg->h, RPMTAG_NAME);
+ char *version = get_name(pkg->h, RPMTAG_VERSION);
+ char *release = get_name(pkg->h, RPMTAG_RELEASE);
+ char *arch = headerIsEntry(pkg->h, RPMTAG_SOURCERPM) ? get_name(pkg->h, RPMTAG_ARCH) : "src";
- p += 1 + snprintf(buff, sizeof(buff), "%s.%s@%d@%d@%s", nvr, arch,
+ p += 1 + snprintf(buff, sizeof(buff), "%s-%s-%s.%s@%d@%d@%s", name, version, release, arch,
get_int(pkg->h, RPMTAG_EPOCH), get_int(pkg->h, RPMTAG_SIZE),
get_name(pkg->h, RPMTAG_GROUP));
pkg->info = memcpy(malloc(p-buff), buff, p-buff);
}
if (pkg->filesize == 0) pkg->filesize = get_filesize(pkg->h);
- if (pkg->requires == NULL && pkg->suggests == NULL) {
- pkg->requires = pack_list(pkg->h, RPMTAG_REQUIRENAME, RPMTAG_REQUIREFLAGS, RPMTAG_REQUIREVERSION);
- pkg->suggests = pack_list(pkg->h, RPMTAG_SUGGESTSNAME, 0, 0);
- }
+ if (pkg->requires == NULL && pkg->suggests == NULL)
+ has_old_suggests = 0;
+ pkg->requires = pack_list(pkg->h, RPMTAG_REQUIRENAME, RPMTAG_REQUIREFLAGS, RPMTAG_REQUIREVERSION, is_not_old_suggests);
+ if (has_old_suggests)
+ pkg->suggests = pack_list(pkg->h, RPMTAG_REQUIRENAME, RPMTAG_REQUIREFLAGS, RPMTAG_REQUIREVERSION, is_old_suggests);
+ else
+ pkg->suggests = pack_list(pkg->h, RPMTAG_SUGGESTSNAME, 0, 0, NULL);
if (pkg->obsoletes == NULL)
- pkg->obsoletes = pack_list(pkg->h, RPMTAG_OBSOLETENAME, RPMTAG_OBSOLETEFLAGS, RPMTAG_OBSOLETEVERSION);
+ pkg->obsoletes = pack_list(pkg->h, RPMTAG_OBSOLETENAME, RPMTAG_OBSOLETEFLAGS, RPMTAG_OBSOLETEVERSION, NULL);
if (pkg->conflicts == NULL)
- pkg->conflicts = pack_list(pkg->h, RPMTAG_CONFLICTNAME, RPMTAG_CONFLICTFLAGS, RPMTAG_CONFLICTVERSION);
+ pkg->conflicts = pack_list(pkg->h, RPMTAG_CONFLICTNAME, RPMTAG_CONFLICTFLAGS, RPMTAG_CONFLICTVERSION, NULL);
if (pkg->provides == NULL)
- pkg->provides = pack_list(pkg->h, RPMTAG_PROVIDENAME, RPMTAG_PROVIDEFLAGS, RPMTAG_PROVIDEVERSION);
+ pkg->provides = pack_list(pkg->h, RPMTAG_PROVIDENAME, RPMTAG_PROVIDEFLAGS, RPMTAG_PROVIDEVERSION, NULL);
if (pkg->summary == NULL) {
char *summary = get_name(pkg->h, RPMTAG_SUMMARY);
int len = 1 + strlen(summary);
@@ -781,13 +819,13 @@ pack_header(const URPM__Package pkg) {
pkg->summary = memcpy(malloc(len), summary, len);
}
- _header_free(pkg);
+ if (!(pkg->flag & FLAG_NO_HEADER_FREE)) pkg->h =headerFree(pkg->h);
pkg->h = NULL;
}
}
static void
-update_hash_entry(HV *hash, const char *name, STRLEN len, int force, IV use_sense, const URPM__Package pkg) {
+update_hash_entry(HV *hash, char *name, STRLEN len, int force, IV use_sense, URPM__Package pkg) {
SV** isv;
if (!len) len = strlen(name);
@@ -813,24 +851,24 @@ update_hash_entry(HV *hash, const char *name, STRLEN len, int force, IV use_sens
}
static void
-update_provide_entry(const char *name, STRLEN len, int force, IV use_sense, const URPM__Package pkg, HV *provides) {
+update_provide_entry(char *name, STRLEN len, int force, IV use_sense, URPM__Package pkg, HV *provides) {
update_hash_entry(provides, name, len, force, use_sense, pkg);
}
static void
-update_provides(const URPM__Package pkg, HV *provides) {
+update_provides(URPM__Package pkg, HV *provides) {
if (pkg->h) {
int len;
struct rpmtd_s td, td_flags;
- rpmsenseFlags *flags = NULL;
+ int32_t *flags = NULL;
unsigned int i;
/* examine requires for files which need to be marked in provides */
if (headerGet(pkg->h, RPMTAG_REQUIRENAME, &td, HEADERGET_DEFAULT)) {
+ char **list = td.data;
for (i = 0; i < rpmtdCount(&td); ++i) {
- const char *s = rpmtdNextString(&td);
- len = strlen(s);
- if (s[0] == '/') (void)hv_fetch(provides, s, len, 1);
+ len = strlen(list[i]);
+ if (list[i][0] == '/') (void)hv_fetch(provides, list[i], len, 1);
}
}
@@ -880,15 +918,16 @@ update_provides(const URPM__Package pkg, HV *provides) {
}
static void
-update_obsoletes(const URPM__Package pkg, HV *obsoletes) {
+update_obsoletes(URPM__Package pkg, HV *obsoletes) {
if (pkg->h) {
struct rpmtd_s td;
/* update all provides */
if (headerGet(pkg->h, RPMTAG_OBSOLETENAME, &td, HEADERGET_DEFAULT)) {
+ char **list = td.data;
unsigned int i;
for (i = 0; i < rpmtdCount(&td); ++i)
- update_hash_entry(obsoletes, rpmtdNextString(&td), 0, 1, 0, pkg);
+ update_hash_entry(obsoletes, list[i], 0, 1, 0, pkg);
}
} else {
char *ps, *s;
@@ -909,9 +948,10 @@ update_obsoletes(const URPM__Package pkg, HV *obsoletes) {
}
static void
-update_provides_files(const URPM__Package pkg, HV *provides) {
+update_provides_files(URPM__Package pkg, HV *provides) {
if (pkg->h) {
STRLEN len;
+ char **list = NULL;
unsigned int i;
struct rpmtd_s td_baseNames, td_dirIndexes, td_dirNames;
@@ -937,26 +977,25 @@ update_provides_files(const URPM__Package pkg, HV *provides) {
update_provide_entry(buff, p-buff, 0, 0, pkg, provides);
}
- rpmtdFreeData(&td_baseNames);
- rpmtdFreeData(&td_dirNames);
+ free(baseNames);
+ free(dirNames);
} else {
struct rpmtd_s td;
-
- if (headerGet(pkg->h, RPMTAG_OLDFILENAMES, &td, HEADERGET_DEFAULT)) {
+ headerGet(pkg->h, RPMTAG_OLDFILENAMES, &td, HEADERGET_DEFAULT);
+ if (list) {
for (i = 0; i < rpmtdCount(&td); i++) {
- const char *s = rpmtdNextString(&td);
- len = strlen(s);
+ len = strlen(list[i]);
- update_provide_entry(s, len, 0, 0, pkg, provides);
+ update_provide_entry(list[i], len, 0, 0, pkg, provides);
}
- rpmtdFreeData(&td);
+ free(list);
}
}
}
}
-static FD_t
+FD_t
open_archive(char *filename, int *empty_archive) {
int fd;
FD_t rfd = NULL;
@@ -1038,7 +1077,7 @@ parse_line(AV *depslist, HV *provides, HV *obsoletes, URPM__Package pkg, char *b
pkg->info = memcpy(malloc(data_len), data, data_len);
pkg->flag &= ~FLAG_ID;
pkg->flag |= 1 + av_len(depslist);
- sv_pkg = sv_setref_pv(newSVpvs(""), "URPM::Package",
+ sv_pkg = sv_setref_pv(newSVpv("", 0), "URPM::Package",
_pkg = memcpy(malloc(sizeof(struct s_Package)), pkg, sizeof(struct s_Package)));
if (call_package_callback(urpm, sv_pkg, callback)) {
if (provides) update_provides(_pkg, provides);
@@ -1153,7 +1192,7 @@ update_header(char *filename, URPM__Package pkg, __attribute__((unused)) int kee
if (fd != NULL && rpmReadPackageFile(ts, fd, filename, &header) == 0 && header) {
Fclose(fd);
- _header_free(pkg);
+ if (pkg->h && !(pkg->flag & FLAG_NO_HEADER_FREE)) pkg->h = headerFree(pkg->h);
pkg->h = header;
pkg->flag &= ~FLAG_NO_HEADER_FREE;
@@ -1168,7 +1207,7 @@ update_header(char *filename, URPM__Package pkg, __attribute__((unused)) int kee
close(d);
if (fd != NULL) {
- _header_free(pkg);
+ if (pkg->h && !(pkg->flag & FLAG_NO_HEADER_FREE)) pkg->h = headerFree(pkg->h);
pkg->h = headerRead(fd, HEADER_MAGIC_YES);
pkg->flag &= ~FLAG_NO_HEADER_FREE;
Fclose(fd);
@@ -1192,9 +1231,9 @@ read_config_files(int force) {
return rc;
}
-static rpmVSFlags
+static void
ts_nosignature(rpmts ts) {
- return rpmtsSetVSFlags(ts, _RPMVSF_NODIGESTS | _RPMVSF_NOSIGNATURES);
+ rpmtsSetVSFlags(ts, _RPMVSF_NODIGESTS | _RPMVSF_NOSIGNATURES);
}
static void *rpmRunTransactions_callback(__attribute__((unused)) const void *h,
@@ -1295,11 +1334,20 @@ static void *rpmRunTransactions_callback(__attribute__((unused)) const void *h,
i = POPi;
fd = fdDup(i);
if (fd) {
+#ifdef RPM490
fd = fdLink(fd);
- Fcntl(fd, F_SETFD, (void *)1); /* necessary to avoid forked/execed process to lock removable media */
+#else
+ fd = fdLink(fd, "persist perl-URPM");
+#endif
+ Fcntl(fd, F_SETFD, (void *)1); /* necessary to avoid forked/execed process to lock removable */
}
PUTBACK;
} else if (callback == td->callback_close) {
+#ifdef RPM490
+ fd = fdFree(fd);
+#else
+ fd = fdFree(fd, "persist perl-URPM");
+#endif
if (fd) {
Fclose(fd);
fd = NULL;
@@ -1312,8 +1360,7 @@ static void *rpmRunTransactions_callback(__attribute__((unused)) const void *h,
return callback == td->callback_open ? fd : NULL;
}
-static rpmTag
-rpmtag_from_string(char *tag)
+int rpmtag_from_string(char *tag)
{
if (!strcmp(tag, "name"))
return RPMTAG_NAME;
@@ -1334,44 +1381,6 @@ rpmtag_from_string(char *tag)
else croak("unknown tag [%s]", tag);
}
-static int compare_evrs(int lepoch, char*lversion, char*lrelease, int repoch, char*rversion, char*rrelease) {
- int compare;
- compare = lepoch - repoch;
- if (!compare) {
- compare = rpmvercmp(lversion, rversion);
- if (!compare && rrelease)
- compare = rpmvercmp(lrelease, rrelease);
- }
- return compare;
-}
-
-static int get_e_v_r(URPM__Package pkg, int *epoch, char **version, char **release, char **arch) {
- if (pkg->info) {
- char *s, *eos;
-
- if ((s = strchr(pkg->info, '@')) != NULL) {
- if ((eos = strchr(s+1, '@')) != NULL)
- *eos = 0; /* mark end of string to enable searching backwards */
- *epoch = atoi(s+1);
- if (eos != NULL) *eos = '@';
- } else
- *epoch = 0;
- get_fullname_parts(pkg, NULL, version, release, arch, &eos);
- /* temporarily mark end of each substring */
- (*release)[-1] = 0;
- (*arch)[-1] = 0;
- return 1;
- } else if (pkg->h) {
- *epoch = get_int(pkg->h, RPMTAG_EPOCH);
- *version = get_name(pkg->h, RPMTAG_VERSION);
- *release = get_name(pkg->h, RPMTAG_RELEASE);
- *arch = get_arch(pkg->h);
- return 1;
- }
- return 0;
-}
-
-
MODULE = URPM PACKAGE = URPM::Package PREFIX = Pkg_
void
@@ -1386,7 +1395,7 @@ Pkg_DESTROY(pkg)
free(pkg->provides);
free(pkg->rflags);
free(pkg->summary);
- _header_free(pkg);
+ if (pkg->h && !(pkg->flag & FLAG_NO_HEADER_FREE)) pkg->h = headerFree(pkg->h);
free(pkg);
void
@@ -1445,7 +1454,7 @@ Pkg_arch(pkg)
get_fullname_parts(pkg, NULL, NULL, NULL, &arch, &eos);
mXPUSHs(newSVpv(arch, eos-arch));
} else if (pkg->h) {
- mXPUSHs(newSVpv(get_arch(pkg->h), 0));
+ mXPUSHs(newSVpv(headerIsEntry(pkg->h, RPMTAG_SOURCERPM) ? get_name(pkg->h, RPMTAG_ARCH) : "src", 0));
}
int
@@ -1471,6 +1480,19 @@ Pkg_is_arch_compat__XS(pkg)
OUTPUT:
RETVAL
+int
+Pkg_is_platform_compat(pkg)
+ URPM::Package pkg
+ INIT:
+ CODE:
+ croak("is_platform_compat() is available only since rpm 4.4.8");
+ { /* to match last } and avoid another #ifdef for it */
+ RETVAL = 0;
+ }
+
+ OUTPUT:
+ RETVAL
+
void
Pkg_summary(pkg)
URPM::Package pkg
@@ -1484,57 +1506,94 @@ Pkg_summary(pkg)
void
Pkg_description(pkg)
URPM::Package pkg
- ALIAS:
- sourcerpm = 1
- packager = 2
- buildhost = 3
- url = 4
- license = 5
- distribution = 6
- vendor = 7
- os = 8
- payload_format = 9
- disttag = 10
PPCODE:
if (pkg->h)
- switch (ix) {
- case 0:
- mXPUSHs(newSVpv_utf8(get_name(pkg->h, RPMTAG_DESCRIPTION), 0)); break;
- case 1:
- mXPUSHs(newSVpv(get_name(pkg->h, RPMTAG_SOURCERPM), 0)); break;
- case 2:
- mXPUSHs(newSVpv_utf8(get_name(pkg->h, RPMTAG_PACKAGER), 0)); break;
- case 3:
- mXPUSHs(newSVpv(get_name(pkg->h, RPMTAG_BUILDHOST), 0)); break;
- case 4:
- mXPUSHs(newSVpv(get_name(pkg->h, RPMTAG_URL), 0)); break;
- case 5:
- mXPUSHs(newSVpv(get_name(pkg->h, RPMTAG_LICENSE), 0)); break;
- case 6:
- mXPUSHs(newSVpv(get_name(pkg->h, RPMTAG_DISTRIBUTION), 0)); break;
- case 7:
- mXPUSHs(newSVpv(get_name(pkg->h, RPMTAG_VENDOR), 0)); break;
- case 8:
- mXPUSHs(newSVpv(get_name(pkg->h, RPMTAG_OS), 0)); break;
- case 9:
- mXPUSHs(newSVpv(get_name(pkg->h, RPMTAG_PAYLOADFORMAT), 0)); break;
- case 10:
- mXPUSHs(newSVpv(get_name(pkg->h, RPMTAG_DISTTAG), 0)); break;
- }
+ mXPUSHs(newSVpv_utf8(get_name(pkg->h, RPMTAG_DESCRIPTION), 0));
+
+void
+Pkg_sourcerpm(pkg)
+ URPM::Package pkg
+ PPCODE:
+ if (pkg->h)
+ mXPUSHs(newSVpv(get_name(pkg->h, RPMTAG_SOURCERPM), 0));
+
+void
+Pkg_packager(pkg)
+ URPM::Package pkg
+ PPCODE:
+ if (pkg->h)
+ mXPUSHs(newSVpv_utf8(get_name(pkg->h, RPMTAG_PACKAGER), 0));
+
+void
+Pkg_buildhost(pkg)
+ URPM::Package pkg
+ PPCODE:
+ if (pkg->h)
+ mXPUSHs(newSVpv(get_name(pkg->h, RPMTAG_BUILDHOST), 0));
int
Pkg_buildtime(pkg)
URPM::Package pkg
- ALIAS:
- installtid = 1
CODE:
if (pkg->h)
- RETVAL = get_int(pkg->h, ix == 1 ? RPMTAG_INSTALLTID : RPMTAG_BUILDTIME);
+ RETVAL = get_int(pkg->h, RPMTAG_BUILDTIME);
+ else
+ RETVAL = 0;
+ OUTPUT:
+ RETVAL
+
+int
+Pkg_installtid(pkg)
+ URPM::Package pkg
+ CODE:
+ if (pkg->h)
+ RETVAL = get_int(pkg->h, RPMTAG_INSTALLTID);
else
RETVAL = 0;
OUTPUT:
RETVAL
+void
+Pkg_url(pkg)
+ URPM::Package pkg
+ PPCODE:
+ if (pkg->h)
+ mXPUSHs(newSVpv(get_name(pkg->h, RPMTAG_URL), 0));
+
+void
+Pkg_license(pkg)
+ URPM::Package pkg
+ PPCODE:
+ if (pkg->h)
+ mXPUSHs(newSVpv(get_name(pkg->h, RPMTAG_LICENSE), 0));
+
+void
+Pkg_distribution(pkg)
+ URPM::Package pkg
+ PPCODE:
+ if (pkg->h)
+ mXPUSHs(newSVpv(get_name(pkg->h, RPMTAG_DISTRIBUTION), 0));
+
+void
+Pkg_vendor(pkg)
+ URPM::Package pkg
+ PPCODE:
+ if (pkg->h)
+ mXPUSHs(newSVpv(get_name(pkg->h, RPMTAG_VENDOR), 0));
+
+void
+Pkg_os(pkg)
+ URPM::Package pkg
+ PPCODE:
+ if (pkg->h)
+ mXPUSHs(newSVpv(get_name(pkg->h, RPMTAG_OS), 0));
+
+void
+Pkg_payload_format(pkg)
+ URPM::Package pkg
+ PPCODE:
+ if (pkg->h)
+ mXPUSHs(newSVpv(get_name(pkg->h, RPMTAG_PAYLOADFORMAT), 0));
void
Pkg_fullname(pkg)
@@ -1554,24 +1613,25 @@ Pkg_fullname(pkg)
if (version - name < 1 || release - version < 1 || arch - release < 1)
croak("invalid fullname");
EXTEND(SP, 4);
- mPUSHs(newSVpv(name, version-name-1));
- mPUSHs(newSVpv(version, release-version-1));
- mPUSHs(newSVpv(release, arch-release-1));
- mPUSHs(newSVpv(arch, eos-arch));
+ PUSHs(sv_2mortal(newSVpv(name, version-name-1)));
+ PUSHs(sv_2mortal(newSVpv(version, release-version-1)));
+ PUSHs(sv_2mortal(newSVpv(release, arch-release-1)));
+ PUSHs(sv_2mortal(newSVpv(arch, eos-arch)));
}
} else if (pkg->h) {
- char *arch = get_arch(pkg->h);
+ char *name = get_name(pkg->h, RPMTAG_NAME);
+ char *version = get_name(pkg->h, RPMTAG_VERSION);
+ char *release = get_name(pkg->h, RPMTAG_RELEASE);
+ char *arch = headerIsEntry(pkg->h, RPMTAG_SOURCERPM) ? get_name(pkg->h, RPMTAG_ARCH) : "src";
if (gimme == G_SCALAR) {
- char *s = headerGetAsString(pkg->h, RPMTAG_NVR);
- mXPUSHs(newSVpvf("%s.%s", s, arch));
- free(s);
+ mXPUSHs(newSVpvf("%s-%s-%s.%s", name, version, release, arch));
} else if (gimme == G_ARRAY) {
EXTEND(SP, 4);
- mPUSHs(newSVpv(get_name(pkg->h, RPMTAG_NAME), 0));
- mPUSHs(newSVpv(get_name(pkg->h, RPMTAG_VERSION), 0));
- mPUSHs(newSVpv(get_name(pkg->h, RPMTAG_RELEASE), 0));
- mPUSHs(newSVpv(arch, 0));
+ PUSHs(sv_2mortal(newSVpv(name, 0)));
+ PUSHs(sv_2mortal(newSVpv(version, 0)));
+ PUSHs(sv_2mortal(newSVpv(release, 0)));
+ PUSHs(sv_2mortal(newSVpv(arch, 0)));
}
}
@@ -1583,8 +1643,7 @@ Pkg_epoch(pkg)
char *s, *eos;
if ((s = strchr(pkg->info, '@')) != NULL) {
- if ((eos = strchr(s+1, '@')) != NULL)
- *eos = 0; /* mark end of string to enable searching backwards */
+ if ((eos = strchr(s+1, '@')) != NULL) *eos = 0; /* mark end of string to enable searching backwards */
RETVAL = atoi(s+1);
if (eos != NULL) *eos = '@';
} else
@@ -1601,16 +1660,57 @@ Pkg_compare_pkg(lpkg, rpkg)
URPM::Package rpkg
PREINIT:
int compare = 0;
- int lepoch, repoch;
- char *lversion, *lrelease, *larch;
- char *rversion, *rrelease, *rarch;
+ int lepoch;
+ char *lversion;
+ char *lrelease;
+ char *larch;
+ char *leos;
+ int repoch;
+ char *rversion;
+ char *rrelease;
+ char *rarch;
+ char *reos;
CODE:
if (lpkg == rpkg) RETVAL = 0;
else {
- if (!get_e_v_r(lpkg, &lepoch, &lversion, &lrelease, &larch))
- croak("undefined package");
+ if (lpkg->info) {
+ char *s;
+
+ if ((s = strchr(lpkg->info, '@')) != NULL) {
+ if ((leos = strchr(s+1, '@')) != NULL) *leos = 0; /* mark end of string to enable searching backwards */
+ lepoch = atoi(s+1);
+ if (leos != NULL) *leos = '@';
+ } else
+ lepoch = 0;
+ get_fullname_parts(lpkg, NULL, &lversion, &lrelease, &larch, &leos);
+ /* temporarily mark end of each substring */
+ lrelease[-1] = 0;
+ larch[-1] = 0;
+ } else if (lpkg->h) {
+ lepoch = get_int(lpkg->h, RPMTAG_EPOCH);
+ lversion = get_name(lpkg->h, RPMTAG_VERSION);
+ lrelease = get_name(lpkg->h, RPMTAG_RELEASE);
+ larch = headerIsEntry(lpkg->h, RPMTAG_SOURCERPM) ? get_name(lpkg->h, RPMTAG_ARCH) : "src";
+ } else croak("undefined package");
+ if (rpkg->info) {
+ char *s;
- if (!get_e_v_r(rpkg, &repoch, &rversion, &rrelease, &rarch)) {
+ if ((s = strchr(rpkg->info, '@')) != NULL) {
+ if ((reos = strchr(s+1, '@')) != NULL) *reos = 0; /* mark end of string to enable searching backwards */
+ repoch = atoi(s+1);
+ if (reos != NULL) *reos = '@';
+ } else
+ repoch = 0;
+ get_fullname_parts(rpkg, NULL, &rversion, &rrelease, &rarch, &reos);
+ /* temporarily mark end of each substring */
+ rrelease[-1] = 0;
+ rarch[-1] = 0;
+ } else if (rpkg->h) {
+ repoch = get_int(rpkg->h, RPMTAG_EPOCH);
+ rversion = get_name(rpkg->h, RPMTAG_VERSION);
+ rrelease = get_name(rpkg->h, RPMTAG_RELEASE);
+ rarch = headerIsEntry(rpkg->h, RPMTAG_SOURCERPM) ? get_name(rpkg->h, RPMTAG_ARCH) : "src";
+ } else {
/* restore info string modified */
if (lpkg->info) {
lrelease[-1] = '-';
@@ -1618,9 +1718,12 @@ Pkg_compare_pkg(lpkg, rpkg)
}
croak("undefined package");
}
- compare = compare_evrs(lepoch, lversion, lrelease, repoch, rversion, rrelease);
- // equal? compare arches too
+ compare = lepoch - repoch;
if (!compare) {
+ compare = rpmvercmp(lversion, rversion);
+ if (!compare) {
+ compare = rpmvercmp(lrelease, rrelease);
+ if (!compare) {
int lscore, rscore;
char *eolarch = strchr(larch, '@');
char *eorarch = strchr(rarch, '@');
@@ -1630,8 +1733,11 @@ Pkg_compare_pkg(lpkg, rpkg)
if (eorarch) *eorarch = 0; rscore = rpmMachineScore(RPM_MACHTABLE_INSTARCH, rarch);
if (lscore == 0) {
if (rscore == 0)
+#if 0
/* Nanar: TODO check this
* hu ?? what is the goal of strcmp, some of arch are equivalent */
+ compare = 0
+#endif
compare = strcmp(larch, rarch);
else
compare = -1;
@@ -1643,6 +1749,8 @@ Pkg_compare_pkg(lpkg, rpkg)
}
if (eolarch) *eolarch = '@';
if (eorarch) *eorarch = '@';
+ }
+ }
}
/* restore info string modified */
if (lpkg->info) {
@@ -1663,38 +1771,70 @@ Pkg_compare(pkg, evr)
URPM::Package pkg
char *evr
PREINIT:
- int _epoch, repoch = 0;
- char *_version, *_release, *_eos;
+ int compare = 0;
+ int _epoch;
+ char *_version;
+ char *_release;
+ char *_eos;
CODE:
- if (!get_e_v_r(pkg, &_epoch, &_version, &_release, &_eos))
- croak("undefined package");
+ if (pkg->info) {
+ char *s;
- char *epoch = NULL, *version, *release;
+ if ((s = strchr(pkg->info, '@')) != NULL) {
+ if ((_eos = strchr(s+1, '@')) != NULL) *_eos = 0; /* mark end of string to enable searching backwards */
+ _epoch = atoi(s+1);
+ if (_eos != NULL) *_eos = '@';
+ } else
+ _epoch = 0;
+ get_fullname_parts(pkg, NULL, &_version, &_release, &_eos, NULL);
+ /* temporarily mark end of each substring */
+ _release[-1] = 0;
+ _eos[-1] = 0;
+ } else if (pkg->h)
+ _epoch = get_int(pkg->h, RPMTAG_EPOCH);
+ else croak("undefined package");
+ if (!compare) {
+ char *epoch, *version, *release;
- /* extract epoch and version from evr */
- version = evr;
- while (*version && isdigit(*version)) version++;
- if (*version == ':') {
- epoch = evr;
- *version++ = 0;
- if (!*epoch) epoch = "0";
- version[-1] = ':'; /* restore in memory modification */
- } else {
- /* there is no epoch defined, so assume epoch = 0 */
+ /* extract epoch and version from evr */
version = evr;
+ while (*version && isdigit(*version)) version++;
+ if (*version == ':') {
+ epoch = evr;
+ *version++ = 0;
+ if (!*epoch) epoch = "0";
+ compare = _epoch - (*epoch ? atoi(epoch) : 0);
+ version[-1] = ':'; /* restore in memory modification */
+ } else {
+ /* there is no epoch defined, so assume epoch = 0 */
+ version = evr;
+ compare = _epoch;
+ }
+ if (!compare) {
+ if (!pkg->info)
+ _version = get_name(pkg->h, RPMTAG_VERSION);
+ /* continue extracting release if any */
+ if ((release = strrchr(version, '-')) != NULL) {
+ *release++ = 0;
+ compare = rpmvercmp(_version, version);
+ if (!compare) {
+ /* need to compare with release here */
+ if (!pkg->info)
+ _release = get_name(pkg->h, RPMTAG_RELEASE);
+ compare = rpmvercmp(_release, release);
+ }
+ release[-1] = '-'; /* restore in memory modification */
+ } else {
+ compare = rpmvercmp(_version, version);
+ }
+ }
}
- if ((release = strrchr(version, '-')) != NULL)
- *release++ = 0;
- repoch = epoch && *epoch ? atoi(epoch) : 0;
-
- RETVAL = compare_evrs(_epoch, _version, _release, repoch, version, release);
/* restore info string modified */
if (pkg->info) {
_release[-1] = '-';
_eos[-1] = '.';
}
- if (release)
- release[-1] = '-'; /* restore in memory modification */
+ RETVAL = compare;
OUTPUT:
RETVAL
@@ -1706,8 +1846,7 @@ Pkg_size(pkg)
char *s, *eos;
if ((s = strchr(pkg->info, '@')) != NULL && (s = strchr(s+1, '@')) != NULL) {
- if ((eos = strchr(s+1, '@')) != NULL)
- *eos = 0; /* mark end of string to enable searching backwards */
+ if ((eos = strchr(s+1, '@')) != NULL) *eos = 0; /* mark end of string to enable searching backwards */
RETVAL = atoi(s+1);
if (eos != NULL) *eos = '@';
} else
@@ -1767,10 +1906,12 @@ Pkg_filename(pkg)
memcpy(eon, savbuf, 4);
}
} else if (pkg->h) {
- char *nvr = headerGetAsString(pkg->h, RPMTAG_NVR);
- char *arch = get_arch(pkg->h);
+ char *name = get_name(pkg->h, RPMTAG_NAME);
+ char *version = get_name(pkg->h, RPMTAG_VERSION);
+ char *release = get_name(pkg->h, RPMTAG_RELEASE);
+ char *arch = headerIsEntry(pkg->h, RPMTAG_SOURCERPM) ? get_name(pkg->h, RPMTAG_ARCH) : "src";
- mXPUSHs(newSVpvf("%s.%s.rpm", nvr, arch));
+ mXPUSHs(newSVpvf("%s-%s-%s.%s.rpm", name, version, release, arch));
}
# deprecated
@@ -1787,10 +1928,12 @@ Pkg_header_filename(pkg)
} else if (pkg->h) {
char buff[1024];
char *p = buff;
- char *nvr = headerGetAsString(pkg->h, RPMTAG_NVR);
- char *arch = get_arch(pkg->h);
+ char *name = get_name(pkg->h, RPMTAG_NAME);
+ char *version = get_name(pkg->h, RPMTAG_VERSION);
+ char *release = get_name(pkg->h, RPMTAG_RELEASE);
+ char *arch = headerIsEntry(pkg->h, RPMTAG_SOURCERPM) ? get_name(pkg->h, RPMTAG_ARCH) : "src";
- p += snprintf(buff, sizeof(buff), "%s.%s", nvr, arch);
+ p += snprintf(buff, sizeof(buff), "%s-%s-%s.%s", name, version, release, arch);
mXPUSHs(newSVpv(buff, p-buff));
}
@@ -1798,8 +1941,9 @@ void
Pkg_id(pkg)
URPM::Package pkg
PPCODE:
- if ((pkg->flag & FLAG_ID) <= FLAG_ID_MAX)
+ if ((pkg->flag & FLAG_ID) <= FLAG_ID_MAX) {
mXPUSHs(newSViv(pkg->flag & FLAG_ID));
+ }
void
Pkg_set_id(pkg, id=-1)
@@ -1834,7 +1978,10 @@ Pkg_suggests(pkg)
URPM::Package pkg
PPCODE:
PUTBACK;
- return_list_str(pkg->suggests, pkg->h, RPMTAG_SUGGESTSNAME, 0, 0, callback_list_str_xpush, NULL);
+ int count = return_list_str(pkg->suggests, pkg->h, RPMTAG_SUGGESTSNAME, 0, 0, callback_list_str_xpush, NULL);
+ if (count == 0)
+ return_list_str(pkg->suggests, pkg->h, RPMTAG_REQUIRENAME, RPMTAG_REQUIREFLAGS, 0,
+ callback_list_str_xpush_old_suggests, NULL);
SPAGAIN;
void
@@ -1849,46 +1996,22 @@ Pkg_obsoletes(pkg)
void
Pkg_obsoletes_nosense(pkg)
URPM::Package pkg
- ALIAS:
- conflicts_nosense = 1
- provides_nosense = 2
PPCODE:
PUTBACK;
- rpmTag tag;
- char *s;
- switch (ix) {
- case 1: tag = RPMTAG_CONFLICTNAME; s = pkg->conflicts; break;
- case 2: tag = RPMTAG_PROVIDENAME; s = pkg->provides; break;
- default: tag = RPMTAG_OBSOLETENAME; s = pkg->obsoletes; break;
- }
- return_list_str(s, pkg->h, tag, 0, 0, callback_list_str_xpush, NULL);
+ return_list_str(pkg->obsoletes, pkg->h, RPMTAG_OBSOLETENAME, 0, 0, callback_list_str_xpush, NULL);
SPAGAIN;
int
-Pkg_obsoletes_overlap(pkg, s)
+Pkg_obsoletes_overlap(pkg, s, b_nopromote=1, direction=-1)
URPM::Package pkg
char *s
- ALIAS:
- provides_overlap = 1
+ int b_nopromote
+ int direction
PREINIT:
struct cb_overlap_s os;
char *eon = NULL;
char eonc = '\0';
- rpmTag tag_name;
- rpmTag tag_flags, tag_version;
- CODE:
- switch (ix) {
- case 1:
- tag_name = RPMTAG_PROVIDENAME;
- tag_flags = RPMTAG_PROVIDEFLAGS;
- tag_version = RPMTAG_PROVIDEVERSION;
- break;
- default:
- tag_name = RPMTAG_OBSOLETENAME;
- tag_flags = RPMTAG_OBSOLETEFLAGS;
- tag_version = RPMTAG_OBSOLETEVERSION;
- break;
- }
+ CODE:
os.name = s;
os.flags = 0;
while (*s && *s != ' ' && *s != '[' && *s != '<' && *s != '>' && *s != '=') ++s;
@@ -1905,14 +2028,12 @@ Pkg_obsoletes_overlap(pkg, s)
os.evr = s;
} else
os.evr = "";
- os.direction = ix == 0 ? -1 : 1;
+ os.direction = direction;
+ os.b_nopromote = b_nopromote;
/* mark end of name */
- if (eon) {
- eonc = *eon;
- *eon = 0;
- }
+ if (eon) { eonc = *eon; *eon = 0; }
/* return_list_str returns a negative value is the callback has returned non-zero */
- RETVAL = return_list_str(ix == 0 ? pkg->obsoletes : pkg->provides, pkg->h, tag_name, tag_flags, tag_version,
+ RETVAL = return_list_str(pkg->obsoletes, pkg->h, RPMTAG_OBSOLETENAME, RPMTAG_OBSOLETEFLAGS, RPMTAG_OBSOLETEVERSION,
callback_list_str_overlap, &os) < 0;
/* restore end of name */
if (eon) *eon = eonc;
@@ -1929,6 +2050,14 @@ Pkg_conflicts(pkg)
SPAGAIN;
void
+Pkg_conflicts_nosense(pkg)
+ URPM::Package pkg
+ PPCODE:
+ PUTBACK;
+ return_list_str(pkg->conflicts, pkg->h, RPMTAG_CONFLICTNAME, 0, 0, callback_list_str_xpush, NULL);
+ SPAGAIN;
+
+void
Pkg_provides(pkg)
URPM::Package pkg
PPCODE:
@@ -1938,69 +2067,220 @@ Pkg_provides(pkg)
SPAGAIN;
void
+Pkg_provides_nosense(pkg)
+ URPM::Package pkg
+ PPCODE:
+ PUTBACK;
+ return_list_str(pkg->provides, pkg->h, RPMTAG_PROVIDENAME, 0, 0, callback_list_str_xpush, NULL);
+ SPAGAIN;
+
+int
+Pkg_provides_overlap(pkg, s, b_nopromote=1, direction=1)
+ URPM::Package pkg
+ char *s
+ int b_nopromote
+ int direction
+ PREINIT:
+ struct cb_overlap_s os;
+ char *eon = NULL;
+ char eonc = '\0';
+ CODE:
+ os.name = s;
+ os.flags = 0;
+ while (*s && *s != ' ' && *s != '[' && *s != '<' && *s != '>' && *s != '=') ++s;
+ if (*s) {
+ eon = s;
+ while (*s) {
+ if (*s == ' ' || *s == '[' || *s == '*' || *s == ']');
+ else if (*s == '<') os.flags |= RPMSENSE_LESS;
+ else if (*s == '>') os.flags |= RPMSENSE_GREATER;
+ else if (*s == '=') os.flags |= RPMSENSE_EQUAL;
+ else break;
+ ++s;
+ }
+ os.evr = s;
+ } else
+ os.evr = "";
+ os.direction = direction;
+ os.b_nopromote = b_nopromote;
+ /* mark end of name */
+ if (eon) { eonc = *eon; *eon = 0; }
+ /* return_list_str returns a negative value is the callback has returned non-zero */
+ RETVAL = return_list_str(pkg->provides, pkg->h, RPMTAG_PROVIDENAME, RPMTAG_PROVIDEFLAGS, RPMTAG_PROVIDEVERSION,
+ callback_list_str_overlap, &os) < 0;
+ /* restore end of name */
+ if (eon) *eon = eonc;
+ OUTPUT:
+ RETVAL
+
+void
Pkg_buildarchs(pkg)
URPM::Package pkg
- ALIAS:
- excludearchs = 1
- exclusivearchs = 2
- dirnames = 3
- filelinktos = 4
- files_md5sum = 5
- files_owner = 6
- files_group = 7
- changelog_name = 8
- changelog_text = 9
PPCODE:
PUTBACK;
- rpmTag tag;
- switch (ix) {
- case 1: tag = RPMTAG_EXCLUDEARCH; break;
- case 2: tag = RPMTAG_EXCLUSIVEARCH; break;
- case 3: tag = RPMTAG_DIRNAMES; break;
- case 4: tag = RPMTAG_FILELINKTOS; break;
- case 5: tag = RPMTAG_FILEMD5S; break;
- case 6: tag = RPMTAG_FILEUSERNAME; break;
- case 7: tag = RPMTAG_FILEGROUPNAME; break;
- case 8: tag = RPMTAG_CHANGELOGNAME; break;
- case 9: tag = RPMTAG_CHANGELOGTEXT; break;
- default: tag = RPMTAG_BUILDARCHS; break;
- }
- xpush_simple_list_str(pkg->h, tag);
+ xpush_simple_list_str(pkg->h, RPMTAG_BUILDARCHS);
+ SPAGAIN;
+
+void
+Pkg_excludearchs(pkg)
+ URPM::Package pkg
+ PPCODE:
+ PUTBACK;
+ xpush_simple_list_str(pkg->h, RPMTAG_EXCLUDEARCH);
+ SPAGAIN;
+
+void
+Pkg_exclusivearchs(pkg)
+ URPM::Package pkg
+ PPCODE:
+ PUTBACK;
+ xpush_simple_list_str(pkg->h, RPMTAG_EXCLUSIVEARCH);
+ SPAGAIN;
+
+void
+Pkg_dirnames(pkg)
+ URPM::Package pkg
+ PPCODE:
+ PUTBACK;
+ xpush_simple_list_str(pkg->h, RPMTAG_DIRNAMES);
+ SPAGAIN;
+
+void Pkg_distepoch(pkg)
+ URPM::Package pkg
+ PPCODE:
+#ifdef RPMTAG_DISTEPOCH
+ if (pkg->h) {
+ mXPUSHs(newSVpv(get_name(pkg->h, RPMTAG_DISTEPOCH), 0));
+ }
+#else
+ croak("distepoch isn't available with this rpm version");
+#endif
+
+void Pkg_disttag(pkg)
+ URPM::Package pkg
+ PPCODE:
+ if (pkg->h) {
+ mXPUSHs(newSVpv(get_name(pkg->h, RPMTAG_DISTTAG), 0));
+ }
+
+void
+Pkg_filelinktos(pkg)
+ URPM::Package pkg
+ PPCODE:
+ PUTBACK;
+ xpush_simple_list_str(pkg->h, RPMTAG_FILELINKTOS);
SPAGAIN;
void
Pkg_files(pkg)
URPM::Package pkg
- ALIAS:
- conf_files = 1
PPCODE:
PUTBACK;
- return_files(pkg->h, ix == 0 ? 0 : FILTER_MODE_CONF_FILES);
+ return_files(pkg->h, 0);
+ SPAGAIN;
+
+void
+Pkg_files_md5sum(pkg)
+ URPM::Package pkg
+ PPCODE:
+ PUTBACK;
+ xpush_simple_list_str(pkg->h, RPMTAG_FILEMD5S);
+ SPAGAIN;
+
+void
+Pkg_files_owner(pkg)
+ URPM::Package pkg
+ PPCODE:
+ PUTBACK;
+ xpush_simple_list_str(pkg->h, RPMTAG_FILEUSERNAME);
+ SPAGAIN;
+
+void
+Pkg_files_group(pkg)
+ URPM::Package pkg
+ PPCODE:
+ PUTBACK;
+ xpush_simple_list_str(pkg->h, RPMTAG_FILEGROUPNAME);
SPAGAIN;
void
Pkg_files_mtime(pkg)
URPM::Package pkg
- ALIAS:
- files_size = 1
- files_uid = 2
- files_gid = 3
- files_mode = 4
- files_flags = 5
- changelog_time = 6
PPCODE:
PUTBACK;
- rpmTag tag;
- switch (ix) {
- case 1: tag = RPMTAG_FILESIZES; break;
- case 2: tag = RPMTAG_FILEUIDS; break;
- case 3: tag = RPMTAG_FILEGIDS; break;
- case 4: tag = RPMTAG_FILEMODES; break;
- case 5: tag = RPMTAG_FILEFLAGS; break;
- case 6: tag = RPMTAG_CHANGELOGTIME; break;
- default: tag = RPMTAG_FILEMTIMES; break;
- }
- return_list_number(pkg->h, tag);
+ return_list_int32_t(pkg->h, RPMTAG_FILEMTIMES);
+ SPAGAIN;
+
+void
+Pkg_files_size(pkg)
+ URPM::Package pkg
+ PPCODE:
+ PUTBACK;
+ return_list_int32_t(pkg->h, RPMTAG_FILESIZES);
+ SPAGAIN;
+
+void
+Pkg_files_uid(pkg)
+ URPM::Package pkg
+ PPCODE:
+ PUTBACK;
+ return_list_int32_t(pkg->h, RPMTAG_FILEUIDS);
+ SPAGAIN;
+
+void
+Pkg_files_gid(pkg)
+ URPM::Package pkg
+ PPCODE:
+ PUTBACK;
+ return_list_int32_t(pkg->h, RPMTAG_FILEGIDS);
+ SPAGAIN;
+
+void
+Pkg_files_mode(pkg)
+ URPM::Package pkg
+ PPCODE:
+ PUTBACK;
+ return_list_uint_16(pkg->h, RPMTAG_FILEMODES);
+ SPAGAIN;
+
+void
+Pkg_files_flags(pkg)
+ URPM::Package pkg
+ PPCODE:
+ PUTBACK;
+ return_list_int32_t(pkg->h, RPMTAG_FILEFLAGS);
+ SPAGAIN;
+
+void
+Pkg_conf_files(pkg)
+ URPM::Package pkg
+ PPCODE:
+ PUTBACK;
+ return_files(pkg->h, FILTER_MODE_CONF_FILES);
+ SPAGAIN;
+
+void
+Pkg_changelog_time(pkg)
+ URPM::Package pkg
+ PPCODE:
+ PUTBACK;
+ return_list_int32_t(pkg->h, RPMTAG_CHANGELOGTIME);
+ SPAGAIN;
+
+void
+Pkg_changelog_name(pkg)
+ URPM::Package pkg
+ PPCODE:
+ PUTBACK;
+ xpush_simple_list_str(pkg->h, RPMTAG_CHANGELOGNAME);
+ SPAGAIN;
+
+void
+Pkg_changelog_text(pkg)
+ URPM::Package pkg
+ PPCODE:
+ PUTBACK;
+ xpush_simple_list_str(pkg->h, RPMTAG_CHANGELOGTEXT);
SPAGAIN;
void
@@ -2013,23 +2293,26 @@ Pkg_queryformat(pkg, fmt)
if (pkg->h) {
s = headerFormat(pkg->h, fmt, NULL);
if (s)
- mXPUSHs(newSVpv_utf8(s, 0));
+ mXPUSHs(newSVpv_utf8(s,0));
}
void
Pkg_get_tag(pkg, tagname)
URPM::Package pkg
int tagname;
- ALIAS:
- get_tag_modifiers = 1
PPCODE:
PUTBACK;
- if (ix == 0)
- return_list_tag(pkg, tagname);
- else
- return_list_tag_modifier(pkg->h, tagname);
+ return_list_tag(pkg, tagname);
SPAGAIN;
+void
+Pkg_get_tag_modifiers(pkg, tagname)
+ URPM::Package pkg
+ int tagname;
+ PPCODE:
+ PUTBACK;
+ return_list_tag_modifier(pkg->h, tagname);
+ SPAGAIN;
void
Pkg_pack_header(pkg)
@@ -2045,7 +2328,10 @@ Pkg_update_header(pkg, filename, ...)
int packing = 0;
int keep_all_tags = 0;
CODE:
- if (items > 3) {
+ /* compability mode with older interface of parse_hdlist */
+ if (items == 3)
+ packing = SvIV(ST(2));
+ else if (items > 3) {
int i;
for (i = 2; i < items-1; i+=2) {
STRLEN len;
@@ -2066,7 +2352,7 @@ void
Pkg_free_header(pkg)
URPM::Package pkg
CODE:
- _header_free(pkg);
+ if (pkg->h && !(pkg->flag & FLAG_NO_HEADER_FREE)) pkg->h = headerFree(pkg->h);
pkg->h = NULL;
void
@@ -2173,56 +2459,135 @@ Pkg_set_flag(pkg, name, value=1)
RETVAL
int
+Pkg_flag_skip(pkg)
+ URPM::Package pkg
+ CODE:
+ RETVAL = pkg->flag & FLAG_SKIP;
+ OUTPUT:
+ RETVAL
+
+int
Pkg_set_flag_skip(pkg, value=1)
URPM::Package pkg
int value
- ALIAS:
- set_flag_base = 1
- set_flag_disable_obsolete = 2
- set_flag_installed = 3
- set_flag_requested = 4
- set_flag_required = 5
- set_flag_upgrade = 6
CODE:
- unsigned flag;
- switch (ix) {
- case 1: flag = FLAG_BASE; break;
- case 2: flag = FLAG_DISABLE_OBSOLETE; break;
- case 3: flag = FLAG_INSTALLED; break;
- case 4: flag = FLAG_REQUESTED; break;
- case 5: flag = FLAG_REQUIRED; break;
- case 6: flag = FLAG_UPGRADE; break;
- default: flag = FLAG_SKIP; break;
- }
- RETVAL = pkg->flag & flag;
- if (value) pkg->flag |= flag;
- else pkg->flag &= ~flag;
+ RETVAL = pkg->flag & FLAG_SKIP;
+ if (value) pkg->flag |= FLAG_SKIP;
+ else pkg->flag &= ~FLAG_SKIP;
OUTPUT:
RETVAL
+int
+Pkg_flag_base(pkg)
+ URPM::Package pkg
+ CODE:
+ RETVAL = pkg->flag & FLAG_BASE;
+ OUTPUT:
+ RETVAL
+
+int
+Pkg_set_flag_base(pkg, value=1)
+ URPM::Package pkg
+ int value
+ CODE:
+ RETVAL = pkg->flag & FLAG_BASE;
+ if (value) pkg->flag |= FLAG_BASE;
+ else pkg->flag &= ~FLAG_BASE;
+ OUTPUT:
+ RETVAL
+
+int
+Pkg_flag_disable_obsolete(pkg)
+ URPM::Package pkg
+ CODE:
+ RETVAL = pkg->flag & FLAG_DISABLE_OBSOLETE;
+ OUTPUT:
+ RETVAL
+
+int
+Pkg_set_flag_disable_obsolete(pkg, value=1)
+ URPM::Package pkg
+ int value
+ CODE:
+ RETVAL = pkg->flag & FLAG_DISABLE_OBSOLETE;
+ if (value) pkg->flag |= FLAG_DISABLE_OBSOLETE;
+ else pkg->flag &= ~FLAG_DISABLE_OBSOLETE;
+ OUTPUT:
+ RETVAL
+
+int
+Pkg_flag_installed(pkg)
+ URPM::Package pkg
+ CODE:
+ RETVAL = pkg->flag & FLAG_INSTALLED;
+ OUTPUT:
+ RETVAL
+
+int
+Pkg_set_flag_installed(pkg, value=1)
+ URPM::Package pkg
+ int value
+ CODE:
+ RETVAL = pkg->flag & FLAG_INSTALLED;
+ if (value) pkg->flag |= FLAG_INSTALLED;
+ else pkg->flag &= ~FLAG_INSTALLED;
+ OUTPUT:
+ RETVAL
+
+int
+Pkg_flag_requested(pkg)
+ URPM::Package pkg
+ CODE:
+ RETVAL = pkg->flag & FLAG_REQUESTED;
+ OUTPUT:
+ RETVAL
+
+int
+Pkg_set_flag_requested(pkg, value=1)
+ URPM::Package pkg
+ int value
+ CODE:
+ RETVAL = pkg->flag & FLAG_REQUESTED;
+ if (value) pkg->flag |= FLAG_REQUESTED;
+ else pkg->flag &= ~FLAG_REQUESTED;
+ OUTPUT:
+ RETVAL
int
Pkg_flag_required(pkg)
URPM::Package pkg
- ALIAS:
- flag_upgrade = 1
- flag_disable_obsolete = 2
- flag_requested = 3
- flag_installed = 4
- flag_base = 5
- flag_skip = 6
CODE:
- unsigned flag;
- switch (ix) {
- case 1: flag = FLAG_UPGRADE; break;
- case 2: flag = FLAG_DISABLE_OBSOLETE; break;
- case 3: flag = FLAG_REQUESTED; break;
- case 4: flag = FLAG_INSTALLED; break;
- case 5: flag = FLAG_BASE; break;
- case 6: flag = FLAG_SKIP; break;
- default: flag = FLAG_REQUIRED; break;
- }
- RETVAL = pkg->flag & flag;
+ RETVAL = pkg->flag & FLAG_REQUIRED;
+ OUTPUT:
+ RETVAL
+
+int
+Pkg_set_flag_required(pkg, value=1)
+ URPM::Package pkg
+ int value
+ CODE:
+ RETVAL = pkg->flag & FLAG_REQUIRED;
+ if (value) pkg->flag |= FLAG_REQUIRED;
+ else pkg->flag &= ~FLAG_REQUIRED;
+ OUTPUT:
+ RETVAL
+
+int
+Pkg_flag_upgrade(pkg)
+ URPM::Package pkg
+ CODE:
+ RETVAL = pkg->flag & FLAG_UPGRADE;
+ OUTPUT:
+ RETVAL
+
+int
+Pkg_set_flag_upgrade(pkg, value=1)
+ URPM::Package pkg
+ int value
+ CODE:
+ RETVAL = pkg->flag & FLAG_UPGRADE;
+ if (value) pkg->flag |= FLAG_UPGRADE;
+ else pkg->flag &= ~FLAG_UPGRADE;
OUTPUT:
RETVAL
@@ -2341,7 +2706,7 @@ Db_open(prefix=NULL, write_perm=0)
RETVAL
int
-Db_rebuild(prefix=NULL)
+Db_rebuild(prefix="")
char *prefix
PREINIT:
rpmts ts;
@@ -2355,7 +2720,7 @@ Db_rebuild(prefix=NULL)
RETVAL
int
-Db_verify(prefix=NULL)
+Db_verify(prefix="")
char *prefix
PREINIT:
rpmts ts;
@@ -2381,20 +2746,35 @@ Db_traverse(db,callback)
PREINIT:
Header header;
rpmdbMatchIterator mi;
- rpmVSFlags ovsflags;
int count = 0;
CODE:
+#ifdef RPM490
db->ts = rpmtsLink(db->ts);
- ovsflags = ts_nosignature(db->ts);
+#else
+ db->ts = rpmtsLink(db->ts, "URPM::DB::traverse");
+#endif
+ ts_nosignature(db->ts);
mi = rpmtsInitIterator(db->ts, RPMDBI_PACKAGES, NULL, 0);
while ((header = rpmdbNextIterator(mi))) {
if (SvROK(callback)) {
- _run_cb_while_traversing(callback, header);
+ dSP;
+ URPM__Package pkg = calloc(1, sizeof(struct s_Package));
+
+ pkg->flag = FLAG_ID_INVALID | FLAG_NO_HEADER_FREE;
+ pkg->h = header;
+
+ PUSHMARK(SP);
+ mXPUSHs(sv_setref_pv(newSVpv("", 0), "URPM::Package", pkg));
+ PUTBACK;
+
+ call_sv(callback, G_DISCARD | G_SCALAR);
+
+ SPAGAIN;
+ pkg->h = NULL; /* avoid using it anymore, in case it has been copied inside callback */
}
++count;
}
rpmdbFreeIterator(mi);
- rpmtsSetVSFlags(db->ts, ovsflags);
(void)rpmtsFree(db->ts);
RETVAL = count;
OUTPUT:
@@ -2410,29 +2790,45 @@ Db_traverse_tag(db,tag,names,callback)
Header header;
rpmdbMatchIterator mi;
int count = 0;
- rpmVSFlags ovsflags;
CODE:
if (SvROK(names) && SvTYPE(SvRV(names)) == SVt_PVAV) {
AV* names_av = (AV*)SvRV(names);
int len = av_len(names_av);
- int i;
- rpmTag rpmtag = rpmtag_from_string(tag);
+ int i, rpmtag;
+
+ rpmtag = rpmtag_from_string(tag);
for (i = 0; i <= len; ++i) {
STRLEN str_len;
SV **isv = av_fetch(names_av, i, 0);
char *name = SvPV(*isv, str_len);
+#ifdef RPM490
db->ts = rpmtsLink(db->ts);
- ovsflags = ts_nosignature(db->ts);
+#else
+ db->ts = rpmtsLink(db->ts, "URPM::DB::traverse_tag");
+#endif
+ ts_nosignature(db->ts);
mi = rpmtsInitIterator(db->ts, rpmtag, name, str_len);
while ((header = rpmdbNextIterator(mi))) {
if (SvROK(callback)) {
- _run_cb_while_traversing(callback, header);
+ dSP;
+ URPM__Package pkg = calloc(1, sizeof(struct s_Package));
+
+ pkg->flag = FLAG_ID_INVALID | FLAG_NO_HEADER_FREE;
+ pkg->h = header;
+
+ PUSHMARK(SP);
+ mXPUSHs(sv_setref_pv(newSVpv("", 0), "URPM::Package", pkg));
+ PUTBACK;
+
+ call_sv(callback, G_DISCARD | G_SCALAR);
+
+ SPAGAIN;
+ pkg->h = NULL; /* avoid using it anymore, in case it has been copied inside callback */
}
++count;
}
(void)rpmdbFreeIterator(mi);
- rpmtsSetVSFlags(db->ts, ovsflags);
(void)rpmtsFree(db->ts);
}
} else croak("bad arguments list");
@@ -2450,21 +2846,36 @@ Db_traverse_tag_find(db,tag,name,callback)
Header header;
rpmdbMatchIterator mi;
CODE:
- rpmTag rpmtag = rpmtag_from_string(tag);
+ int rpmtag = rpmtag_from_string(tag);
int found = 0;
- rpmVSFlags ovsflags;
+#ifdef RPM490
db->ts = rpmtsLink(db->ts);
- ovsflags = ts_nosignature(db->ts);
+#else
+ db->ts = rpmtsLink(db->ts, "URPM::DB::traverse_tag");
+#endif
+ ts_nosignature(db->ts);
mi = rpmtsInitIterator(db->ts, rpmtag, name, 0);
while ((header = rpmdbNextIterator(mi))) {
- int count = _run_cb_while_traversing(callback, header);
+ dSP;
+ URPM__Package pkg = calloc(1, sizeof(struct s_Package));
+
+ pkg->flag = FLAG_ID_INVALID | FLAG_NO_HEADER_FREE;
+ pkg->h = header;
+
+ PUSHMARK(SP);
+ mXPUSHs(sv_setref_pv(newSVpv("", 0), "URPM::Package", pkg));
+ PUTBACK;
+
+ int count = call_sv(callback, G_SCALAR);
+
+ SPAGAIN;
+ pkg->h = NULL; /* avoid using it anymore, in case it has been copied inside callback */
if (count == 1 && POPi) {
found = 1;
break;
}
}
- rpmtsSetVSFlags(db->ts, ovsflags);
(void)rpmdbFreeIterator(mi);
(void)rpmtsFree(db->ts);
RETVAL = found;
@@ -2472,12 +2883,17 @@ Db_traverse_tag_find(db,tag,name,callback)
RETVAL
URPM::Transaction
-Db_create_transaction(db)
+Db_create_transaction(db, prefix="/")
URPM::DB db
+ char *prefix
CODE:
/* this is *REALLY* dangerous to create a new transaction while another is open,
so use the db transaction instead. */
+#ifdef RPM490
db->ts = rpmtsLink(db->ts);
+#else
+ db->ts = rpmtsLink(db->ts, "URPM::DB::create_transaction");
+#endif
++db->count;
RETVAL = db;
OUTPUT:
@@ -2508,7 +2924,10 @@ Trans_add(trans, pkg, ...)
if ((pkg->flag & FLAG_ID) <= FLAG_ID_MAX && pkg->h != NULL) {
int update = 0;
rpmRelocation *relocations = NULL;
- if (items > 3) {
+ /* compability mode with older interface of add */
+ if (items == 3)
+ update = SvIV(ST(2));
+ else if (items > 3) {
int i;
for (i = 2; i < items-1; i+=2) {
STRLEN len;
@@ -2545,7 +2964,19 @@ Trans_remove(trans, name)
Header h;
rpmdbMatchIterator mi;
int count = 0;
+ char *boa = NULL, *bor = NULL;
CODE:
+ /* hide arch in name if present */
+ if ((boa = strrchr(name, '.'))) {
+ *boa = 0;
+ if ((bor = strrchr(name, '-'))) {
+ *bor = 0;
+ if (!strrchr(name, '-'))
+ *boa = '.'; boa = NULL;
+ *bor = '-'; bor = NULL;
+ } else
+ *boa = '.'; boa = NULL;
+ }
mi = rpmtsInitIterator(trans->ts, RPMDBI_LABEL, name, 0);
while ((h = rpmdbNextIterator(mi))) {
unsigned int recOffset = rpmdbGetIteratorOffset(mi);
@@ -2555,6 +2986,7 @@ Trans_remove(trans, name)
}
}
rpmdbFreeIterator(mi);
+ if (boa) *boa = '.';
RETVAL=count;
OUTPUT:
RETVAL
@@ -2576,7 +3008,7 @@ Trans_traverse(trans, callback)
pkg->flag = FLAG_ID_INVALID | FLAG_NO_HEADER_FREE;
pkg->h = h;
PUSHMARK(SP);
- mXPUSHs(sv_setref_pv(newSVpvs(""), "URPM::Package", pkg));
+ mXPUSHs(sv_setref_pv(newSVpv("", 0), "URPM::Package", pkg));
PUTBACK;
call_sv(callback, G_DISCARD | G_SCALAR);
SPAGAIN;
@@ -2608,7 +3040,7 @@ Trans_check(trans, ...)
if (gimme == G_SCALAR)
mXPUSHs(newSViv(0));
else if (gimme == G_ARRAY)
- mXPUSHs(newSVpvs("error while checking dependencies"));
+ mXPUSHs(newSVpv("error while checking dependencies", 0));
} else {
rpmps ps = rpmtsProblems(trans->ts);
if (rpmpsNumProblems(ps) > 0) {
@@ -2639,7 +3071,7 @@ Trans_order(trans)
if (gimme == G_SCALAR)
mXPUSHs(newSViv(0));
else if (gimme == G_ARRAY)
- mXPUSHs(newSVpvs("error while ordering dependencies"));
+ mXPUSHs(newSVpv("error while ordering dependencies", 0));
}
int
@@ -2654,22 +3086,39 @@ char *
Trans_Element_name(trans, index)
URPM::Transaction trans
int index
- ALIAS:
- Element_version = 1
- Element_release = 2
- Element_fullname = 3
CODE:
rpmte te = rpmtsElement(trans->ts, index);
- if (te) {
- switch (ix) {
- case 1: RETVAL = (char *) rpmteV(te); break;
- case 2: RETVAL = (char *) rpmteR(te); break;
- case 3: RETVAL = (char *) rpmteNEVRA(te); break;
- default: RETVAL = (char *) rpmteN(te); break;
- }
- } else {
- RETVAL = NULL;
- }
+ RETVAL = te ? (char *) rpmteN(te) : NULL;
+ OUTPUT:
+ RETVAL
+
+char *
+Trans_Element_version(trans, index)
+ URPM::Transaction trans
+ int index
+ CODE:
+ rpmte te = rpmtsElement(trans->ts, index);
+ RETVAL = te ? (char *) rpmteV(te) : NULL;
+ OUTPUT:
+ RETVAL
+
+char *
+Trans_Element_release(trans, index)
+ URPM::Transaction trans
+ int index
+ CODE:
+ rpmte te = rpmtsElement(trans->ts, index);
+ RETVAL = te ? (char *) rpmteR(te) : NULL;
+ OUTPUT:
+ RETVAL
+
+char *
+Trans_Element_fullname(trans, index)
+ URPM::Transaction trans
+ int index
+ CODE:
+ rpmte te = rpmtsElement(trans->ts, index);
+ RETVAL = te ? (char *) rpmteNEVRA(te) : NULL;
OUTPUT:
RETVAL
@@ -2746,7 +3195,11 @@ Trans_run(trans, data, ...)
if (repa) free(repa);
}
rpmtsSetFlags(trans->ts, transFlags);
+#ifdef RPM490
trans->ts = rpmtsLink(trans->ts);
+#else
+ trans->ts = rpmtsLink(trans->ts, "URPM::Transaction::run");
+#endif
rpmtsSetNotifyCallback(trans->ts, rpmRunTransactions_callback, &td);
if (rpmtsRun(trans->ts, NULL, probFilter) > 0) {
rpmps ps = rpmtsProblems(trans->ts);
@@ -2776,15 +3229,22 @@ Urpm_read_config_files()
OUTPUT:
RETVAL
+void
+Urpm_list_rpm_tag(urpm=Nullsv)
+ SV *urpm
+ CODE:
+ croak("list_rpm_tag() has been removed from perl-URPM. please report if you need it back");
+
int
rpmvercmp(one, two)
char *one
char *two
int
-Urpm_ranges_overlap(a, b)
+Urpm_ranges_overlap(a, b, b_nopromote=1)
char *a
char *b
+ int b_nopromote
PREINIT:
char *sa = a, *sb = b;
int aflags = 0, bflags = 0;
@@ -2814,7 +3274,7 @@ Urpm_ranges_overlap(a, b)
else break;
++sb;
}
- RETVAL = ranges_overlap(aflags, sa, bflags, sb);
+ RETVAL = ranges_overlap(aflags, sa, bflags, sb, b_nopromote);
}
OUTPUT:
RETVAL
@@ -2834,13 +3294,12 @@ Urpm_parse_synthesis__XS(urpm, filename, ...)
if (depslist != NULL) {
char buff[65536];
- char *p, *eol, *t;
+ char *p, *eol;
int buff_len;
struct s_Package pkg;
- FD_t f = NULL;
+ gzFile f;
int start_id = 1 + av_len(depslist);
SV *callback = NULL;
- rpmCompressedMagic compressed = COMPRESSED_OTHER;
if (items > 2) {
int i;
@@ -2854,35 +3313,19 @@ Urpm_parse_synthesis__XS(urpm, filename, ...)
}
PUTBACK;
- int rc = rpmFileIsCompressed(filename, &compressed);
-
- switch (compressed) {
- case COMPRESSED_BZIP2: t = "r.bzip2"; break;
- case COMPRESSED_LZMA:
- case COMPRESSED_XZ:
- t = "r.xz"; break;
- case COMPRESSED_OTHER:
- default:
- t = "r.gzip"; break;
- }
- f = Fopen(filename, "r.fdio");
-
- if (!rc && (f = Fdopen(f, t)) != NULL && !Ferror(f)) {
+ if ((f = gzopen(filename, "rb")) != NULL) {
memset(&pkg, 0, sizeof(struct s_Package));
buff[sizeof(buff)-1] = 0;
p = buff;
int ok = 1;
- while ((buff_len = Fread(p, sizeof(buff)-1-(p-buff), 1, f)) >= 0 &&
+ while ((buff_len = gzread(f, p, sizeof(buff)-1-(p-buff))) >= 0 &&
(buff_len += p-buff)) {
buff[buff_len] = 0;
p = buff;
if ((eol = strchr(p, '\n')) != NULL) {
do {
*eol++ = 0;
- if (!parse_line(depslist, provides, obsoletes, &pkg, p, urpm, callback)) {
- ok = 0;
- break;
- }
+ if (!parse_line(depslist, provides, obsoletes, &pkg, p, urpm, callback)) { ok = 0; break; }
p = eol;
} while ((eol = strchr(p, '\n')) != NULL);
} else {
@@ -2891,15 +3334,17 @@ Urpm_parse_synthesis__XS(urpm, filename, ...)
ok = 0;
break;
}
+ if (gzeof(f)) {
+ if (!parse_line(depslist, provides, obsoletes, &pkg, p, urpm, callback)) ok = 0;
+ break;
+ } else {
/* move the remaining non-complete-line at beginning */
memmove(buff, p, buff_len-(p-buff));
/* point to the end of the non-complete-line */
p = &buff[buff_len-(p-buff)];
+ }
}
- // EOF:
- if (!parse_line(depslist, provides, obsoletes, &pkg, p, urpm, callback))
- ok = 0;
- if (Fclose(f) != 0) ok = 0;
+ if (gzclose(f) != 0) ok = 0;
SPAGAIN;
if (ok) {
mXPUSHs(newSViv(start_id));
@@ -2944,7 +3389,10 @@ Urpm_parse_hdlist__XS(urpm, filename, ...)
int packing = 0;
SV *callback = NULL;
- if (items > 3) {
+ /* compability mode with older interface of parse_hdlist */
+ if (items == 3)
+ packing = SvTRUE(ST(2));
+ else if (items > 3) {
int i;
for (i = 2; i < items-1; i+=2) {
STRLEN len;
@@ -2961,13 +3409,14 @@ Urpm_parse_hdlist__XS(urpm, filename, ...)
do {
header = headerRead(fd, HEADER_MAGIC_YES);
if (header != NULL) {
- struct s_Package *_pkg;
+ struct s_Package pkg, *_pkg;
SV *sv_pkg;
- _pkg = calloc(1, sizeof(struct s_Package));
- _pkg->flag = 1 + av_len(depslist);
- _pkg->h = header;
- sv_pkg = sv_setref_pv(newSVpvs(""), "URPM::Package", _pkg);
+ memset(&pkg, 0, sizeof(struct s_Package));
+ pkg.flag = 1 + av_len(depslist);
+ pkg.h = header;
+ sv_pkg = sv_setref_pv(newSVpv("", 0), "URPM::Package",
+ _pkg = memcpy(malloc(sizeof(struct s_Package)), &pkg, sizeof(struct s_Package)));
if (call_package_callback(urpm, sv_pkg, callback)) {
if (provides) {
update_provides(_pkg, provides);
@@ -3011,14 +3460,17 @@ Urpm_parse_rpm(urpm, filename, ...)
HV *obsoletes = fobsoletes && SvROK(*fobsoletes) && SvTYPE(SvRV(*fobsoletes)) == SVt_PVHV ? (HV*)SvRV(*fobsoletes) : NULL;
if (depslist != NULL) {
- struct s_Package *_pkg;
+ struct s_Package pkg, *_pkg;
SV *sv_pkg;
int packing = 0;
int keep_all_tags = 0;
SV *callback = NULL;
rpmVSFlags vsflags = RPMVSF_DEFAULT;
- if (items > 3) {
+ /* compability mode with older interface of parse_hdlist */
+ if (items == 3)
+ packing = SvTRUE(ST(2));
+ else if (items > 3) {
int i;
for (i = 2; i < items-1; i+=2) {
STRLEN len;
@@ -3052,11 +3504,12 @@ Urpm_parse_rpm(urpm, filename, ...)
}
}
PUTBACK;
- _pkg = calloc(1, sizeof(struct s_Package));
- _pkg->flag = 1 + av_len(depslist);
+ memset(&pkg, 0, sizeof(struct s_Package));
+ pkg.flag = 1 + av_len(depslist);
+ _pkg = memcpy(malloc(sizeof(struct s_Package)), &pkg, sizeof(struct s_Package));
if (update_header(filename, _pkg, keep_all_tags, vsflags)) {
- sv_pkg = sv_setref_pv(newSVpvs(""), "URPM::Package", _pkg);
+ sv_pkg = sv_setref_pv(newSVpv("", 0), "URPM::Package", _pkg);
if (call_package_callback(urpm, sv_pkg, callback)) {
if (provides) {
update_provides(_pkg, provides);
@@ -3148,7 +3601,7 @@ Urpm_get_gpg_fingerprint(filename)
char *
-Urpm_verify_signature(filename, prefix=NULL)
+Urpm_verify_signature(filename, prefix="/")
char *filename
char *prefix
PREINIT:
@@ -3213,7 +3666,11 @@ Urpm_import_pubkey_file(db, filename)
size_t pktlen = 0;
int rc;
CODE:
+#ifdef RPM490
rpmts ts = rpmtsLink(db->ts);
+#else
+ rpmts ts = rpmtsLink(db->ts, "URPM::import_pubkey_file");
+#endif
rpmtsClean(ts);
if ((rc = pgpReadPkts(filename, (uint8_t ** ) &pkt, &pktlen)) <= 0)
@@ -3230,17 +3687,44 @@ Urpm_import_pubkey_file(db, filename)
RETVAL
int
-Urpm_archscore(param)
- const char * param
- ALIAS:
- osscore = 1
+Urpm_import_pubkey(...)
+ CODE:
+ unused_variable(&items);
+ croak("import_pubkey() is dead. use import_pubkey_file() instead");
+ RETVAL = 1;
+ OUTPUT:
+ RETVAL
+
+int
+Urpm_archscore(arch)
+ const char * arch
PREINIT:
CODE:
read_config_files(0);
- RETVAL=rpmMachineScore(ix == 0 ? RPM_MACHTABLE_INSTARCH : RPM_MACHTABLE_INSTOS, param);
+ RETVAL=rpmMachineScore(RPM_MACHTABLE_INSTARCH, arch);
OUTPUT:
RETVAL
+int
+Urpm_osscore(os)
+ const char * os
+ PREINIT:
+ CODE:
+ read_config_files(0);
+ RETVAL=rpmMachineScore(RPM_MACHTABLE_INSTOS, os);
+ OUTPUT:
+ RETVAL
+
+int
+Urpm_platformscore(platform)
+ const char * platform
+ CODE:
+ read_config_files(0);
+ unused_variable(platform);
+ croak("platformscore() is available only since rpm 4.4.8");
+ RETVAL=0;
+ OUTPUT:
+ RETVAL
void
Urpm_stream2header(fp)
@@ -3266,6 +3750,7 @@ void
Urpm_spec2srcheader(specfile)
char *specfile
PREINIT:
+ rpmts ts = rpmtsCreate();
URPM__Package pkg;
Spec spec = NULL;
Header header = NULL;
@@ -3273,33 +3758,65 @@ Urpm_spec2srcheader(specfile)
/* ensure the config is in memory with all macro */
read_config_files(0);
/* Do not verify architecture */
+#define SPEC_ANYARCH 1
/* Do not verify whether sources exist */
+#define SPEC_FORCE 1
+#ifdef RPM490
spec = rpmSpecParse(specfile, RPMSPEC_ANYARCH|RPMSPEC_FORCE, NULL);
if (spec) {
header = rpmSpecSourceHeader(spec);
+#else
+ if (!parseSpec(ts, specfile, "/", NULL, 0, NULL, NULL, SPEC_ANYARCH, SPEC_FORCE)) {
+#endif
SV *sv_pkg;
+#ifndef RPM490
+ // FIXME: has disappeared in rpm-4.9.0rpmSpecParse
+ // (See http://www.rpm.org/wiki/Releases/4.9.0)
+ spec = rpmtsSetSpec(ts, NULL);
+ header = spec->sourceHeader;
+ if (! header)
+ initSourceHeader(spec);
+#endif
pkg = (URPM__Package)calloc(1, sizeof(struct s_Package));
headerPutString(header, RPMTAG_SOURCERPM, "");
+
+ {
+ struct rpmtd_s td = {
+ .tag = RPMTAG_ARCH,
+ .type = RPM_STRING_TYPE,
+ .data = (void *) "src",
+ .count = 1,
+ };
/* parseSpec() sets RPMTAG_ARCH to %{_target_cpu} whereas we really a header similar to .src.rpm header */
- headerPutString(header, RPMTAG_ARCH, "src");
+ headerMod(header, &td);
+ }
+#ifdef RPM490
pkg->h = headerLink(header);
+#else
+ pkg->h = headerLink(spec->sourceHeader);
+#endif
sv_pkg = sv_newmortal();
sv_setref_pv(sv_pkg, "URPM::Package", (void*)pkg);
XPUSHs(sv_pkg);
+#ifdef RPM490
spec = rpmSpecFree(spec);
+#else
+ spec = freeSpec(spec);
+#endif
} else {
XPUSHs(&PL_sv_undef);
- /* apparently rpmlib sets errno to this when given a bad spec. */
+ /* apparently rpmlib sets errno this when given a bad spec. */
if (errno == EBADF)
errno = 0;
}
+ ts = rpmtsFree(ts);
void
expand(name)
char * name
PPCODE:
const char * value = rpmExpand(name, NULL);
- mXPUSHs(newSVpv(value, 0));
+ XPUSHs(sv_2mortal(newSVpv(value, 0)));
void
add_macro_noexpand(macro)