Package: python3-scapy
Version: 2.4.4-4
Tags: patch

When conf.use_pcap is set, the function sr() does not select proper
outgoing interfaces, so it gets zero answers.

In the following example, the proper interface for the network
192.168.168.0/24 is veth0. However, sr() sends ICMP packets to the
default inteface 'ens3' when conf.use_pcap is set:


-----BEGIN CLI-----
>>> conf.route
Network        Netmask        Gateway   Iface  Output IP      Metric
0.0.0.0        0.0.0.0        10.0.2.2  ens3   10.0.2.15      0
10.0.2.0       255.255.255.0  0.0.0.0   ens3   10.0.2.15      0
127.0.0.0      255.0.0.0      0.0.0.0   lo     127.0.0.1      1
192.168.168.0  255.255.255.0  0.0.0.0   veth0  192.168.168.1  0

>>> conf.iface
'ens3'

>>> conf.use_pcap
True

>>>  sr(IP(dst='192.168.168.2')/ICMP(seq=(1,1000)), timeout=1)
Begin emission:
Finished sending 1000 packets.
.......................................................................
.......................................................................
......................................................
Received 196 packets, got 0 answers, remaining 1000 packets
(<Results: TCP:0 UDP:0 ICMP:0 Other:0>,
 <Unanswered: TCP:0 UDP:0 ICMP:1000 Other:0>)



# tcpdump -ni ens3 -c10 icmp
tcpdump: verbose output suppressed, use -v[v]... for full protocol
decode
listening on ens3, link-type EN10MB (Ethernet), snapshot length 262144
bytes
22:22:28.165580 IP 192.168.168.1 > 192.168.168.2: ICMP echo request, id
0, seq 1, length 8
22:22:28.167091 IP 192.168.168.1 > 192.168.168.2: ICMP echo request, id
0, seq 2, length 8
22:22:28.168075 IP 192.168.168.1 > 192.168.168.2: ICMP echo request, id
0, seq 3, length 8
22:22:28.169068 IP 192.168.168.1 > 192.168.168.2: ICMP echo request, id
0, seq 4, length 8
22:22:28.169988 IP 192.168.168.1 > 192.168.168.2: ICMP echo request, id
0, seq 5, length 8
22:22:28.170900 IP 192.168.168.1 > 192.168.168.2: ICMP echo request, id
0, seq 6, length 8
22:22:28.171933 IP 192.168.168.1 > 192.168.168.2: ICMP echo request, id
0, seq 7, length 8
22:22:28.172917 IP 192.168.168.1 > 192.168.168.2: ICMP echo request, id
0, seq 8, length 8
22:22:28.174020 IP 192.168.168.1 > 192.168.168.2: ICMP echo request, id
0, seq 9, length 8
22:22:28.174913 IP 192.168.168.1 > 192.168.168.2: ICMP echo request, id
0, seq 10, length 8
10 packets captured
94 packets received by filter
0 packets dropped by kernel
-----END CLI-----



The problem gets resolved when the proper 'iface' is set globally or
supplied to the sr() function:

-----BEGIN CLI-----
>>> conf.iface
'ens3'

>>>  sr(IP(dst='192.168.168.2')/ICMP(seq=(1,1000)), timeout=1,
iface='veth0')
Begin emission:
Finished sending 1000 packets.
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
******
Received 1000 packets, got 1000 answers, remaining 0 packets
(<Results: TCP:0 UDP:0 ICMP:1000 Other:0>,
 <Unanswered: TCP:0 UDP:0 ICMP:0 Other:0>)


>>> conf.iface = 'veth0'
>>> conf.iface
'veth0'


>>>  sr(IP(dst='192.168.168.2')/ICMP(seq=(1,1000)), timeout=1)
Begin emission:
Finished sending 1000 packets.
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
******
Received 1000 packets, got 1000 answers, remaining 0 packets
(<Results: TCP:0 UDP:0 ICMP:1000 Other:0>,
 <Unanswered: TCP:0 UDP:0 ICMP:0 Other:0>)
-----END CLI-----


The problem was fixed in the upstream by calling the missing function
_interface_selection() as part of general sr1() cleanup [1] for the
reported issue 3583 [2].


