Skip to content

Commit

Permalink
Merge pull request #397 from oliverkurth/stable-3.1
Browse files Browse the repository at this point in the history
backport a few fixes to 3.1
  • Loading branch information
oliverkurth authored Feb 15, 2023
2 parents e392773 + 4942894 commit 1e996f9
Show file tree
Hide file tree
Showing 9 changed files with 242 additions and 12 deletions.
2 changes: 1 addition & 1 deletion CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@

CMAKE_MINIMUM_REQUIRED(VERSION 3.0 FATAL_ERROR)

project(tdnf VERSION 3.1.11 LANGUAGES C)
project(tdnf VERSION 3.1.12 LANGUAGES C)
set(VERSION ${PROJECT_VERSION})
set(PROJECT_YEAR 2023)

Expand Down
7 changes: 7 additions & 0 deletions client/config.c
Original file line number Diff line number Diff line change
Expand Up @@ -135,6 +135,13 @@ TDNFReadConfig(
&pConf->ppszMinVersions);
BAIL_ON_TDNF_ERROR(dwError);

dwError = TDNFReadKeyValueInt(
pSection,
TDNF_CONF_KEY_OPENMAX,
TDNF_DEFAULT_OPENMAX,
&pConf->nOpenMax);
BAIL_ON_TDNF_ERROR(dwError);

dwError = TDNFConfigReadProxySettings(
pSection,
pConf);
Expand Down
4 changes: 4 additions & 0 deletions client/defines.h
Original file line number Diff line number Diff line change
Expand Up @@ -76,6 +76,8 @@ typedef enum
#define TDNF_PLUGIN_CONF_KEY_ENABLED "enabled"
#define TDNF_CONF_KEY_EXCLUDE "excludepkgs"
#define TDNF_CONF_KEY_MINVERSIONS "minversions"
#define TDNF_CONF_KEY_OPENMAX "openmax"

//Repo file key names
#define TDNF_REPO_KEY_BASEURL "baseurl"
#define TDNF_REPO_KEY_ENABLED "enabled"
Expand Down Expand Up @@ -119,6 +121,8 @@ typedef enum
#define TDNF_SOLVCACHE_DIR_NAME "solvcache"
#define TDNF_REPO_METADATA_EXPIRE_NEVER "never"

#define TDNF_DEFAULT_OPENMAX 1024

// repo default settings
#define TDNF_REPO_DEFAULT_ENABLED 0
#define TDNF_REPO_DEFAULT_SKIP 0
Expand Down
101 changes: 91 additions & 10 deletions client/rpmtrans.c
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@
*/

#include "includes.h"
#include <sys/resource.h>

