Discussion:
[systemd-devel] Why do passive target units have to exist?
林自均
2017-10-16 15:15:39 UTC
Permalink
Hi folks,

I am reading systemd documents, and I find passive target units a little
bit confusing.

Take "network.target" for example:

"systemd-networkd.service" specifies "Wants=network.target" and
"Before=network.target". That effectively makes starting
"systemd-networkd.service" brings up both "systemd-networkd.service" and
"network.target", and make sure that "network.target" is active after
"systemd-networkd.service" being active. It also implies that the shutdown
order is correct: "network.target" will be stopped before
"systemd-networkd.service". Everything is fine.

What if we use an active target unit to achieve all this? Can we specify a
"WantedBy=network.target" in "systemd-network.target"? So that we can
enable "systemd-network.service" (which makes a symbolic link in the
"network.target.wants" directory) and start "network.target" to pull in
"systemd-networkd.service". That also makes sure "network.target" is active
after "systemd-networkd.service" because of the target unit default
dependencies. And shutdown order will be correct too.

The only difference I can tell is the units to start. With a passive
"network.target", we start "systemd-networkd.service". With an active
"network.target", we start "network.target".

Is there any benefits of passive target units over active target units?

John
Andrei Borzenkov
2017-10-17 16:58:02 UTC
Permalink
Post by 林自均
Hi folks,
I am reading systemd documents, and I find passive target units a little
bit confusing.
"systemd-networkd.service" specifies "Wants=network.target" and
"Before=network.target". That effectively makes starting
"systemd-networkd.service" brings up both "systemd-networkd.service" and
"network.target", and make sure that "network.target" is active after
"systemd-networkd.service" being active. It also implies that the shutdown
order is correct: "network.target" will be stopped before
"systemd-networkd.service". Everything is fine.
What if we use an active target unit to achieve all this? Can we specify a
"WantedBy=network.target" in "systemd-network.target"? So that we can
enable "systemd-network.service" (which makes a symbolic link in the
"network.target.wants" directory) and start "network.target" to pull in
"systemd-networkd.service". That also makes sure "network.target" is active
after "systemd-networkd.service" because of the target unit default
dependencies. And shutdown order will be correct too.
The only difference I can tell is the units to start. With a passive
"network.target", we start "systemd-networkd.service". With an active
"network.target", we start "network.target".
Is there any benefits of passive target units over active target units?
I think it's historical artefact from the very early days when systemd
had to rely on initscripts. initscript implementing networking did
provide $network a.k.a network.target, but of course did not hook itself
into native systemd units. As long as you are sure to use native units
only there is no practical difference.
林自均
2017-10-19 09:46:24 UTC
Permalink
Hi Andrei,

Thank you for your reply!
Just to confirm: there are about 10 passive system targets in
systemd.special(5):

- getty-pre.target
- cryptsetup-pre.target
- local-fs-pre.target
- network.target
- network-pre.target
- nss-lookup.target
- nss-user-lookup.target
- remote-fs-pre.target
- rpcbind.target
- time-sync.target

Are they all related to early days initscripts?

Thanks.

John
Post by 林自均
Post by 林自均
Hi folks,
I am reading systemd documents, and I find passive target units a little
bit confusing.
"systemd-networkd.service" specifies "Wants=network.target" and
"Before=network.target". That effectively makes starting
"systemd-networkd.service" brings up both "systemd-networkd.service" and
"network.target", and make sure that "network.target" is active after
"systemd-networkd.service" being active. It also implies that the
shutdown
Post by 林自均
order is correct: "network.target" will be stopped before
"systemd-networkd.service". Everything is fine.
What if we use an active target unit to achieve all this? Can we specify
a
Post by 林自均
"WantedBy=network.target" in "systemd-network.target"? So that we can
enable "systemd-network.service" (which makes a symbolic link in the
"network.target.wants" directory) and start "network.target" to pull in
"systemd-networkd.service". That also makes sure "network.target" is
active
Post by 林自均
after "systemd-networkd.service" because of the target unit default
dependencies. And shutdown order will be correct too.
The only difference I can tell is the units to start. With a passive
"network.target", we start "systemd-networkd.service". With an active
"network.target", we start "network.target".
Is there any benefits of passive target units over active target units?
I think it's historical artefact from the very early days when systemd
had to rely on initscripts. initscript implementing networking did
provide $network a.k.a network.target, but of course did not hook itself
into native systemd units. As long as you are sure to use native units
only there is no practical difference.
Lennart Poettering
2017-10-24 08:45:58 UTC
Permalink
Post by 林自均
Hi Andrei,
Thank you for your reply!
Just to confirm: there are about 10 passive system targets in
- getty-pre.target
- cryptsetup-pre.target
- local-fs-pre.target
- network.target
- network-pre.target
- nss-lookup.target
- nss-user-lookup.target
- remote-fs-pre.target
- rpcbind.target
- time-sync.target
Are they all related to early days initscripts?
No, they have nothing to do with that really. They are all
synchronization points that we don't want in the boot transaction if
possible, but pull them in if we have to.