Considering that the upstream commit
50e867aa9ee9061e79890e5f535eb5ccb6e2a7f3 does a bit more than just
fixing the sr() function, probably just adding the missing function in
sr() might be the safest way to backport the fix to 2.4.4.

I have attached a debdiff patch that basically adds the missing
function without refactoring the related sr1() function.

Below is the result of using the updated package:

-----BEGIN CLI----
# dpkg -s python3-scapy | grep Ver
Version: 2.4.4-5

>>> conf.use_pcap
True

>>> conf.iface
'ens3'

>>> sr(IP(dst='192.168.168.2')/ICMP(seq=(1,1000)), timeout=1)
Begin emission:
Finished sending 1000 packets.
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
***********************************************************************
******
Received 1000 packets, got 1000 answers, remaining 0 packets
(<Results: TCP:0 UDP:0 ICMP:1000 Other:0>,
 <Unanswered: TCP:0 UDP:0 ICMP:0 Other:0>)
-----END CLI----


To replicate the network configuration I used for the test, the
following commands can be used:

-----BEGIN CLI----
ip net add scapy
ip link add type veth
ip link set veth1 netns scapy
ip link set veth0 up
ip addr add 192.168.168.1/24 dev veth0

ip netns exec scapy ip link set lo up
ip netns exec scapy ip link set veth1 up
ip netns exec scapy ip addr add 192.168.168.2/24 dev veth1
-----END CLI----


Please note that the requirement to set 'conf.use_pcap' is necessary in
my environment to overcome the recently found issue [3] with the native
super sockets.

Thank you.

Regards,
Garri

[1] https://github.com/secdev/scapy/pull/3610
[2] https://github.com/secdev/scapy/issues/3583
[3] https://github.com/secdev/scapy/issues/4531
diff -Nru scapy-2.4.4/debian/changelog scapy-2.4.4/debian/changelog
--- scapy-2.4.4/debian/changelog	2021-01-11 10:40:10.000000000 +0000
+++ scapy-2.4.4/debian/changelog	2024-09-15 21:51:12.000000000 +0000
@@ -1,3 +1,11 @@
+scapy (2.4.4-5) unstable; urgency=medium
+
+  * Non-maintainer upload.
+
+  * Add a patch to fix interface selection in sr()
+
+ -- Garri Djavadyan <g.djavad...@gmail.com>  Sun, 15 Sep 2024 21:51:12 +0000
+
 scapy (2.4.4-4) unstable; urgency=medium
 
   * Team upload.
diff -Nru scapy-2.4.4/debian/patches/fix-select-iface-in-sr.patch scapy-2.4.4/debian/patches/fix-select-iface-in-sr.patch
--- scapy-2.4.4/debian/patches/fix-select-iface-in-sr.patch	1970-01-01 00:00:00.000000000 +0000
+++ scapy-2.4.4/debian/patches/fix-select-iface-in-sr.patch	2024-09-15 21:50:07.000000000 +0000
@@ -0,0 +1,12 @@
+Index: scapy-2.4.4/scapy/sendrecv.py
+===================================================================
+--- scapy-2.4.4.orig/scapy/sendrecv.py	2020-09-02 11:26:21.000000000 +0000
++++ scapy-2.4.4/scapy/sendrecv.py	2024-09-15 21:50:01.563810502 +0000
+@@ -505,6 +505,7 @@
+     """
+     Send and receive packets at layer 3
+     """
++    iface = _interface_selection(iface, x)
+     s = conf.L3socket(promisc=promisc, filter=filter,
+                       iface=iface, nofilter=nofilter)
+     result = sndrcv(s, x, *args, **kargs)
diff -Nru scapy-2.4.4/debian/patches/series scapy-2.4.4/debian/patches/series
--- scapy-2.4.4/debian/patches/series	2021-01-11 10:40:10.000000000 +0000
+++ scapy-2.4.4/debian/patches/series	2024-09-15 21:49:37.000000000 +0000
@@ -5,3 +5,4 @@
 add-support-for-python3.9.patch
 Fix-find-library-libc-for-python-3.9.patch
 upstream-42d58d8729.patch
+fix-select-iface-in-sr.patch

Reply via email to