rpm/hardlinks.diff

61 lines
2.0 KiB
Diff

--- lib/rpmfiles.h.orig
+++ lib/rpmfiles.h
@@ -156,7 +156,7 @@ typedef rpmFlags rpmfiFlags;
#define RPMFI_FLAGS_ERASE \
(RPMFI_NOFILECLASS | RPMFI_NOFILELANGS | \
- RPMFI_NOFILEMTIMES | RPMFI_NOFILERDEVS | RPMFI_NOFILEINODES | \
+ RPMFI_NOFILEMTIMES | RPMFI_NOFILERDEVS | \
RPMFI_NOFILEVERIFYFLAGS)
#define RPMFI_FLAGS_INSTALL \
--- lib/transaction.c.orig
+++ lib/transaction.c
@@ -412,6 +412,8 @@ static void handleInstInstalledFile(const rpmts ts, rpmte p, rpmfiles fi, int fx
{
rpmfs fs = rpmteGetFileStates(p);
int isCfgFile = ((rpmfilesFFlags(otherFi, ofx) | rpmfilesFFlags(fi, fx)) & RPMFILE_CONFIG);
+ int nlink;
+ const int *links;
if (XFA_SKIPPING(rpmfsGetAction(fs, fx)))
return;
@@ -481,7 +483,10 @@ static void handleInstInstalledFile(const rpmts ts, rpmte p, rpmfiles fi, int fx
}
}
- rpmfilesSetFReplacedSize(fi, fx, rpmfilesFSize(otherFi, ofx));
+ /* Only account for the last file of a hardlink set */
+ nlink = rpmfilesFLinks(otherFi, ofx, &links);
+ if (nlink <= 1 || links[nlink - 1] == ofx)
+ rpmfilesSetFReplacedSize(fi, fx, rpmfilesFSize(otherFi, ofx));
}
/**
@@ -491,6 +496,7 @@ static void handleInstInstalledFile(const rpmts ts, rpmte p, rpmfiles fi, int fx
static void handleOverlappedFiles(rpmts ts, fingerPrintCache fpc, rpmte p, rpmfiles fi)
{
rpm_loff_t fixupSize = 0;
+ rpm_loff_t fileSize = 0;
int i, j;
rpmfs fs = rpmteGetFileStates(p);
rpmfs otherFs;
@@ -675,9 +681,16 @@ assert(otherFi != NULL);
}
rpmfilesFree(otherFi);
+ fileSize = rpmfilesFSize(fi, i);
+ nlink = rpmfilesFLinks(fi, i, &links);
+ if (nlink > 1 && links[nlink - 1] != i) {
+ /* Only account for the last file of a hardlink set */
+ fileSize = 0;
+ fixupSize = 0;
+ }
/* Update disk space info for a file. */
rpmtsUpdateDSI(ts, fpEntryDev(fpc, fiFps), fpEntryDir(fpc, fiFps),
- rpmfilesFSize(fi, i), rpmfilesFReplacedSize(fi, i),
+ fileSize, rpmfilesFReplacedSize(fi, i),
fixupSize, rpmfsGetAction(fs, i));
}