Lennart
--
Lennart Poettering, Red Hat
Lennart Poettering
2017-10-24 08:45:00 UTC
Permalink
Post by 林自均
Hi folks,
I am reading systemd documents, and I find passive target units a little
bit confusing.
"systemd-networkd.service" specifies "Wants=network.target" and
"Before=network.target". That effectively makes starting
"systemd-networkd.service" brings up both "systemd-networkd.service" and
"network.target", and make sure that "network.target" is active after
"systemd-networkd.service" being active. It also implies that the shutdown
order is correct: "network.target" will be stopped before
"systemd-networkd.service". Everything is fine.
What if we use an active target unit to achieve all this? Can we specify a
"WantedBy=network.target" in "systemd-network.target"? So that we can
enable "systemd-network.service" (which makes a symbolic link in the
"network.target.wants" directory) and start "network.target" to pull in
"systemd-networkd.service". That also makes sure "network.target" is active
after "systemd-networkd.service" because of the target unit default
dependencies. And shutdown order will be correct too.
The only difference I can tell is the units to start. With a passive
"network.target", we start "systemd-networkd.service". With an active
"network.target", we start "network.target".
Is there any benefits of passive target units over active target units?
We generally try to minimize synchronization points. "network.target"
is one, and we don't want it around if there's no reason to have
it. The more synchronization points you have the more serial your boot
becomes.

The logic hence is: if there's not networking stack then there's no
reason for services to synchronize before or after it, and thus it's
the networking stack that pulls in network.target and not its
consumer, if you so will.

Does that make sense?

Lennart
--
Lennart Poettering, Red Hat
林自均
2017-10-25 04:52:43 UTC
Permalink
Hi Lennart,

Yes, it makes sense to me. Thank you for your explanation.

However, I still have a question about it. If the general goal is to
minimize synchronization points, why don't we convert more active targets
into passive targets? For example: not all machines have swap, so can the
swap.target be a passive target to avoid unnecessary sync point? I guess
there must be a reason not to do so, but I don't know what it is.

John
Post by 林自均
Post by 林自均
Hi folks,
I am reading systemd documents, and I find passive target units a little
bit confusing.
"systemd-networkd.service" specifies "Wants=network.target" and
"Before=network.target". That effectively makes starting
"systemd-networkd.service" brings up both "systemd-networkd.service" and
"network.target", and make sure that "network.target" is active after
"systemd-networkd.service" being active. It also implies that the
shutdown
Post by 林自均
order is correct: "network.target" will be stopped before
"systemd-networkd.service". Everything is fine.
What if we use an active target unit to achieve all this? Can we specify
a
Post by 林自均
"WantedBy=network.target" in "systemd-network.target"? So that we can
enable "systemd-network.service" (which makes a symbolic link in the
"network.target.wants" directory) and start "network.target" to pull in
"systemd-networkd.service". That also makes sure "network.target" is
active
Post by 林自均
after "systemd-networkd.service" because of the target unit default
dependencies. And shutdown order will be correct too.
The only difference I can tell is the units to start. With a passive
"network.target", we start "systemd-networkd.service". With an active
"network.target", we start "network.target".
Is there any benefits of passive target units over active target units?
We generally try to minimize synchronization points. "network.target"
is one, and we don't want it around if there's no reason to have
it. The more synchronization points you have the more serial your boot
becomes.
The logic hence is: if there's not networking stack then there's no
reason for services to synchronize before or after it, and thus it's
the networking stack that pulls in network.target and not its
consumer, if you so will.
Does that make sense?
Lennart
--
Lennart Poettering, Red Hat
Lennart Poettering
2017-10-25 07:18:40 UTC
Permalink
Post by 林自均
Hi Lennart,
Yes, it makes sense to me. Thank you for your explanation.
However, I still have a question about it. If the general goal is to
minimize synchronization points, why don't we convert more active targets
into passive targets? For example: not all machines have swap, so can the
swap.target be a passive target to avoid unnecessary sync point? I guess
there must be a reason not to do so, but I don't know what it is.
Well, targets are not just sync points, they are also ways how to
group things. swap.target is a way to pull in all swap devices,
local-fs.target a way to pull in all local file systems and so on.

Lennart
--
Lennart Poettering, Red Hat
Loading...