as if there were no packages installed in the system. Use with caution as you
can damage your system using this option.
+.SH "NOTES"
+.TP
+.B Notification About Running Processes Using Deleted Files
+After each upgrade or removal of packages Zypper checks whether
+there are any runing processes that may be using files recently
+deleted by an upgrade or package removal. If such processes are
+found, zypper will list them in a table having the following columns:
+
+* PID\ \ \ \ \ \ ID of the process
+.br
+* PPID\ \ \ \ \ ID of the parent process
+.br
+* UID\ \ \ \ \ \ ID of the user running the process
+.br
+* Login\ \ \ \ login name of the user running the process
+.br
+* Command\ \ command used to execute the process
+.br
+* Service\ \ guessed name of the service. If an init script exists for this
+ \ \ \ \ \ \ \ \ \ \ service, you can do "rcservicename restart" to restart it.
+.br
+* Files\ \ \ \ the list of the deleted files
+
.SH "FILES"
.TP
.B /etc/zypp/zypper.conf, $HOME/.zypper.conf
// --------------------------------------------------------------------------
+unsigned Summary::packagesToUpgrade() const
+{
+ // total packages to remove (packages only - patches, patterns, and products
+ // are virtual; srcpackages do not get removed by zypper)
+ KindToResPairSet::const_iterator it = toupgrade.find(ResKind::package);
+ if (it != toupgrade.end())
+ return it->second.size();
+ return 0;
+}
+
+// --------------------------------------------------------------------------
+
void Summary::writeResolvableList(ostream & out, const ResPairSet & resolvables)
{
// find multi-version packages
void writePackageCounts(std::ostream & out);
void writeDownloadAndInstalledSizeSummary(std::ostream & out);
+
unsigned packagesToGetAndInstall() const
{ return _inst_pkg_total; }
unsigned packagesToRemove() const;
+ unsigned packagesToUpgrade() const;
const zypp::ByteCount & toDownload() const
{ return _todownload; }
const zypp::ByteCount & installedSizeChange() const
#include "zypp/FileChecker.h"
#include "zypp/media/MediaException.h"
+#include "zypp/misc/CheckAccessDeleted.h"
#include "misc.h" // confirm_licenses
#include "utils/misc.h"
#include "utils/prompt.h" // Continue? and solver problem prompt
#include "utils/pager.h" // to view the summary
+#include "Table.h" // for process list in suggest_restart_services
#include "Summary.h"
#include "solve-commit.h"
return policy;
}
+/** fate #300763
+ * This is called after each commit to show running processes that use
+ * libraries or other files that have been removed since their execution.
+ * This is particularly useful after zypper remove or zypper update.
+ */
+static void suggest_restart_services(Zypper & zypper)
+{
+ zypper.out().info(
+ _("Checking for running processes using deleted libraries..."), Out::HIGH);
+ zypp::CheckAccessDeleted checker(false); // wait for explicit call to check()
+ try
+ {
+ checker.check();
+ }
+ catch(const zypp::Exception & e)
+ {
+ if (zypper.out().verbosity() > Out::NORMAL)
+ zypper.out().error(e, _("Check failed:"));
+ }
+
+ Table t;
+ t.allowAbbrev(6);
+ TableHeader th;
+ // process ID
+ th << _("PID");
+ // parent process ID
+ th << _("PPID");
+ // process user ID
+ th << _("UID");
+ // process login name
+ th << _("Login");
+ // process command name
+ th << _("Command");
+ // "/etc/init.d/ script that might be used to restart the command (guessed)
+ th << _("Service");
+ // "list of deleted files or libraries accessed"
+ th << _("Files");
+ t << th;
+
+ for_( it, checker.begin(), checker.end() )
+ {
+ TableRow tr;
+ vector<string>::const_iterator fit = it->files.begin();
+ tr << it->pid << it->ppid << it->puid << it->login << it->command
+ << it->service() << (fit != it->files.end() ? *fit : "");
+ t << tr;
+ for (; fit != it->files.end(); ++fit)
+ {
+ TableRow tr1;
+ tr1 << "" << "" << "" << "" << "" << "" << *fit;
+ t << tr1;
+ }
+ }
+
+ if (t.empty())
+ {
+ zypper.out().info(_("No such processes found."), Out::HIGH);
+ }
+ else
+ {
+ cout << endl;
+ zypper.out().info(_("The following running processes use deleted files:"));
+ cout << endl;
+ cout << t << endl;
+ zypper.out().info(_("You may wish to restart these processes."));
+ zypper.out().info(str::form(
+ _("See '%s' for information about the meaning of values"
+ " in the above table."),
+ "man zypper"));
+ }
+}
+
// ----------------------------------------------------------------------------
// commit
// ----------------------------------------------------------------------------
" needed patches."),
Out::QUIET, Out::TYPE_NORMAL); // don't show this to machines
}
+
+ // check for running services
+ if (summary.packagesToRemove() && summary.packagesToUpgrade())
+ suggest_restart_services(zypper);
}
}
// noting to do