File 0003-Make-build-in-place-much-less-of-a-hack-and-also-wor.patch of Package rpm

From d1075106bb315913574e1acac921058d23dd5130 Mon Sep 17 00:00:00 2001
From: Panu Matilainen <pmatilai@redhat.com>
Date: Thu, 23 May 2024 10:22:15 +0300
Subject: [PATCH 3/3] Make --build-in-place much less of a hack and also, work

Instead of skipping everything in %setup, take advantage of it:
we shouldn't unpack any sources but otherwise we can just let it
fall through it, defining buildsubdir and everything, if we let
rpm do its normal %mkbuilddir thing and just symlink to the in-place
tree from rpm's %builddir. This way it's not such an ugly duckling
interfering with how normal rpms are built, and even honors %setup
flags to a degree.

This fixes two regressions: one introduced when adding %mkbuilddir that
nukes your current directory with no questions asked if --build-in-place
is used before it even starts, and an earlier one from commit
b34333fa021c0ee7215714eeef96d1a2843ea08e that would nuke your precious
in-place directory afterwards. And as a side-effect of all this, debuginfo
generation also now works with --build-in-place.

Fixes: #3122
Fixes: #3042
---
 build/parsePrep.c | 17 ++++++++++-----
 tests/rpmbuild.at | 55 +++++++++++++++++++++++++++++++++++++++++++++++
 tools/rpmbuild.c  |  8 +------
 3 files changed, 68 insertions(+), 12 deletions(-)

diff --git a/build/parsePrep.c b/build/parsePrep.c
index 4754827f5..6aa692d40 100644
--- a/build/parsePrep.c
+++ b/build/parsePrep.c
@@ -171,6 +171,7 @@ void doSetupMacro(rpmMacroBuf mb, rpmMacroEntry me, ARGV_t margs, size_t *parsed
     int leaveDirs = 0, skipDefaultAction = 0;
     int createDir = 0, quietly = 0, autoPath = 0;
     char * dirName = NULL;
+    int buildInPlace = rpmExpandNumeric("%{?_build_in_place}");
     struct poptOption optionsTable[] = {
 	    { NULL, 'a', POPT_ARG_STRING, NULL, 'a',	NULL, NULL},
 	    { NULL, 'b', POPT_ARG_STRING, NULL, 'b',	NULL, NULL},
@@ -190,10 +191,6 @@ void doSetupMacro(rpmMacroBuf mb, rpmMacroEntry me, ARGV_t margs, size_t *parsed
 	goto exit;
     }
 
-    if (rpmExpandNumeric("%{_build_in_place}")) {
-	goto exit;
-    }
-
     optCon = poptGetContext(NULL, argc, argv, optionsTable, 0);
     while ((arg = poptGetNextOpt(optCon)) > 0) {
 	char *optArg = poptGetOptArg(optCon);
@@ -206,7 +203,8 @@ void doSetupMacro(rpmMacroBuf mb, rpmMacroEntry me, ARGV_t margs, size_t *parsed
 	    goto exit;
 	}
 
-	{   char *chptr = doUntar(spec, num, quietly, 0);
+	if (!buildInPlace) {
+	    char *chptr = doUntar(spec, num, quietly, 0);
 	    if (chptr == NULL)
 		goto exit;
 
@@ -235,6 +233,15 @@ void doSetupMacro(rpmMacroBuf mb, rpmMacroEntry me, ARGV_t margs, size_t *parsed
 	free(buildSubdir);
     }
     
+    if (buildInPlace) {
+	skipDefaultAction = 1;
+	leaveDirs = 1;
+	/* note that pwd needs to be from parse, not build time */
+	char *buf = rpmExpand("ln -s %(pwd) %{buildsubdir}", NULL);
+	appendMb(mb, buf, 1);
+	free(buf);
+    }
+
     /* cd to the build dir */
     {	char * buildDir = rpmGenPath(spec->rootDir, "%{_builddir}", "");
 
diff --git a/tests/rpmbuild.at b/tests/rpmbuild.at
index 7e4b088aa..a665a6bce 100644
--- a/tests/rpmbuild.at
+++ b/tests/rpmbuild.at
@@ -321,6 +321,61 @@ run rpmbuild \
 [ignore])
 RPMTEST_CLEANUP
 
+AT_SETUP([rpmbuild --build-in-place])
+AT_KEYWORDS([build])
+RPMDB_INIT
+
+RPMTEST_CHECK([
+runroot_other tar xf /data/SOURCES/hello-2.0.tar.gz
+runroot_other mv hello-2.0/hello.spec .
+runroot_other find hello-2.0 | sort
+],
+[0],
+[hello-2.0
+hello-2.0/COPYING
+hello-2.0/FAQ
+hello-2.0/Makefile
+hello-2.0/README
+hello-2.0/hello.c
+],
+[])
+
+RPMTEST_CHECK([
+runroot --chdir hello-2.0 rpmbuild -bb --build-in-place ../hello.spec
+],
+[0],
+[ignore],
+[ignore])
+
+RPMTEST_CHECK([
+runroot rpm -qp --qf "%{name}-%{version}-%{release}\n" /build/RPMS/*/*.rpm
+],
+[0],
+[hello-2.0-1
+hello-debuginfo-2.0-1
+],
+[])
+
+# finally, see that we left the tree intact 
+RPMTEST_CHECK([
+runroot_other find hello-2.0 | sort
+],
+[0],
+[hello-2.0
+hello-2.0/COPYING
+hello-2.0/FAQ
+hello-2.0/Makefile
+hello-2.0/README
+hello-2.0/debugfiles.list
+hello-2.0/debuglinks.list
+hello-2.0/debugsources.list
+hello-2.0/elfbins.list
+hello-2.0/hello
+hello-2.0/hello.c
+],
+[])
+RPMTEST_CLEANUP
+
 AT_SETUP([rpmbuild with %autosetup -C])
 AT_KEYWORDS([build])
 RPMDB_INIT
diff --git a/tools/rpmbuild.c b/tools/rpmbuild.c
index 459427fe3..dd36e24d8 100644
--- a/tools/rpmbuild.c
+++ b/tools/rpmbuild.c
@@ -136,6 +136,7 @@ static void buildArgCallback( poptContext con,
     case POPT_BUILDINPLACE:
 	rpmDefineMacro(NULL, "_build_in_place 1", 0);
 	buildInPlace = 1;
+	nobuildAmount |= RPMBUILD_RMBUILD;
 	break;
     }
 }
@@ -432,13 +433,6 @@ static int buildForTarget(rpmts ts, const char * arg, BTA_t ba,
     int rc = 1; /* assume failure */
     rpmSpecFlags specFlags = spec_flags;
 
-    /* Override default BUILD value for _builddir */
-    if (buildInPlace) {
-	char *cwd = rpmGetCwd();
-	rpmPushMacro(NULL, "_builddir", NULL, cwd, 0);
-	free(cwd);
-    }
-
     if (ba->buildRootOverride)
 	buildRootURL = rpmGenPath(NULL, ba->buildRootOverride, NULL);
 
-- 
2.45.1

openSUSE Build Service is sponsored by