dns-delegates: add support for setting a firewall mark
This makes it possible to have DNS requests for certain domains routed differently than normal requests, which is for instance useful when using policy routing to route traffic over a VPN but DNS requests for the VPN endpoint itself, should be routed differently. It doesn't make much sense to configure a firewall mark at the level of a network interface, but at the level of a DNS delegate it can be very useful.
This commit is contained in:
committed by
Lennart Poettering
parent
a5ceab95ab
commit
e271497d97
@@ -69,6 +69,18 @@
|
||||
<xi:include href="version-info.xml" xpointer="v258"/>
|
||||
</listitem>
|
||||
</varlistentry>
|
||||
<varlistentry>
|
||||
<term><varname>FirewallMark=</varname></term>
|
||||
<listitem>
|
||||
<para>Takes a 32 bit unsigned integer value. Controls the firewall mark of packets generated by the
|
||||
socket used to make DNS requests for this DNS delegate. This can be used in the firewall logic to
|
||||
filter packets from this socket.
|
||||
This sets the <constant>SO_MARK</constant> socket option. See <citerefentry
|
||||
project='die-net'><refentrytitle>iptables</refentrytitle><manvolnum>8</manvolnum></citerefentry> for
|
||||
details.</para>
|
||||
<xi:include href="version-info.xml" xpointer="v260"/>
|
||||
</listitem>
|
||||
</varlistentry>
|
||||
</variablelist>
|
||||
|
||||
</refsect1>
|
||||
@@ -79,10 +91,11 @@
|
||||
<programlisting># /etc/systemd/dns-delegate.d/foobar.dns-delegate
|
||||
[Delegate]
|
||||
DNS=203.0.113.47
|
||||
Domains=foobar.com</programlisting>
|
||||
Domains=foobar.com
|
||||
FirewallMark=42</programlisting>
|
||||
|
||||
<para>This ensures lookups of <literal>foobar.com</literal> and any domains below it are directed to
|
||||
DNS server 203.0.113.47.</para>
|
||||
DNS server 203.0.113.47 and any packets related to this lookup have a firewall mark set to 42.</para>
|
||||
</example>
|
||||
</refsect1>
|
||||
|
||||
|
||||
@@ -21,3 +21,4 @@ struct ConfigPerfItem;
|
||||
Delegate.DNS, config_parse_delegate_dns_servers, 0, 0
|
||||
Delegate.Domains, config_parse_delegate_domains, 0, 0
|
||||
Delegate.DefaultRoute, config_parse_tristate, 0, offsetof(DnsDelegate, default_route)
|
||||
Delegate.FirewallMark, config_parse_unsigned, 0, offsetof(DnsDelegate, fwmark)
|
||||
|
||||
@@ -23,6 +23,8 @@ typedef struct DnsDelegate {
|
||||
|
||||
int default_route;
|
||||
|
||||
uint32_t fwmark;
|
||||
|
||||
DnsScope *scope;
|
||||
|
||||
LIST_FIELDS(DnsDelegate, delegates);
|
||||
|
||||
@@ -475,6 +475,12 @@ static int dns_scope_socket(
|
||||
return r;
|
||||
}
|
||||
|
||||
if (s->delegate && s->delegate->fwmark > 0) {
|
||||
r = setsockopt_int(fd, SOL_SOCKET, SO_MARK, s->delegate->fwmark);
|
||||
if (r < 0)
|
||||
return log_debug_errno(r, "Failed to set firewall mark on DNS socket: %m)");
|
||||
}
|
||||
|
||||
bool addr_is_nonlocal = s->link &&
|
||||
!manager_find_link_address(s->manager, sa.sa.sa_family, sockaddr_in_addr(&sa.sa)) &&
|
||||
in_addr_is_localhost(sa.sa.sa_family, sockaddr_in_addr(&sa.sa)) == 0;
|
||||
|
||||
@@ -1452,6 +1452,7 @@ testcase_delegate() {
|
||||
[Delegate]
|
||||
DNS=192.168.77.78
|
||||
Domains=exercise.test
|
||||
FirewallMark=42
|
||||
EOF
|
||||
systemctl reload systemd-resolved
|
||||
resolvectl status
|
||||
|
||||
Reference in New Issue
Block a user