source: https://wiki.nftables.org/wiki-nftables/index.php/Ruleset_debug/tracing
이전 글: Scripting
다음 글: Output text modifier
debug/tracing은 nftabels 0.6, linux kernel 4.6 부터 지원합니다. 최근에 설치한 Ubuntu 18.04에 설치한 nftables과 kernel version은 아래와 같습니다.
- nftables: 0.8.2-1
- Linux: 5.4.0-80
iptables에서 -j TRACE와 같은 것이며, 더 향상된 기능이 있습니다.
패켓에 대한 tracing을 하려면, 절차는 trace 목적의 chain을 만들어 hook 에 base chain으로 등록한 후, 해당 chain에서 nftrace를 활성화하는 룰을 설정하고, 마지막으로 tracing event를 지켜보면 됩니다.
- add chain to a hook
- enable nftrace
- monitor trace
nftrace 활성화 방법
아래와 같이 rule을 추가하면 됩니다. 이렇게 하면 해당 chain을 지나는 모든 패켓에 대해 tracing을 하는 것입니다.
meta nftrace set 1
만약 IP/TCP 패켓만 tracing 하려면 활성화 rule을 ip protocol tcp에 대해서만 적용합니다.
ip protocol tcp meta nftrace set 1
실제 서비스에 적용된 상태에서는 범위를 좁혀 tracing하는 것을 추천합니다.
Hook에 chain 추가
chain을 추가하기 위해서는 table을 먼저 생성해야 합니다. 그리고 나서 hook을 정하여 chain을 생성합니다. 그리고 나서 nftrace를 활성화하는 rule을 선언합니다.
# nftrace table ip filter 생성
salsal@r3:~$ sudo nft add table ip filter
# chain trace_chain을 type filter로 설정하고 hook prerouting에 추가
salsal@r3:~$ sudo nft add chain filter trace_chain '{ type filter hook prerouting priority -301; }'
chain에 룰 추가
# trace_chain을 지나는 전체 패켓에 대해 nftrace 활성화
salsal@r3:~$ sudo nft add rule filter trace_chain meta nftrace set 1
salsal@r3:~$ sudo nft list ruleset
table ip filter {
chain trace_chain {
type filter hook prerouting priority -301; policy accept;
nftrace set 1
}
}
salsal@r3:~$
trace 지켜보기
salsal@r3:~$ sudo nft monitor trace
trace id 4704db2b ip filter trace_chain packet: iif "enp0s3" ether saddr 52:54:00:12:35:02 ether daddr 08:00:27:57:d9:98 ip saddr 35.224.170.84 ip daddr 10.0.2.15 ip dscp cs0 ip ecn not-ect ip ttl 64 ip id 13397 ip length 44 tcp sport http tcp dport 36446 tcp flags == 0x12 tcp window 65535
trace id 4704db2b ip filter trace_chain rule nftrace set 1 (verdict continue)
trace id 4704db2b ip filter trace_chain verdict continue
예제
다음과 같은 ruleset을 ruleset.nft 에 저장합니다.
flush ruleset
table ip filter {
chain input {
type filter hook input priority 0; policy drop;
ct state established,related counter packets 153677 bytes 6163412 accept
ct state new tcp dport ssh counter packets 0 bytes 0 accept
}
}
ruleset을 로드합니다.
salsal@r3:~$ sudo nft -f nftables.nft
salsal@r3:~$ sudo nft list ruleset
flush ruleset
table ip filter {
chain input {
type filter hook input priority 0; policy drop;
ct state established,related counter packets 153677 bytes 6163412 accept
ct state new tcp dport ssh counter packets 0 bytes 0 accept
}
}
hook prerouting에 priority가 더 높은 (숫자는 작은) trace_chain을 추가합니다.
salsal@r3:~$ sudo nft add chain ip filter trace_chain '{ type filter hook prerouting priority -1; }'
salsal@r3:~$ sudo nft add rule ip filter trace_chain icmp type {echo-request, echo-reply} nftrace set 1
salsal@r3:~$ sudo nft list ruleset
table ip filter {
chain input {
type filter hook input priority 0; policy drop;
ct state established,related counter packets 237 bytes 13760 accept
ct state new tcp dport ssh counter packets 0 bytes 0 accept
}
chain trace_chain {
type filter hook prerouting priority -1; policy accept;
icmp type {echo-request, echo-reply} nftrace set 1
}
}
시스템 r3에서 nftrace를 활성화합니다.
salsal@r3:~$ sudo nft monitor trace
시스템 r3와 연결되어 있는 시스템 r2에서 r3로 향하는 icmp packet을 발송합니다.
salsal@r2:~$ ping -c 2 -W 1 192.168.23.3
PING 192.168.23.3 (192.168.23.3) 56(84) bytes of data.
--- 192.168.23.3 ping statistics ---
2 packets transmitted, 0 received, 100% packet loss, time 1004ms
그 때 시스템 r3의 nftrace 결과를 살펴봅니다.
salsal@r3:~$ sudo nft monitor trace
trace id e10637fc ip filter trace_chain packet: iif "enp0s10" ether saddr 08:00:27:6a:e2:a9 ether daddr 08:00:27:f2:19:0d ip saddr 192.168.23.2 ip daddr 192.168.23.3 ip dscp cs0 ip ecn not-ect ip ttl 64 ip id 12173 ip length 84 icmp type echo-request icmp code 0 icmp id 3703 icmp sequence 1
trace id e10637fc ip filter trace_chain rule icmp type { } nftrace set 1 (verdict continue)
trace id e10637fc ip filter trace_chain verdict continue
trace id e10637fc ip filter trace_chain
trace id e10637fc ip filter input verdict continue
trace id e10637fc ip filter input
trace id d864f713 ip filter trace_chain packet: iif "enp0s10" ether saddr 08:00:27:6a:e2:a9 ether daddr 08:00:27:f2:19:0d ip saddr 192.168.23.2 ip daddr 192.168.23.3 ip dscp cs0 ip ecn not-ect ip ttl 64 ip id 12216 ip length 84 icmp type echo-request icmp code 0 icmp id 3703 icmp sequence 2
trace id d864f713 ip filter trace_chain rule icmp type { } nftrace set 1 (verdict continue)
trace id d864f713 ip filter trace_chain verdict continue
trace id d864f713 ip filter trace_chain
trace id d864f713 ip filter input verdict continue
trace id d864f713 ip filter input
위 내용을 살펴보면
trace id e10637fc ip filter trace_chain packet: iif "enp0s10" ....
- r3의 adapter enp0s10 로 들어온 시스템은 trace_chain을 통과합니다.
trace id e10637fc ip filter trace_chain rule icmp type { } nftrace set 1 (verdict continue)
- 처음 만난 rule icmp type을 통과하며 default policy가 accpet 이므로 통과합니다. (ip filter trace_chain verdict continue)
trace id e10637fc ip filter input verdict continue
- chain trace_chain을 통과하여 chain input을 지납니다.
chain input에서는 nftrace가 활성화되어 있지 않아 상세 내역을 출력하지 않는 듯 합니다.
이전 글: Scripting
다음 글: Output text modifier
'nftables' 카테고리의 다른 글
nftables examples (0) | 2021.08.06 |
---|---|
Output text modifier (0) | 2021.08.06 |
Scripting (0) | 2021.08.06 |
룰셋 갱신 지켜보기 / Monitoring ruleset updates (0) | 2021.08.06 |
룰셋 레벨 명령 / Operations at ruleset level (0) | 2021.08.06 |