[packages/rpm/rpm.org] - teach rpm how to read /proc files - add cpuinfo() deps

baggins baggins at pld-linux.org
Sun Nov 8 22:00:21 CET 2020


commit 2aa7d974ad81aa11e64f99d8a0b8af5d8176b044
Author: Jan Rękorajski <baggins at pld-linux.org>
Date:   Sun Nov 8 21:58:05 2020 +0100

    - teach rpm how to read /proc files
    - add cpuinfo() deps

 cpuinfo-deps.patch          | 289 ++++++++++++++++++++++++++++++++++++++++++++
 rpm.spec                    |   6 +-
 rpmio-read-proc-files.patch |  25 ++++
 uname-deps.patch            |  45 ++++---
 4 files changed, 346 insertions(+), 19 deletions(-)
---
diff --git a/rpm.spec b/rpm.spec
index 9d5dc2c..c7bef13 100644
--- a/rpm.spec
+++ b/rpm.spec
@@ -26,7 +26,7 @@ Summary(ru.UTF-8):	Менеджер пакетов от RPM
 Summary(uk.UTF-8):	Менеджер пакетів від RPM
 Name:		rpm
 Version:	4.16.0
-Release:	0.5
+Release:	0.7
 Epoch:		1
 License:	GPL v2 / LGPL v2.1
 Group:		Base
@@ -75,6 +75,8 @@ Patch20:	uname-deps.patch
 Patch21:	aarch64.patch
 Patch22:	ix86-platforms.patch
 Patch23:	shortcircuited-deps.patch
+Patch24:	cpuinfo-deps.patch
+Patch25:	rpmio-read-proc-files.patch
 URL:		https://rpm.org/
 BuildRequires:	acl-devel
 BuildRequires:	db-devel >= %{db_ver}
@@ -564,6 +566,8 @@ Dokumentacja API RPM-a oraz przewodniki w formacie HTML generowane ze
 %patch21 -p1
 %patch22 -p1
 %patch23 -p1
+%patch24 -p1
+%patch25 -p1
 
 install %{SOURCE15} scripts/perl.prov.in
 
