On Wed, Jul 21, 2010 at 01:52:50PM -0700, Russ Allbery wrote: > diff --git a/policy.sgml b/policy.sgml > index 847f716..eb458fe 100644 > --- a/policy.sgml > +++ b/policy.sgml > @@ -1079,10 +1079,10 @@ > </p> > > <p> > - Sometimes, a package requires another package to be installed > - <em>and</em> configured before it can be installed. In this > - case, you must specify a <tt>Pre-Depends</tt> entry for > - the package. > + Sometimes, a package requires another package to be unpacked > + <em>and</em> configured before it can be unpacked. In this > + case, the dependent package must specify this dependency in > + the <tt>Pre-Depends</tt> control field. > </p> > > <p>
I think "depending package" is clearer than "dependent package", since there's less possibility of confusion with "dependency". (The usage "dependent package" does not currently exist elsewhere in Policy.) > + The package will not yet be unpacked, so > + the <prgn>preinst</prgn> script cannot rely on any files > + included in its package. Only essential packages and > + pre-dependencies (<tt>Pre-Depends</tt>) may be assumed to be > + available. Pre-dependencies will be at least unpacked. > + They may be only unpacked or "Half-Configured", not > + completely configured, but only if a previous version of the > + pre-dependency was completely configured and the > + pre-dependency had not been removed since then. > </item> Maybe it would be clearer to write it this way? Pre-dependencies will have been configured at least once, but at the time the preinst is called they may only be in an unpacked or "Half-Configured" state if a previous version of the pre-dependency was completely configured and has not been removed (uninstalled?) since then. Does dpkg provide any guarantee that the dependencies of the pre-dependency are also present at this point? If it doesn't, I think that should be considered a bug in dpkg, since you may be invoking a command that links against a library whose soname has changed since the last time the pre-dep package was configured. If it /does/ provide this guarantee, I think it should be documented in Policy. > + The <prgn>postinst</prgn> script may be called in the following > + ways: > + <taglist> > + <tag><var>postinst</var> <tt>configure</tt> > + <var>most-recently-configured-version</var></tag> > <item> > - <var>conflictor's-prerm</var> <tt>remove</tt> > - <tt>in-favour</tt> <var>package</var> > - <var>new-version</var> > + The files contained in the package will be unpacked. All > + package dependencies will at least be unpacked. If there > + are no circular dependencies involved, all package > + dependencies will be configured. > </item> Should this include a pointer to the section documenting the rules for breaking circular dependencies? > + unpacked in some error situations.<footnote> > + For example, suppose packages foo and bar are installed > + with foo depending on bar. If an upgrade of bar were > + started and then aborted, and then an attempt to remove > + foo failed because its <prgn>prerm</prgn> script failed, > + foo's <tt>postinst abort-remove</tt> would be called with > + bar only "Half-Installed". > + </footnote> > </item> > - </list> > + </taglist> > + </p> This footnote is interesting to me because although it accurately documents dpkg's behavior, I'm not sure what implications it has for how packages should guard against this case. I think I've always ignored this possibility in my maintainer scripts, and will continue to do so on the grounds that any attempt to handle this gracefully is likely to introduce much greater complexity (and therefore bugs) with very little upside (when all is said and done, a package you were trying to remove is still installed, so do we care if it configures successfully?) If we can make a straightforward recommendation to maintainers for how to handle this case, I think we should include that in the footnote. Otherwise, if it shouldn't affect how we write maintainer scripts, perhaps it's better not to have this footnote at all since it would only lead to maintainers trying to be too clever and shooting themselves in the foot? > + <p> > + The <prgn>postrm</prgn> script may be called in the following > + ways: > + <taglist> > + <tag><var>postrm</var> <tt>remove</tt></tag> > + <tag><var>postrm</var> <tt>purge</tt></tag> > + <tag><var>old-postrm</var> <tt>upgrade</tt> > + <var>new-version</var></tag> > + <tag><var>disappearer's-postrm</var> <tt>disappear</tt> > + <var>overwriter</var> <var>overwriter-version</var></tag> > <item> > - <var>new-postrm</var> <tt>abort-install</tt> > - <var>old-version</var> > + The <prgn>postrm</prgn> script is called after the package's > + files have been removed or replaced. The package > + whose <prgn>postrm</prgn> is being called may have > + previously been deconfigured and only be unpacked, at which > + point subsequent package changes do not consider its > + dependencies. Therefore, all <prgn>postrm</prgn> actions > + may only rely on essential packages and cannot assume that > + the package's dependencies are available. > </item> True as written, but less helpful than it should be. There are a number of cases where postrm scripts still need to *try* to invoke non-essential functionality, and fail gracefully if it's unavailable; this should be explicitly encouraged so that maintainers don't come away thinking they shouldn't try to clean up after themselves. Ex.: if you have a package that manages a config file with ucf, you *must* call ucf --purge from "postrm purge" if ucf is present on the system at this point; failure to do so will give completely unintuitive handling of the config file on package purge && reinstall. Proposed wording (improvements requested): Therefore, all <prgn>postrm</prgn> actions may only rely on essential packages and must gracefully omit anything requiring the package's dependencies when those dependencies are unavailable. > - The <tt>Depends</tt> field thus allows package maintainers > - to impose an order in which packages should be configured. > + If there is a circular dependency among packages being installed > + or removed, installation or removal order honoring the > + dependency order is impossible, requiring the dependency loop be > + broken at some point and the dependency requirements violated > + for at least one package. Packages involved in circular > + dependencies may not be able to rely on their dependencies being > + configured when being configured depending on which side of the > + break of the circular dependency loop they happen to be on. If > + one of the packages in the loop has no <prgn>postinst</prgn> > + script, then the cycle will be broken at that package; this > + ensures that all <prgn>postinst</prgn> scripts are run with > + their dependencies properly configured if this is possible. > + Otherwise the breaking point is arbitrary. Packages should > + therefore avoid circular dependencies where possible, > + particularly if they have <prgn>postinst</prgn> scripts. > </p> > > <p> --> Packages involved in circular dependencies may not be able to rely on their dependencies being configured before they themselves are configured, depending on which side of the break of the circular dependency loop they happen to be on. > @@ -4588,12 +4651,17 @@ Build-Depends: foo [linux-any], bar [any-i386], baz > [!linux-any] > > <p> > The <tt>Depends</tt> field should also be used if the > - <prgn>postinst</prgn>, <prgn>prerm</prgn> or > - <prgn>postrm</prgn> scripts require the package to be > - present in order to run. Note, however, that the > - <prgn>postrm</prgn> cannot rely on any non-essential > - packages to be present during the <tt>purge</tt> > - phase. > + <prgn>postinst</prgn> or <prgn>prerm</prgn> scripts > + require the depended-on package to be unpacked or > + configured in order to run. In the case of <tt>postinst > + configure</tt>, the depended-on packages will be unpacked > + and configured first. (If both packages are involved in a > + dependency loop, this might not work as expected; see the > + explanation a few paragraphs back.) In the case > + of <prgn>prerm</prgn> or other <prgn>postinst</prgn> > + actions, the package dependencies will be at least > + unpacked or "Half-Installed". > + </p> > </item> I disagree with this change. If you are making use of non-essential packages in your postrm, you *should* use the Depends: field; you just *also* have to have a clean fallback plan if the dependency is not satisfied when the postrm is called. The normal use case is "whichever of the two packages is removed first must clean up". While I can't think of a case where the cleanup interface called from the postrm isn't already a dependency for other reasons (e.g., for use in the postinst), I'd like this to be explicit all the same. The rest looks good to me. Thanks, -- Steve Langasek Give me a lever long enough and a Free OS Debian Developer to set it on, and I can move the world. Ubuntu Developer http://www.debian.org/ slanga...@ubuntu.com vor...@debian.org
signature.asc
Description: Digital signature