FortiGate
FortiGate Next Generation Firewall utilizes purpose-built security processors and threat intelligence security services from FortiGuard labs to deliver top-rated protection and high performance, including encrypted traffic.
nvisentin_FTNT
Article Id 190623
Description
This article explains why multicast traffic over redundant interface ends up with duplicate packets on the receiver.

Solution
In the following diagram, the receiver retrieves multicast stream from the sender on multicast address 239.1.1.1.

agodwin_FD39706_tn_FD39706-1.jpg

Unicast routing can be either static or dynamic.

Multicast routing uses PIM sparse mode, FGT2 port9 is the RP.

PIM neighbor is running over redundant interface:
FGT1 # get router info multicast pim sparse-mode neighbour
Neighbor          Interface          Uptime/Expires    Ver   DR
Address                                                      Priority/Mode
192.168.1.19      port33,39          17:14:11/00:01:30 v2    1 / DR

FGT2 # get router info multicast pim sparse-mode neighbour
Neighbor          Interface          Uptime/Expires    Ver   DR
Address                                                      Priority/Mode
192.168.1.18      port1,2            17:15:05/00:01:39 v2    1 /
Multicast routing is working properly:
FGT1 # get router info multicast pim sparse-mode table 239.1.1.1 
IP Multicast Routing Table

(*,*,RP) Entries: 0
(*,G) Entries: 1
(S,G) Entries: 2
(S,G,rpt) Entries: 1
FCR Entries: 0

(10.1.1.2, 239.1.1.1)
RPF nbr: 0.0.0.0
RPF idx: None
SPT bit: 1
Upstream State: JOINED
 Local:
 Joined:
     port33,39
 Asserted:
     port33,39: winner
 Outgoing:
     port33,39

(10.1.1.2, 239.1.1.1, rpt)
RP: 0.0.0.0
RPF nbr: 192.168.1.19
RPF idx: port33,39
Upstream State: RPT NOT JOINED
 Local:
 Pruned:
 Outgoing:


FGT2 # get router info multicast pim sparse-mode table 239.1.1.1

IP Multicast Routing Table

(*,*,RP) Entries: 0
(*,G) Entries: 4
(S,G) Entries: 2
(S,G,rpt) Entries: 2
FCR Entries: 0

(*, 239.1.1.1)
RP: 10.2.2.1
RPF nbr: 0.0.0.0
RPF idx: None
Upstream State: JOINED
 Local:
     port9
 Joined:
 Asserted:
FCR:

(10.1.1.2, 239.1.1.1)
RPF nbr: 192.168.1.18
RPF idx: port1,2
SPT bit: 1
Upstream State: JOINED
 Local:
 Joined:
 Asserted:
     port1,2: loser
 Outgoing:
     port9

(10.1.1.2, 239.1.1.1, rpt)
RP: 10.2.2.1
RPF nbr: 0.0.0.0
RPF idx: None
Upstream State: PRUNED
 Local:
 Pruned:
 Outgoing:
     port9


On the receiver, there are 2 copies of the same multicast packet:
agodwin_FD39706_tn_FD39706-2.jpg

Looking at a sniffer trace:
FGT1 # diag sniffer packet any 'host 239.1.1.1' 4 0
7.936514 port17 in 10.1.1.2 -> 239.1.1.1: icmp: echo request
7.936523 port33,39 out 10.1.1.2 -> 239.1.1.1: icmp: echo request
7.936524 port33 out 10.1.1.2 -> 239.1.1.1: icmp: echo request
7.936533 port39 in 10.1.1.2 -> 239.1.1.1: icmp: echo request
7.936533 port33,39 in 10.1.1.2 -> 239.1.1.1: icmp: echo request

FGT2 # diag sniffer packet any 'host 239.1.1.1' 4 0
8.665930 port2 in 10.1.1.2 -> 239.1.1.1: icmp: echo request
8.665931 port1,2 in 10.1.1.2 -> 239.1.1.1: icmp: echo request
8.665935 port9 out 10.1.1.2 -> 239.1.1.1: icmp: echo request
8.665936 port1 in 10.1.1.2 -> 239.1.1.1: icmp: echo request
8.665936 port1,2 in 10.1.1.2 -> 239.1.1.1: icmp: echo request
8.665938 port9 out 10.1.1.2 -> 239.1.1.1: icmp: echo request
Focussing on FGT1:

Ingress packet is received on port17:
7.936514 port17 in 10.1.1.2 -> 239.1.1.1: icmp: echo request

The same packet is sent out on redundant interface port33,39, then physical interface port33:
7.936523 port33,39 out 10.1.1.2 -> 239.1.1.1: icmp: echo request
7.936524 port33 out 10.1.1.2 -> 239.1.1.1: icmp: echo request

The same packet is received on port39:
7.936533 port39 in 10.1.1.2 -> 239.1.1.1: icmp: echo request

The reason why the packet is received on port39 is that the switch floods the multicast frames to all ports except the original one.

Remember that flooding of BUM (Broadcast, Unknown unicast and Multicast) is an inherent part of switching.

Focussing on FGT2:

Ingress packet is received on port2 and reaches the redundant interface:
8.665930 port2 in 10.1.1.2 -> 239.1.1.1: icmp: echo request
8.665931 port1,2 in 10.1.1.2 -> 239.1.1.1: icmp: echo request

The same packet is sent out on port9 :
8.665935 port9 out 10.1.1.2 -> 239.1.1.1: icmp: echo request

In the meantime, the same packet is received on port1 (other member of redundant port1,2):
8.665936 port1 in 10.1.1.2 -> 239.1.1.1: icmp: echo request
8.665936 port1,2 in 10.1.1.2 -> 239.1.1.1: icmp: echo request

It is then sent out on port9 resulting in 2 copies of the same packet on the receiver:
8.665938 port9 out 10.1.1.2 -> 239.1.1.1: icmp: echo request

The reason why the same packet is received on port1 and port2 is that the switch floods the multicast frames to all ports except the original one.

Hence it is not recommended to use redundant interface when there is multicast traffic on the network.

The only way to prevent the issue explained above is to enable PIM snooping on the switch in between the FortiGates so the switch will snoop the PIM join and PIM prune in order to forward the multicast traffic only to the proper interfaces instead of flooding it.

Contributors