diff --git a/cpuinfo-deps.patch b/cpuinfo-deps.patch
new file mode 100644
index 0000000..1dab910
--- /dev/null
+++ b/cpuinfo-deps.patch
@@ -0,0 +1,289 @@
+diff -ur rpm-4.16.0/lib/depends.c rpm-4.16.0-cpuinfo/lib/depends.c
+--- rpm-4.16.0/lib/depends.c	2020-11-08 20:19:15.625093667 +0100
++++ rpm-4.16.0-cpuinfo/lib/depends.c	2020-11-08 20:23:46.685893216 +0100
+@@ -697,6 +697,16 @@
+ 	}
+     }
+ 
++    if (strstr(N, "cpuinfo(") == N) {
++	if (tsmem->cpuinfo == NULL)
++	    rpmdsCpuinfoPool(rpmtsPool(ts), &(tsmem->cpuinfo));
++	
++	if (tsmem->cpuinfo != NULL && rpmdsSearch(tsmem->cpuinfo, dep) >= 0) {
++	    rpmdsNotify(dep, "(cpuinfo provides)", rc);
++	    goto exit;
++	}
++    }
++
+     /* Dont look at pre-requisites of already installed packages */
+     if (!adding && isTransientReq(dsflags))
+ 	goto exit;
+diff -ur rpm-4.16.0/lib/rpmds.c rpm-4.16.0-cpuinfo/lib/rpmds.c
+--- rpm-4.16.0/lib/rpmds.c	2020-11-08 20:19:15.625093667 +0100
++++ rpm-4.16.0-cpuinfo/lib/rpmds.c	2020-11-08 20:16:25.941242497 +0100
+@@ -2,6 +2,8 @@
+  * \file lib/rpmds.c
+  */
+ #include "system.h"
++#include <popt.h>
++#include <ctype.h>
+ #include <sys/utsname.h>
+ 
+ #include <rpm/rpmtypes.h>
+@@ -9,6 +11,9 @@
+ #include <rpm/rpmstring.h>
+ #include <rpm/rpmlog.h>
+ #include <rpm/rpmstrpool.h>
++#include <rpm/rpmmacro.h>
++
++#include "rpmio/rpmio_internal.h"	/* XXX for rpmioSlurp */
+ 
+ #include "lib/rpmds_internal.h"
+ 
+@@ -1655,3 +1670,203 @@
+ {
+     return rpmdsUnamePool(NULL, dsp);
+ }
++
++struct cpuinfo_s {
++    const char *name;
++    int done;
++    int flags;
++};
++
++static struct cpuinfo_s ctags[] = {
++    { "processor",	0,  0 },
++    { "Processor",	0,  1 },	/* XXX armv5 */
++    { "vendor_id",	0,  0 },
++    { "cpu_family",	0,  1 },
++    { "model",		0,  1 },
++    { "model_name",	0,  0 },
++    { "stepping",	0,  1 },
++    { "cpu_MHz",	0,  1 },
++    { "CPU_implementer",0,  1 },	/* XXX armv5 */
++    { "CPU_architecture",0,  1 },	/* XXX armv5 */
++    { "CPU_variant",	0,  1 },	/* XXX armv5 */
++    { "CPU_part",	0,  1 },	/* XXX armv5 */
++    { "CPU_revision",	0,  1 },	/* XXX armv5 */
++    { "Hardware",	0,  2 },	/* XXX armv5 */
++    { "Revision",	0,  1 },	/* XXX armv5 */
++    { "Serial",		0,  1 },	/* XXX armv5 */
++    { "cache_size",	0,  1 },
++    { "physical_id",	0,  0 },
++    { "siblings",	0,  0 },
++    { "core_id",	0,  0 },
++    { "cpu_cores",	0,  0 },
++    { "fdiv_bug",	0,  3 },
++    { "hlt_bug",	0,  3 },
++    { "f00f_bug",	0,  3 },
++    { "coma_bug",	0,  3 },
++    { "fpu",		0,  0 },	/* XXX use flags attribute instead. */
++    { "fpu_exception",	0,  3 },
++    { "cpuid_level",	0,  0 },
++    { "wp",		0,  3 },
++    { "flags",		0,  4 },
++    { "Features",	0,  4 },	/* XXX armv5 */
++    { "bogomips",	0,  1 },
++    { "BogoMIPS",	0,  1 },	/* XXX armv5 */
++    { "clflush_size",	0,  1 },
++    { NULL,		0, -1 }
++};
++
++/**
++ * Return dependency format to use for a cpuinfo line.
++ * @param name		field name
++ * @return		type of format (0 == ignore, -1 == not found)
++ */
++static int rpmdsCpuinfoCtagFlags(const char * name)
++{
++    struct cpuinfo_s * ct;
++    int flags = -1;
++
++    for (ct = ctags; ct->name != NULL; ct++) {
++	if (strcmp(ct->name, name))
++	    continue;
++	if (ct->done)
++	    continue;
++	ct->done = 1;		/* XXX insure single occurrence */
++	flags = ct->flags;
++	break;
++    }
++    return flags;
++}
++
++#define	_PROC_CPUINFO	"/proc/cpuinfo"
++
++int rpmdsCpuinfoPool(rpmstrPool pool, rpmds *dsp)
++{
++    char * cpuinfo_path = NULL;
++    struct cpuinfo_s * ct;
++    const char * NS = "cpuinfo";
++    char * iob = NULL;
++    char * f, * fe, * fend;
++    char * g, * ge;
++    char * t;
++    int rc = -1;
++
++	cpuinfo_path = rpmExpand("%{?_rpmds_cpuinfo_path}", NULL);
++	/* XXX may need to validate path existence somewhen. */
++	if (cpuinfo_path == NULL || *cpuinfo_path != '/') {
++	    cpuinfo_path = _free(cpuinfo_path);
++	    cpuinfo_path = xstrdup(_PROC_CPUINFO);
++	}
++
++    /* Reset done variables. */
++    for (ct = ctags; ct->name != NULL; ct++)
++	ct->done = 0;
++
++    rc = rpmioSlurp(cpuinfo_path, (uint8_t **) &iob, NULL);
++    if (rc != 0 || iob == NULL)
++	goto exit;
++
++    for (f = (char *)iob; *f != '\0'; f = fend) {
++	/* find EOL */
++	fe = f;
++	while (*fe != '\0' && !(*fe == '\n' || *fe == '\r'))
++	    fe++;
++	ge = fe;
++	while (*fe != '\0' && (*fe == '\n' || *fe == '\r'))
++	    *fe++ = '\0';
++	fend = fe;
++
++	/* rtrim on line. */
++	while (--ge > f && isspace(*ge))
++	    *ge = '\0';
++
++	/* ltrim on line. */
++	while (*f && isspace(*f))
++	    f++;
++
++	/* split on ':' */
++	fe = f;
++	while (*fe && *fe != ':')
++            fe++;
++	if (*fe == '\0')
++	    continue;
++	g = fe + 1;
++
++	/* rtrim on field 1. */
++	*fe = '\0';
++	while (--fe > f && isspace(*fe))
++	    *fe = '\0';
++	if (*f == '\0')
++	    continue;
++
++	/* ltrim on field 2. */
++	while (*g && isspace(*g))
++            g++;
++	if (*g == '\0')
++	    continue;
++
++	for (t = f; *t != '\0'; t++) {
++	    if (isspace(*t))
++		*t = '_';
++	}
++
++	switch (rpmdsCpuinfoCtagFlags(f)) {
++	case -1:	/* not found */
++	case 0:		/* ignore */
++	default:
++	    continue;
++	    break;
++	case 1:		/* Provides: cpuinfo(f) = g */
++	    for (t = g; *t != '\0'; t++) {
++		if (isspace(*t) || *t == '(' || *t == ')')
++		    *t = '_';
++	    }
++	    rc = rpmdsNSAdd(pool, dsp, NS, f, g, RPMSENSE_EQUAL);
++            if (rc < 0)
++       		goto exit;
++	    break;
++	case 2:		/* Provides: cpuinfo(g) */
++	    for (t = g; *t != '\0'; t++) {
++		if (isspace(*t) || *t == '(' || *t == ')')
++		    *t = '_';
++	    }
++	    rc = rpmdsNSAdd(pool, dsp, NS, g, "", RPMSENSE_ANY);
++            if (rc < 0)
++       		goto exit;
++	    break;
++	case 3:		/* if ("yes") Provides: cpuinfo(f) */
++	   if (!strcmp(g, "yes")) {
++		rc = rpmdsNSAdd(pool, dsp, NS, f, "", RPMSENSE_ANY);
++                if (rc < 0)
++          		goto exit;
++	   }
++	    break;
++	case 4:		/* Provides: cpuinfo(g[i]) */
++	{   char ** av = NULL;
++	    int i = 0;
++	    rc = poptParseArgvString(g, NULL, (const char ***)&av);
++	    if (!rc && av != NULL)
++	    while ((t = av[i++]) != NULL) {
++		rc = rpmdsNSAdd(pool, dsp, NS, t, "", RPMSENSE_ANY);
++                if (rc < 0)
++       		    goto exit;
++	    }
++	    t = NULL;
++	    if (av != NULL)
++		free(av);
++	}   break;
++	}
++    }
++
++exit:
++    _free(cpuinfo_path);
++    free(iob);
++    /* freeze the pool to save memory, but only if private pool */
++    if (*dsp && (*dsp)->pool != pool)
++	rpmstrPoolFreeze((*dsp)->pool, 0);
++    return (rc < 0) ? -1 : 0;
++}
++
++int rpmdsCpuinfo(rpmds * dsp)
++{
++    return rpmdsCpuinfoPool(NULL, dsp);
++}
+diff -ur rpm-4.16.0/lib/rpmds.h rpm-4.16.0-cpuinfo/lib/rpmds.h
+--- rpm-4.16.0/lib/rpmds.h	2020-11-08 20:19:15.625093667 +0100
++++ rpm-4.16.0-cpuinfo/lib/rpmds.h	2020-11-08 20:03:44.001865655 +0100
+@@ -419,6 +419,13 @@
+  */
+ int rpmdsUname(rpmds * dsp);
+ 
++/**
++ * Load cpuinfo provides into a dependency set.
++ * @retval *dsp		(loaded) dependency set
++ * @return		0 on success
++ */
++int rpmdsCpuinfo(rpmds * dsp);
++
+ /** \ingroup rpmds
+  * Create and load a dependency set.
+  * @param pool		shared string pool (or NULL for private pool)
+@@ -483,6 +490,14 @@
+  */
+ int rpmdsUnamePool(rpmstrPool pool, rpmds * dsp);
+ 
++/**
++ * Load cpuinfo provides into a dependency set.
++ * @param pool		shared string pool (or NULL for private pool)
++ * @retval *dsp		(loaded) dependency set
++ * @return		0 on success
++ */
++int rpmdsCpuinfoPool(rpmstrPool pool, rpmds * dsp);
++
+ 
+ typedef enum rpmrichOp_e {
+     RPMRICHOP_SINGLE  = 1,
+diff -ur rpm-4.16.0/lib/rpmts_internal.h rpm-4.16.0-cpuinfo/lib/rpmts_internal.h
+--- rpm-4.16.0/lib/rpmts_internal.h	2020-11-08 20:19:15.625093667 +0100
++++ rpm-4.16.0-cpuinfo/lib/rpmts_internal.h	2020-11-08 20:22:24.382319931 +0100
+@@ -22,6 +22,7 @@
+ 
+     rpmds rpmlib;		/*!< rpmlib() dependency set. */
+     rpmds uname;		/*!< uname() dependency set. */
++    rpmds cpuinfo;		/*!< cpuinfo() dependency set. */
+     rpmte * order;		/*!< Packages sorted by dependencies. */
+     int orderCount;		/*!< No. of transaction elements. */
+     int orderAlloced;		/*!< No. of allocated transaction elements. */
diff --git a/rpmio-read-proc-files.patch b/rpmio-read-proc-files.patch
new file mode 100644
index 0000000..27118bf
--- /dev/null
+++ b/rpmio-read-proc-files.patch
@@ -0,0 +1,25 @@
+--- rpm-4.16.0/rpmio/rpmio.c~	2020-08-27 15:13:08.000000000 +0200
++++ rpm-4.16.0/rpmio/rpmio.c	2020-11-08 21:31:26.311430982 +0100
+@@ -1709,6 +1709,22 @@
+ 	}
+ 	b[blen] = '\0';
+     }
++#if defined(__linux__)
++    /* XXX st->st_size = 0 for /proc files on linux, see stat(2). */
++    /* XXX glibc mmap'd libio no workie for /proc files on linux?!? */
++    else if (!strncmp(fn, "/proc/", sizeof("/proc/")-1)) {
++	blen = blenmax;
++	b = xmalloc(blen+1);
++	b[0] = '\0';
++
++	size = read(Fileno(fd), b, blen);
++	if (size < 0) {
++		rc = 1;
++		goto exit;
++	}
++	blen = size;
++    }
++#endif
+ 
+ exit:
+     if (fd) (void) Fclose(fd);
diff --git a/uname-deps.patch b/uname-deps.patch
index 4863617..61ba652 100644
--- a/uname-deps.patch
+++ b/uname-deps.patch
@@ -7,7 +7,7 @@ index 28a4a784d..1d8ce1f8a 100644
      }
  
 +    char * N = rpmdsN(dep);