uint32_t
TDNFRpmExecTransaction(
Expand Down Expand Up @@ -170,7 +171,7 @@ TDNFPopulateTransaction(
}
if(pSolvedInfo->pPkgsToReinstall)
{
dwError = TDNFTransAddInstallPkgs(
dwError = TDNFTransAddUpgradePkgs(
pTS,
pTdnf,
pSolvedInfo->pPkgsToReinstall);
Expand Down Expand Up @@ -390,6 +391,60 @@ reportProblems(PTDNFRPMTS pTS)
goto cleanup;
}

/*
* Restrict number of open files. When rpm cannot access /proc
* it tries to set the close on exec flag for every possible
* fd, which may take a long time if the limit is very high.
* See also https://github.com/rpm-software-management/rpm/issues/2081.
* This can be disabled by setting "openmax=0" in the configuration.
*/

uint32_t
TDNFSetOpenMax(PTDNF pTdnf)
{
uint32_t dwError = 0;
char *pszProcPath = NULL;
int nIsDir = 0;

if(!pTdnf || !pTdnf->pConf || !pTdnf->pArgs)
{
dwError = ERROR_TDNF_INVALID_PARAMETER;
BAIL_ON_TDNF_ERROR(dwError);
}

/* First, check if /proc is available - if rpm can
open it there is no issue. */
dwError = TDNFJoinPath(&pszProcPath,
pTdnf->pArgs->pszInstallRoot ?
pTdnf->pArgs->pszInstallRoot : "",
"/proc/self/fd",
NULL);
BAIL_ON_TDNF_ERROR(dwError);

dwError = TDNFIsDir(pszProcPath, &nIsDir);
if (dwError == ERROR_TDNF_SYSTEM_BASE + ENOENT) {
nIsDir = 0;
dwError = 0;
}
BAIL_ON_TDNF_ERROR(dwError);

if (!nIsDir) {
int nOpenMax = pTdnf->pConf->nOpenMax;
struct rlimit rl = {nOpenMax, nOpenMax};
if (setrlimit(RLIMIT_NOFILE, &rl) != 0) {
/* shouldn't be fatal */
pr_err("warning: could not set rlimit: %s (%d)."
"This may cause degraded performance.\n",
strerror(errno), errno);
}
}
cleanup:
TDNF_SAFE_FREE_MEMORY(pszProcPath);
return dwError;
error:
goto cleanup;
}

uint32_t
TDNFRunTransaction(
PTDNFRPMTS pTS,
Expand All @@ -402,7 +457,7 @@ TDNFRunTransaction(
uint32_t dwSkipDigest = 0;
int rc;

if(!pTS || !pTdnf || !pTdnf->pArgs)
if(!pTS || !pTdnf || !pTdnf->pConf || !pTdnf->pArgs)
{
dwError = ERROR_TDNF_INVALID_PARAMETER;
BAIL_ON_TDNF_ERROR(dwError);
Expand Down Expand Up @@ -453,7 +508,10 @@ TDNFRunTransaction(
BAIL_ON_TDNF_ERROR(dwError);
}

//TODO do callbacks for output
if (pTdnf->pConf->nOpenMax > 0) {
dwError = TDNFSetOpenMax(pTdnf);
BAIL_ON_TDNF_ERROR(dwError);
}
pr_info("Running transaction\n");

rpmtsSetFlags(pTS->pTS, pTS->nTransFlags);
Expand Down Expand Up @@ -549,13 +607,35 @@ TDNFTransAddInstallPkg(
{
if (!pTdnf->pArgs->nDownloadOnly || pTdnf->pArgs->pszDownloadDir == NULL)
{
dwError = TDNFDownloadPackageToCache(
pTdnf,
pszPackageLocation,
pszPkgName,
pszRepoName,
&pszFilePath
);
int nInPlace = 0;
PTDNF_REPO_DATA_INTERNAL pRepo = NULL;

dwError = TDNFGetRepoById(pTdnf, pszRepoName, &pRepo);
BAIL_ON_TDNF_ERROR(dwError);

/* avoid copying a file to cache if we can access it directly */
if (strncasecmp(pRepo->pszBaseUrl, "file://", 7) == 0)
{
dwError = TDNFJoinPath(&pszFilePath,
&(pRepo->pszBaseUrl[7]),
pszPackageLocation,
NULL);
BAIL_ON_TDNF_ERROR(dwError);
if(access(pszFilePath, F_OK) == 0) {
nInPlace = 1;
}
}

if (!nInPlace)
{
dwError = TDNFDownloadPackageToCache(
pTdnf,
pszPackageLocation,
pszPkgName,
pszRepoName,
&pszFilePath
);
}
}
else
{
Expand All @@ -577,6 +657,7 @@ TDNFTransAddInstallPkg(
if(access(pszFilePath, F_OK))
{
dwError = errno;
pr_err("could not access file %s: %s (%d)\n", pszFilePath, strerror(errno), errno);
BAIL_ON_TDNF_SYSTEM_ERROR(dwError);
}

Expand Down
36 changes: 36 additions & 0 deletions common/memory.c
Original file line number Diff line number Diff line change
Expand Up @@ -62,6 +62,42 @@ TDNFAllocateMemory(
goto cleanup;
}

uint32_t
TDNFReAllocateMemory(
size_t nSize,
void** ppMemory
)
{
uint32_t dwError = 0;
void* pMemory = NULL;

if (!ppMemory || !nSize)
{
dwError = ERROR_TDNF_INVALID_PARAMETER;
BAIL_ON_TDNF_ERROR(dwError);
}

pMemory = realloc(*ppMemory, nSize);
if (!pMemory)
{
dwError = ERROR_TDNF_OUT_OF_MEMORY;
BAIL_ON_TDNF_ERROR(dwError);
}

*ppMemory = pMemory;

cleanup:
return dwError;

error:
if (ppMemory)
{
*ppMemory = NULL;
}
TDNF_SAFE_FREE_MEMORY(pMemory);
goto cleanup;
}

void
TDNFFreeMemory(
void* pMemory
Expand Down
10 changes: 10 additions & 0 deletions common/prototypes.h
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,12 @@ TDNFAllocateMemory(
void** ppMemory
);

uint32_t
TDNFReAllocateMemory(
size_t nSize,
void** ppMemory
);

uint32_t
TDNFAllocateString(
const char* pszSrc,
Expand Down Expand Up @@ -244,6 +250,10 @@ TDNFStringMatchesOneOf(
char **ppszList,
int *pRet);

uint32_t
TDNFJoinPath(
char **ppszPath, ...);

//setopt.c
uint32_t
AddSetOpt(
Expand Down
85 changes: 85 additions & 0 deletions common/utils.c
Original file line number Diff line number Diff line change
Expand Up @@ -759,3 +759,88 @@ TDNFStringMatchesOneOf(const char *pszSearch, char **ppszList, int *pRet)
error:
goto cleanup;
}

uint32_t
TDNFJoinPath(char **ppszPath, ...)
{
uint32_t dwError = 0;
va_list ap;
char *pszNode = NULL;
int i, nCount = 0;
char *pszTmp, *pszNodeTmp;
char *pszNodeCopy = NULL;
char *pszResult = NULL;
int nLength = 0;
int nLengthTmp = 0;

if (!ppszPath)
{
dwError = ERROR_TDNF_INVALID_PARAMETER;
BAIL_ON_TDNF_ERROR(dwError);
}

va_start(ap, ppszPath);
for(pszNode = va_arg(ap, char *); pszNode; pszNode = va_arg(ap, char *))
{
nCount++;
}
va_end(ap);

va_start(ap, ppszPath);
for(pszNode = va_arg(ap, char *), i = 0; pszNode; pszNode = va_arg(ap, char *), i++)
{
dwError = TDNFAllocateString(pszNode, &pszNodeCopy);
BAIL_ON_TDNF_ERROR(dwError);
pszNodeTmp = pszNodeCopy;
/* if the first node is an absolute path, the result should be absolute -
* safe this by initializing with a '/' if absolute, otherwise with an empty string
* before stripping all leading slashes */
if (i == 0)
{
if (*pszNodeTmp == '/')
{
dwError = TDNFAllocateString("/", &pszResult);
nLength++;
}
else
{
dwError = TDNFAllocateString("", &pszResult);
}
BAIL_ON_TDNF_ERROR(dwError);
}
/* now strip leading slashes */
while(*pszNodeTmp == '/') pszNodeTmp++;

/* strip trailing slashes */
nLengthTmp = strlen(pszNodeTmp);
pszTmp = pszNodeTmp + nLengthTmp - 1;
while(pszTmp >= pszNodeTmp && *pszTmp == '/')
{
*pszTmp = 0;
pszTmp--;
}
nLength += nLengthTmp + 2;

dwError = TDNFReAllocateMemory(nLength, (void **)&pszResult);
BAIL_ON_TDNF_ERROR(dwError);

strcat(pszResult, pszNodeTmp);
/* put new slashes between nodes, except for the end */
if (i != nCount-1)
{
strcat(pszResult, "/");
}

TDNF_SAFE_FREE_MEMORY(pszNodeCopy);
}
va_end(ap);

*ppszPath = pszResult;
cleanup:
return dwError;
error:
TDNF_SAFE_FREE_MEMORY(pszResult);
TDNF_SAFE_FREE_MEMORY(pszNodeCopy);
goto cleanup;
}

1 change: 1 addition & 0 deletions include/tdnftypes.h
Original file line number Diff line number Diff line change
Expand Up @@ -256,6 +256,7 @@ typedef struct _TDNF_CONF
int nInstallOnlyLimit;
int nCleanRequirementsOnRemove;
int nKeepCache;
int nOpenMax; //set max number of open files
char* pszRepoDir;
char* pszCacheDir;
char* pszProxy;
Expand Down
8 changes: 7 additions & 1 deletion solv/tdnfpackage.c
Original file line number Diff line number Diff line change
Expand Up @@ -1181,7 +1181,13 @@ SolvGetTransResultsWithType(
break;
}

if (dwType == dwPkgType)
/* Solver uses SOLVER_TRANSACTION_CHANGE if a pkg has
the same nevra, but has differences. If the pkg is
completly identical it uses SOLVER_TRANSACTION_REINSTALL.
For our purposes we don't care. */
if ((dwType == dwPkgType) ||
(dwType == SOLVER_TRANSACTION_REINSTALL &&
dwPkgType == SOLVER_TRANSACTION_CHANGE))
queue_push(&queueSolvedPackages, dwPkg);
}
dwError = SolvQueueToPackageList(&queueSolvedPackages, &pPkgList);
Expand Down

0 comments on commit 1e996f9

Please sign in to comment.