-
Notifications
You must be signed in to change notification settings - Fork 414
Move ~/.rpmmacros and ~/.rpmrc to ~/.config/rpm/ #3750
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: master
Are you sure you want to change the base?
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -38,9 +38,12 @@ _macro path_ uses this to achieve the following hierarchy of settings: | |
|
|
||
| The default _macro path_ can be inspected with *rpm --showrc|grep ^Macro*. | ||
|
|
||
| In older versions of rpm, the path of per-user macros was _~/.rpmmacros_. | ||
| This is still processed if it exists and the new configuration directory | ||
| does not exist. | ||
| In older versions of rpm, the path of per-user macros was | ||
| _~/.rpmmacros_. RPM will try to move this file to the new | ||
| locations. If this is not possible it will create | ||
| _~/.rpmconfig_migration_lock_ to prevent attempting the migration over | ||
| and over again. In this case the file is still processed if it exists | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I suppose "this file" is the macros file, correct? If so, I'd suggest mentioning it explicitly here, to avoid confusion. Also, I wonder if we should mention here (briefly) what happens when the lock file is removed. As it is now, the migration would only be retried if the new directory in |
||
| and the new configuration directory does not exist. | ||
|
|
||
| # CONFIGURATION | ||
| The following configurables are supported for the *rpm* runtime (as | ||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -5,6 +5,7 @@ | |
| #include <string> | ||
| #include <unordered_map> | ||
| #include <vector> | ||
| #include <filesystem> | ||
|
|
||
| #include <fcntl.h> | ||
| #include <stdarg.h> | ||
|
|
@@ -48,6 +49,8 @@ | |
| using wrlock = std::unique_lock<std::shared_mutex>; | ||
| using rdlock = std::shared_lock<std::shared_mutex>; | ||
|
|
||
| namespace fs = std::filesystem; | ||
|
|
||
| static const char * defrcfiles = NULL; | ||
| const char * macrofiles = NULL; | ||
|
|
||
|
|
@@ -358,6 +361,109 @@ const char * lookupInDefaultTable(const char * name, | |
| return name; | ||
| } | ||
|
|
||
| static int moveConfigFiles(std::string userdir) | ||
| { | ||
| /* Don't migrate in scripts */ | ||
| if (!isatty(STDIN_FILENO)) | ||
| return -1; | ||
| /* Don't migrate with root priviledges */ | ||
| if (geteuid() == 0) | ||
| return -1; | ||
|
|
||
| fs::path home = std::getenv("HOME"); | ||
| std::error_code ec; | ||
| std::error_code ec2; | ||
| fs::path oldmacros = home / ".rpmmacros"; | ||
| fs::path oldrpmrc = home / ".rpmrc"; | ||
| fs::path lockfile = home / ".rpmconfig_migration_lock"; | ||
| fs::path macros_target = ""; | ||
| fs::path rpmrc_target = ""; | ||
|
|
||
| bool move_rpmrc = false; | ||
| bool move_macros = false; | ||
|
|
||
| if (userdir.substr(0, 2) == "~/") | ||
| userdir.replace(0, 1, home); | ||
|
|
||
| fs::path userdir_path = userdir; | ||
| fs::path newmacros = userdir_path / "macros"; | ||
| fs::path newrpmrc = userdir_path / "rpmrc"; | ||
|
|
||
| if (!fs::is_regular_file(oldmacros, ec) && !fs::is_regular_file(oldrpmrc, ec)) | ||
| return -1; | ||
|
|
||
| int fd = open(lockfile.c_str(), O_CREAT|O_EXCL|O_WRONLY, 0644); | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Perhaps silly, but couldn't we reuse the |
||
| if (fd < 0) | ||
| return -1; | ||
| close(fd); | ||
|
|
||
| /* recheck after acquiring lock */ | ||
| if (fs::exists(userdir_path, ec) || | ||
| (!fs::is_regular_file(oldmacros, ec) && | ||
| !fs::is_regular_file(oldrpmrc, ec))) { | ||
| fs::remove(lockfile, ec); | ||
| return -1; | ||
| } | ||
|
|
||
| fs::create_directories(userdir_path, ec); | ||
| if (ec) goto err; | ||
|
|
||
| if (fs::is_regular_file(oldmacros)) { | ||
| fs::rename(oldmacros, newmacros, ec); | ||
| if (ec) goto undo; | ||
| macros_target = fs::relative(newmacros, home, ec); | ||
| if (ec) goto undo; | ||
| move_macros = true; | ||
| fs::create_symlink(macros_target , oldmacros, ec); | ||
| if (ec) goto undo; | ||
| } | ||
| if (fs::is_regular_file(oldrpmrc)) { | ||
| fs::rename(oldrpmrc, newrpmrc, ec); | ||
| if (ec) goto undo; | ||
| rpmrc_target = fs::relative(newrpmrc, home, ec); | ||
| if (ec) goto undo; | ||
| move_rpmrc = true; | ||
| fs::create_symlink(rpmrc_target , oldrpmrc, ec); | ||
| if (ec) goto undo; | ||
| } | ||
|
|
||
| if (fs::is_symlink(oldmacros, ec)) { | ||
| rpmlog(RPMLOG_WARNING, "Migrated %s to %s (leaving a symlink)\n", | ||
| oldmacros.c_str(), newmacros.c_str()); | ||
pmatilai marked this conversation as resolved.
Show resolved
Hide resolved
|
||
| } | ||
| if (fs::is_symlink(oldrpmrc, ec)) { | ||
| rpmlog(RPMLOG_WARNING, "Migrated %s to %s (leaving a symlink)\n", | ||
| oldrpmrc.c_str(), newrpmrc.c_str()); | ||
| } | ||
|
|
||
| fs::remove(lockfile, ec); | ||
|
|
||
| return 0; | ||
| undo: | ||
| if (move_macros && fs::is_symlink(oldmacros, ec2)) | ||
| fs::remove(oldmacros, ec2); | ||
| if (move_rpmrc && fs::is_symlink(oldrpmrc, ec2)) | ||
| fs::remove(oldrpmrc, ec2); | ||
|
|
||
| if (fs::is_regular_file(newmacros, ec2)) | ||
| fs::rename(newmacros, oldmacros, ec2); | ||
| if (fs::is_regular_file(newrpmrc, ec2)) | ||
| fs::rename(newrpmrc, oldrpmrc, ec2); | ||
| /* userdir_path did not exist at the beginning */ | ||
| fs::remove(userdir_path, ec2); | ||
| err: | ||
| if (fs::exists(oldmacros, ec2)) { | ||
| rpmlog(RPMLOG_ERR, "Could not migrate %s to %s: %s\n", | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Do we really want this to be an error? It seems too drastic, a failed migration doesn't mean reduced functionality in rpm, it's more of a house-keeping thing that's nice to have (at least for now). |
||
| oldmacros.c_str(), newmacros.c_str(), ec.message().c_str()); | ||
| } | ||
| if (fs::exists(oldrpmrc, ec2)) { | ||
| rpmlog(RPMLOG_ERR, "Could not migrate %s to %s: %s\n", | ||
| oldrpmrc.c_str(), newrpmrc.c_str(), ec.message().c_str()); | ||
pmatilai marked this conversation as resolved.
Show resolved
Hide resolved
|
||
| } | ||
|
|
||
| return -1; | ||
| } | ||
|
|
||
| static void setDefaults(void) | ||
| { | ||
| /* If either is missing, we need to go through this whole dance */ | ||
|
|
@@ -379,11 +485,13 @@ static void setDefaults(void) | |
| if (rpmGlob(userdir, NULL, NULL)) { | ||
| const char *oldmacros = "~/.rpmmacros"; | ||
| const char *oldrc = "~/.rpmrc"; | ||
| if (rpmGlob(oldmacros, NULL, NULL) == 0 || rpmGlob(oldrc, NULL, NULL) == 0) { | ||
| free(usermacros); | ||
| free(userrc); | ||
| usermacros = xstrdup(oldmacros); | ||
| userrc = xstrdup(oldrc); | ||
| if ((rpmGlob(oldmacros, NULL, NULL) == 0 || rpmGlob(oldrc, NULL, NULL) == 0)) { | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This line change seems accidental (?) |
||
| if (moveConfigFiles(userdir)) { | ||
| free(usermacros); | ||
| free(userrc); | ||
| usermacros = xstrdup(oldmacros); | ||
| userrc = xstrdup(oldrc); | ||
| } | ||
| } | ||
| } | ||
|
|
||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -7,9 +7,9 @@ AT_KEYWORDS([macros]) | |
|
|
||
| # .rpmmacros exists, new directory not | ||
| RPMTEST_CHECK([[ | ||
| rm -rf ~/.config/rpm ~/.rpmmacros | ||
| touch ~/.rpmmacros | ||
| rpm --showrc | awk '/^Macro path/{print(a[split($0,a,":")])}' | ||
| runroot rm -rf /root/.config/rpm /root/.rpmmacros | ||
| runroot touch /root/.rpmmacros | ||
| runroot rpm --showrc | awk '/^Macro path/{print(a[split($0,a,":")])}' | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Are these changes intentional? |
||
| ]], | ||
| [0], | ||
| [~/.rpmmacros | ||
|
|
@@ -50,6 +50,60 @@ SOMENV=/tmp/somewhere rpm --macros "%{getenv:SOMENV}" --eval "%somewhere" | |
| []) | ||
| RPMTEST_CLEANUP | ||
|
|
||
| RPMTEST_SETUP_RW([macro path]) | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. There already is a test with this name, maybe add something after a colon? |
||
| AT_KEYWORDS([convert .macros]) | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This, OTOH, should probably be just |
||
| RPMTEST_USER | ||
|
|
||
| runroot_user rm -f /home/$RPMUSER/.config/rpm | ||
| runroot_user rm -f /home/$RPMUSER/.rpmmacros | ||
| runroot_user rm -f /home/$RPMUSER/.rpmrc | ||
| runroot_user bash -c "echo %foo bar > /home/$RPMUSER/.rpmmacros" | ||
| runroot_user touch "/home/$RPMUSER/.rpmrc" | ||
|
|
||
| RPMTEST_CHECK([[ | ||
| runroot_user mkdir /home/$RPMUSER/.config | ||
| runroot_user chmod 000 /home/$RPMUSER/.config | ||
| runroot_user rpm -E "%{foo}" | ||
| runroot_user chmod 755 /home/$RPMUSER/.config | ||
| runroot_user ls /home/$RPMUSER/.rpmconfig_migration_lock | ||
| runroot_user rpm -E "%{foo}" | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This probably deserves a |
||
| runroot_user rm /home/$RPMUSER/.rpmconfig_migration_lock | ||
| ]], | ||
| [0], | ||
| [bar | ||
| /home/klang/.rpmconfig_migration_lock | ||
| bar | ||
| ], | ||
| [error: Could not migrate /home/klang/.rpmmacros to /home/klang/.config/rpm/macros: Permission denied | ||
| error: Could not migrate /home/klang/.rpmrc to /home/klang/.config/rpm/rpmrc: Permission denied | ||
| ]) | ||
|
|
||
| RPMTEST_CHECK([[ | ||
| runroot_user readlink /home/$RPMUSER/.rpmmacros | ||
| runroot_user readlink /home/$RPMUSER/.rpmrc | ||
| # don't convert if not tty | ||
| runroot_user rpm -E "%{foo}" < "${RPMTEST}"/data/macros.testfile | ||
| runroot_user readlink /home/$RPMUSER/.rpmmacros | ||
| runroot_user readlink /home/$RPMUSER/.rpmrc | ||
| runroot_user rpm -E "%{foo}" | ||
| runroot_user readlink /home/$RPMUSER/.rpmmacros | ||
| runroot_user readlink /home/$RPMUSER/.rpmrc | ||
| runroot_user rpm -E "%{foo}" | ||
| runroot_user rpm --showrc | awk '/^Macro path/{print(a[split($0,a,":")])}' | ||
| ]], | ||
| [0], | ||
| [bar | ||
| bar | ||
| .config/rpm/macros | ||
| .config/rpm/rpmrc | ||
| bar | ||
| ~/.config/rpm/macros | ||
| ], | ||
| [warning: Migrated /home/klang/.rpmmacros to /home/klang/.config/rpm/macros (leaving a symlink) | ||
| warning: Migrated /home/klang/.rpmrc to /home/klang/.config/rpm/rpmrc (leaving a symlink) | ||
| ]) | ||
| RPMTEST_CLEANUP | ||
|
|
||
| # ------------------------------ | ||
| RPMTEST_SETUP_RW([macro path: skip editor backups]) | ||
| AT_KEYWORDS([macros]) | ||
|
|
||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Maybe mention that
XDG_CONFIG_HOMEis the new location.