-+    if (strstr(N, "uname") == N) {
++    if (strstr(N, "uname(") == N) {
 +	if (tsmem->uname == NULL)
 +	    rpmdsUnamePool(rpmtsPool(ts), &(tsmem->uname));
 +	
@@ -32,44 +32,53 @@ index f7ee76392..754969e39 100644
  
  #include <rpm/rpmtypes.h>
  #include <rpm/rpmlib.h>		/* rpmvercmp */
-@@ -1596,3 +1597,51 @@ rpmRC rpmdsParseRichDep(rpmds dep, rpmds *leftds, rpmds *rightds, rpmrichOp *op,
+@@ -1596,3 +1597,60 @@ rpmRC rpmdsParseRichDep(rpmds dep, rpmds *leftds, rpmds *rightds, rpmrichOp *op,
      return rc;
  }
  
++/**
++ * Merge a single provides, wrapping N as "NS(N)".
++ */
++static int rpmdsNSAdd(rpmstrPool pool, rpmds *dsp, const char * NS,
++		const char *N, const char *EVR, rpmsenseFlags Flags)
++{
++    char *t;
++    rpmds ds;
++    int rc;
++
++    t = (char *) alloca(strlen(NS)+sizeof("()")+strlen(N));
++    *t = '\0';
++    (void) stpcpy( stpcpy( stpcpy( stpcpy(t, NS), "("), N), ")");
++
++    ds = rpmdsSinglePool(pool, RPMTAG_PROVIDENAME, t, EVR, Flags);
++    rc = rpmdsMerge(dsp, ds);
++    rpmdsFree(ds);
++    return rc;
++}
++
 +int rpmdsUnamePool(rpmstrPool pool, rpmds * dsp)
 +{
 +    int rc = -1;
 +    static const char * NS = "uname";
 +    struct utsname un;
-+    rpmds ds;
 +
 +    if (uname(&un) < 0)
 +	goto exit;
 +
-+    ds = rpmdsSinglePool(pool, RPMTAG_PROVIDENAME, "uname(sysname)", un.sysname, RPMSENSE_EQUAL);
-+    rc = rpmdsMerge(dsp, ds);
-+    rpmdsFree(ds);
++    rc = rpmdsNSAdd(pool, dsp, NS, "sysname", un.sysname, RPMSENSE_EQUAL);
 +    if (rc < 0)
 +	goto exit;
-+    ds = rpmdsSinglePool(pool, RPMTAG_PROVIDENAME, "uname(nodename)", un.nodename, RPMSENSE_EQUAL);
-+    rc = rpmdsMerge(dsp, ds);
-+    rpmdsFree(ds);
++    rc = rpmdsNSAdd(pool, dsp, NS, "nodename", un.nodename, RPMSENSE_EQUAL);
 +    if (rc < 0)
 +	goto exit;
-+    ds = rpmdsSinglePool(pool, RPMTAG_PROVIDENAME, "uname(release)", un.release, RPMSENSE_EQUAL);
-+    rc = rpmdsMerge(dsp, ds);
-+    rpmdsFree(ds);
++    rc = rpmdsNSAdd(pool, dsp, NS, "release", un.release, RPMSENSE_EQUAL);
 +    if (rc < 0)
 +	goto exit;
-+    ds = rpmdsSinglePool(pool, RPMTAG_PROVIDENAME, "uname(machine)", un.machine, RPMSENSE_EQUAL);
-+    rc = rpmdsMerge(dsp, ds);
-+    rpmdsFree(ds);
++    rc = rpmdsNSAdd(pool, dsp, NS, "machine", un.machine, RPMSENSE_EQUAL);
 +    if (rc < 0)
 +	goto exit;
 +#if defined(__linux__)
-+    ds = rpmdsSinglePool(pool, RPMTAG_PROVIDENAME, "uname(domainname)", un.domainname, RPMSENSE_EQUAL);
-+    rc = rpmdsMerge(dsp, ds);
-+    rpmdsFree(ds);
++    rc = rpmdsNSAdd(pool, dsp, NS, "domainname", un.domainname, RPMSENSE_EQUAL);
 +    if (rc < 0)
 +	goto exit;
 +#endif
================================================================

---- gitweb:

http://git.pld-linux.org/gitweb.cgi/packages/rpm.git/commitdiff/2aa7d974ad81aa11e64f99d8a0b8af5d8176b044



More information about the pld-cvs-commit mailing list