On Thu, Mar 26, 2020 at 1:11 PM Panu Matilainen
<pmatilai(a)laiskiainen.org> wrote:
On 3/26/20 4:08 PM, Zbigniew Jędrzejewski-Szmek wrote:
> On Thu, Mar 26, 2020 at 08:44:47AM -0400, Neal Gompa wrote:
>> On Thu, Mar 26, 2020 at 8:22 AM Zbigniew Jędrzejewski-Szmek
>> <zbyszek(a)in.waw.pl> wrote:
>>>
>>> On Thu, Mar 26, 2020 at 07:38:33AM -0400, Neal Gompa wrote:
>>>> On Thu, Mar 26, 2020 at 7:33 AM Zbigniew Jędrzejewski-Szmek
>>>> <zbyszek(a)in.waw.pl> wrote:
>>>>>
>>>>> - a one-shot service: this is easier to implement, it just needs to
>>>>> happen in one place. The hard part is making sure that the
machine
>>>>> does not get reboot while the upgrade is happening. This is in
>>>>> particular a problem with VMs and containers. The rebuild should
be
>>>>> wrapped with systemd-inhibit and other guards to make it hard to
>>>>> interrupt.
>>>>
>>>> Wouldn't the systemd-inhibit plugin automatically ensure that a
>>>> rebuild action would block sleep/poweroff?
>>>
>>> Unfortunately... not. From the man page: inhibitors "may be used to
>>> block or delay system sleep and shutdown requests from the user, as
>>> well as automatic idle handling of the OS."
>>> Explicit non-interactive privileged requests override inhibitors [1,2].
>>> This has been discussed, and I think there's general sentiment that we
>>> should have an ability to inhibit "everything", but so far nobody
has
>>> pushed for a solution. A solution could be proritized if it turns out
>>> to be required in Fedora.
>>>
>>> [1]
https://github.com/systemd/systemd/issues/2680
>>> [2]
https://github.com/systemd/systemd/issues/6644
>>>
>>
>> I'm not sure it's needed with rpm 4.14+, since worst case is that you
>> have to trigger the rebuild some other time if it's interrupted.
>>
>>>>> No matter how it wrapped, is the upgrade itself atomic? Having the
new
>>>>> db built under a temporary file name and then atomically rename(2)d
>>>>> into place would be ideal.
>>>>>
>>>>
>>>> Since RPM 4.14, RPM creates a new directory, writes the database
>>>> content there, then renames the directory when it's done.
>>>
>>> Does it use renameat2(RENAME_EXCHANGE)?
>>>
>>
>> No, but I don't think that matters with the way it's implemented?
>>
>> See:
https://github.com/rpm-software-management/rpm/commit/fffd652c56eaef8fc41...
>
> I think otherwise it'd be hard to do an atomic replacement when the
> database consists of more than one file. But looking at the code:
>
> xx = rename(dest, old);
> if (xx) {
> goto exit;
> }
> xx = rename(src, dest);
>
> (dest, src, old are all single-file paths)
> if I'm reading this correctly, it doesn't even to atomic replacement
> of individual files. If the machine is rebooted between the two
> renames above, no database ;(
It *used to* replace files one by one before
https://github.com/rpm-software-management/rpm/commit/fffd652c56eaef8fc41...
Now it's just two rename() calls on directories, so it's worlds better
and the best we can do with portable system calls. So yes if you win the
unlucky lottery to have system reboot between those two rename() calls,
you can end up with having to manually rename it into place.
So to put that into perspective, --rebuilddb was *much* worse for over
twenty years and I've never heard anybodys database getting nuked
because of *that*.
>
> On Thu, Mar 26, 2020 at 03:29:50PM +0200, Panu Matilainen wrote:
>> No, rpm doesn't use many Linux-specific calls and this is no
>> exception. In fact it doesn't use any of the *at() family calls
>> directly either.
>
> But why?! It's not like rpm is massive on Windows Server... Isn't
> good support for Linux absolutely the most important thing?
The places where rpm turns up never ceases to astonish me, starting from
OS X to FreeBSD to the old proprietory unixen (AIX was already
mentioned). There's even an actively maintained OS/2 port of rpm.
Seriously. To that, I had to mostly say no.
(And cygwin, but we don't talk about Cygwin...)
--
真実はいつも一つ!/ Always, there's only one truth!