On 05/14/14 at 11:29am, Vivek Goyal wrote:
On Wed, May 14, 2014 at 03:22:40PM +0800, WANG Chao wrote:
[..]
> > Second quesiton, So looks like there are two error paths. If error
> > happens early enough, then dracut can drop us into emergency shell
> > otherwise later systemd can put us into emergency shell. It depends
> > when error happened.
>
> After a search in 2nd kernel, I find out there are two cases that will
> call dracut-emergency.service:
>
> a.) rd.break= is specified in cmdline. dracut script will eventually
> call dracut-emergency.service
>
> b.) In rescue mode, rescue.service will trigger dracut-emergency. But
> this is not our case, because we are not in rescue mode.
>
> So to me if we don't specify "rd.break=", we won't trigger
> dracut-emergency. Given the fact that we already disabled
> dracut-emergency.service, we don't need to worry about it.
>
> I don't understand why early error is handled by
> dracut-emergency.service and late is handled by systemd's
> emergency.service. Where do you get that?
I think I got it wrong. So looks like know systemd will get control
from the beginning. (init is pointing to systemd binary). And all
the dracut functionality has been converted into dracut services.
That means, if some dracut functionality fails, it will be handled
like any other sytemd service failure.
So you are right, looks like dracut will drop to a shell only if user
asked for it. Otherwise if some error happens, respective dracut service
might just fail.
Hence systemd will take care of all dracut serivices, ordering between
them and when services fail, how other serivces are started. Now it is
systemd's responsibility to figure out when is it safe to continue with
boot in case of error and when is it time to say boot can't continue and
drop into emergency shell.
>
> >
> > If error happened in dracut early, then tyring to kick dracut initqueue
> > again will most likely not help much. If error happens later in systemd
> > when it is trying to mount non-root file systems, then kicking
> > dracut-initqueue and enabling sysroot.mount might help.
> >
> > BTW, I still don't understand that why should we try to enable
> > dracut-initqueue explicitly. If sysroot.mount depends on it, then it
> > will automatically be enabled.
>
> sysroot.mount doesn't depends on it but it depends on the device (or the
> filesystem) is available. dracut-initqueue mainly does the job to bring
> up the devices we need.
>
> Say we have a lvm rootfs, udev and its rules only get us the disk
> partitions, like /dev/sda1. But the lvm under /dev/mapper/ won't be
> available, we need to bring it up by command like "vgchange -ay".
That's
> the job done by dracut-initqueue.
Ok, got it. my sysroot.mount looks as follows.
# Automatically generated by systemd-fstab-generator
[Unit]
SourcePath=/proc/cmdline
Before=initrd-root-fs.target
[Mount]
What=/dev/mapper/fedora-root
Where=/sysroot
Type=auto
FsckPassNo=0
Options=ro,ro
So We will wait for /dev/mapper/fedora-root to show up.
>
> >
> > Secondly, if error happened before dracut-initqueue, then there is
> > no point in running initqueue scripts. If error happend after dracut
> > initqueue, then none of the initqueue action will be undone and there
> > is no need to run dracut-initqueue.
>
> We need dracut-initqueue to run its scripts because we need to bring up
> lvm devices. But you're right we don't need to run it again if error
> happens after dracut-initqueue. But currently I'm not sure how we can
> determine if dracut-initqueue is in the state of "yet to be started" or
> "started but stopped again". That's why I start it unconditionally to
> accommodate.
IIUC, if for whatever reason some dracut service fails, systemd will
continue to boot and if need be fail much later and put user into
emergecny shell.
That means if we fall into kdump emergency handler, we have already
tried to run dracut-initqueue already. And either it succeeded or it
failed.
No, this is not right. Error could happen at any point of the boot
process. We can't guarantee dracut-initqueue is already started when
drop into kdump error handler.
IOW, if error happens before dracut-initqueue, we fall into kdump error
handler and initqueue hook scripts never get run. In this case, only
starting sysroot.mount doesn't make sense, because sysroot.mount may
depends on initqueue to bring up the lvm device.
And also there's a chance that some error happens while dracut-initqueue
is running. And we isolate to kdump error handler and dracut-initqueue
service is stopped even it's still running last second.
So the reason to start dracut-initqueue.service before sysroot.mount is,
we don't know if dracut-initqueue gets run or not and all we can do is
to run it again to make sure every script under initqueue hook is run at
least one time.
That means we only need to start sysroot.mount and nothing else. If
it succeeds we dump to rootfs or reboot.
>
> >
> > So I think we just need to explicitly enable sysroot.mount from kdump
> > handler. If it blocks for 90 seconds, we don't have to do anything. But
> > if it exits immediately, then we need to sit in a tight loop and wait
> > for 90 seconds. If root shows up, dump to it otherwise reboot.
>
> Let me clarify things here, we got two ways here:
>
> a.) "systemctl start sysroot.mount"
>
> This will wait the operation until it's finished, aka blocking.
> If the operation isn't finished in 90 seconds, this will return with a
> error code.
>
> b.) "systemctl --no-block sysroot.mount"
>
> This will not wait the operation to finish. But we will poll for root
> fs for 90 seconds.
>
> Currently I'm choosing a.) because simple and we don't need to worry
> about future change for timeout value. What do you think?
Got it. So systemctl by default is *blocking* command and will wait
for sysroot.mount to finish.
So it makes sense to use blocking mode and once it times out, we will
try to dump to root otherwise reboot.
I copied sysroot.mount to vivek.mount. I changed vivek.mount to try
to mount a non-existent device.
# Automatically generated by systemd-fstab-generator
[Unit]
SourcePath=/proc/cmdline
Before=initrd-root-fs.target
[Mount]
What=/dev/mapper/fedora-root-bad
Where=/vivek
Type=auto
FsckPassNo=0
Options=ro,ro
#systemct start vivek.mount
Sure systemctl command blocked and exited after some time with error
message.
I have got only one issue. systemctl does not give any message before
wait starts. So please put a message in kdump which tells user clearly
that we are waiting for root to mount and will timeout after some time.
That way user will not think that kdump is hung.
Make sense. Will do that.
In summary, it looks like we need to start only sysroot.mount and not
dracut-initqueue. And we should be good.
Explained above. We need to run dracut-initqueue to make sure it's at
least got run once.
Thanks
WANG Chao