The Meshtastic firmware does not check for packets claiming to be from the special broadcast address (0xFFFFFFFF) which could result in unexpected behavior and potential for DDoS attacks on the network. A malicious actor could craft a packet to be from that address which would result in an amplification of this one message into every node on the network sending multiple messages. Such an attack could result in degraded network performance for all users as the available bandwidth is consumed.
When a Meshtastic node hears from an address which has not previously been seen the standard behavior is to send a request to that node for information about it. Therefore if a node hears a message from the broadcast address, it will send a message back to the broadcast address requesting information about it. However, sending such a request to the broadcast address has special meaning in Meshtastic. Such a message is normally sent when a node first joins the network and indicates that every other node should send their node information to the sender.
Therefore a malicious actor could send one packet which results in every node which receives it requesting that every other node tell them who they are. The impact of the malicious message would also spread beyond the original number of hops because each receiving node would request to all nodes within their range. Such an attack in traditional networks could be called an amplification attack because of the exponential increase in traffic. This scenario could result in an effective DDoS which degrades the available bandwidth of the network.
The firmware does contain certain protections against amplification, such as only allowing node information to be sent every so often or not when the channel utilization is too high. However, these protections being activated would also prevent non-malicious nodes from discovering each other and degrade the overall service.
I believe the most immediate solution is to update the firmware to drop any messages coming from the broadcast address. However, I am not familiar with all of the inter workings of the firmware so there may be other potential scenarios in which the special behavior associated with the broadcast address could be exploited. It should be analyzed if any other related vulnerabilities also exist.
The following logs demonstrates the behavior that a message is received from the broadcast address and it is treated as an unknown node which should be discovered. This node then receives from another node requesting node info because it also received the malicious message. This test was only done with a few nodes so it does not show the potential impact on a large network of nodes.
DEBUG | ??:??:?? 577 [RadioIf] (bw=250, sf=11, cr=4/5) packet symLen=8 ms, payloadSize=66, time 722 ms
DEBUG | ??:??:?? 577 [RadioIf] Lora RX (id=0xa6b244c5 fr=0xff to=0xff, WantAck=0, HopLim=1 Ch=0x8 encrypted rxSNR=7.25 rxRSSI=-20 hopStart=1)
DEBUG | ??:??:?? 577 [RadioIf] AirTime - Packet received : 722ms
DEBUG | ??:??:?? 577 [Router] Add packet record (id=0xa6b244c5 fr=0xff to=0xff, WantAck=0, HopLim=1 Ch=0x8 encrypted rxSNR=7.25 rxRSSI=-20 hopStart=1)
DEBUG | ??:??:?? 577 [Router] Using channel 0 (hash 0x8)
DEBUG | ??:??:?? 577 [Router] Expanding short PSK #1
DEBUG | ??:??:?? 577 [Router] Using AES128 key!
DEBUG | ??:??:?? 577 [Router] decoded message (id=0xa6b244c5 fr=0xff to=0xff, WantAck=0, HopLim=1 Ch=0x0 Portnum=1 rxSNR=7.25 rxRSSI=-20 hopStart=1)
DEBUG | ??:??:?? 577 [Router] handleReceived(REMOTE) (id=0xa6b244c5 fr=0xff to=0xff, WantAck=0, HopLim=1 Ch=0x0 Portnum=1 rxSNR=7.25 rxRSSI=-20 hopStart=1)
DEBUG | ??:??:?? 577 [Router] Module 'text' wantsPacket=1
INFO | ??:??:?? 577 [Router] Received text msg from=0xffffffff, id=0xa6b244c5, msg=Oh no
DEBUG | ??:??:?? 577 [Router] showing standard frames
DEBUG | ??:??:?? 577 [Router] Showing 0 module frames
DEBUG | ??:??:?? 577 [Router] Total frame count: 103
DEBUG | ??:??:?? 577 [Router] Added modules. numframes: 0
DEBUG | ??:??:?? 577 [Router] Finished building frames. numframes: 5
DEBUG | ??:??:?? 577 [Router] Module 'text' considered
DEBUG | ??:??:?? 577 [Router] Module 'routing' wantsPacket=1
INFO | ??:??:?? 577 [Router] Received routing from=0xffffffff, id=0xa6b244c5, portnum=1, payloadlen=19
DEBUG | ??:??:?? 577 [Router] Routing sniffing (id=0xa6b244c5 fr=0xff to=0xff, WantAck=0, HopLim=1 Ch=0x0 Portnum=1 rxSNR=7.25 rxRSSI=-20 hopStart=1)
INFO | ??:??:?? 577 [Router] Rebroadcasting received floodmsg to neighbors
DEBUG | ??:??:?? 577 [Router] Expanding short PSK #1
DEBUG | ??:??:?? 577 [Router] Using AES128 key!
DEBUG | ??:??:?? 577 [Router] enqueuing for send (id=0xa6b244c5 fr=0xff to=0xff, WantAck=0, HopLim=0 Ch=0x8 encrypted rxSNR=7.25 rxRSSI=-20 hopStart=1 priority=100)
DEBUG | ??:??:?? 577 [Router] txGood=3,rxGood=5,rxBad=0
DEBUG | ??:??:?? 577 [Router] rx_snr found. hop_limit:0 rx_snr:7.250000
DEBUG | ??:??:?? 577 [Router] rx_snr found in packet. Setting tx delay:2387
DEBUG | ??:??:?? 577 [Router] Delivering rx packet (id=0xa6b244c5 fr=0xff to=0xff, WantAck=0, HopLim=1 Ch=0x0 Portnum=1 rxSNR=7.25 rxRSSI=-20 hopStart=1)
DEBUG | ??:??:?? 577 [Router] Update DB node 0xffffffff, rx_time=0
INFO | ??:??:?? 577 [Router] Adding node to database with 4 nodes and 182164 bytes free!
INFO | ??:??:?? 577 [Router] Heard a node on channel 0 we don't know, sending NodeInfo and asking for a response.
DEBUG | ??:??:?? 577 [Router] cancelSending id=0x6260398f, removed=0
INFO | ??:??:?? 577 [Router] sending owner !335c1bac/JH1B/JH1B
DEBUG | ??:??:?? 577 [Router] Partially randomized packet id 2347523473
DEBUG | ??:??:?? 577 [Router] Update DB node 0x335c1bac, rx_time=0
DEBUG | ??:??:?? 577 [Router] handleReceived(LOCAL) (id=0x8bec5d91 fr=0xac to=0xff, WantAck=0, HopLim=3 Ch=0x0 Portnum=4 WANTRESP priority=10)
DEBUG | ??:??:?? 577 [Router] No modules interested in portnum=4, src=LOCAL
DEBUG | ??:??:?? 577 [Router] localSend to channel 0
DEBUG | ??:??:?? 577 [Router] Add packet record (id=0x8bec5d91 fr=0xac to=0xff, WantAck=0, HopLim=3 Ch=0x0 Portnum=4 WANTRESP priority=10)
DEBUG | ??:??:?? 577 [Router] Expanding short PSK #1
DEBUG | ??:??:?? 577 [Router] Using AES128 key!
DEBUG | ??:??:?? 577 [Router] enqueuing for send (id=0x8bec5d91 fr=0xac to=0xff, WantAck=0, HopLim=3 Ch=0x8 encrypted hopStart=3 priority=10)
DEBUG | ??:??:?? 577 [Router] txGood=3,rxGood=5,rxBad=0
DEBUG | ??:??:?? 577 [Router] rx_snr found. hop_limit:0 rx_snr:7.250000
DEBUG | ??:??:?? 577 [Router] rx_snr found in packet. Setting tx delay:2695
DEBUG | ??:??:?? 577 [Router] Forwarding to phone (id=0xa6b244c5 fr=0xff to=0xff, WantAck=0, HopLim=1 Ch=0x0 Portnum=1 rxSNR=7.25 rxRSSI=-20 hopStart=1)
DEBUG | ??:??:?? 577 [Router] Module 'routing' considered
DEBUG | ??:??:?? 579 [RadioIf] rx_snr found. hop_limit:0 rx_snr:7.250000
DEBUG | ??:??:?? 579 [RadioIf] rx_snr found in packet. Setting tx delay:2079
DEBUG | ??:??:?? 580 [RadioIf] (bw=250, sf=11, cr=4/5) packet symLen=8 ms, payloadSize=39, time 526 ms
DEBUG | ??:??:?? 580 [RadioIf] Lora RX (id=0xa6b244c5 fr=0xff to=0xff, WantAck=0, HopLim=0 Ch=0x8 encrypted rxSNR=5.5 rxRSSI=-41 hopStart=1)
DEBUG | ??:??:?? 580 [RadioIf] AirTime - Packet received : 526ms
DEBUG | ??:??:?? 580 [Router] Found existing packet record for fr=0xffffffff,to=0xffffffff,id=0xa6b244c5
DEBUG | ??:??:?? 580 [Router] Found existing packet record for fr=0xffffffff,to=0xffffffff,id=0xa6b244c5
DEBUG | ??:??:?? 580 [Router] Add packet record (id=0xa6b244c5 fr=0xff to=0xff, WantAck=0, HopLim=0 Ch=0x8 encrypted rxSNR=5.5 rxRSSI=-41 hopStart=1)
DEBUG | ??:??:?? 580 [Router] Ignoring incoming msg we've already seen (id=0xa6b244c5 fr=0xff to=0xff, WantAck=0, HopLim=0 Ch=0x8 encrypted rxSNR=5.5 rxRSSI=-41 hopStart=1)
DEBUG | ??:??:?? 580 [Router] cancelSending id=0xa6b244c5, removed=1
DEBUG | ??:??:?? 580 [Router] Incoming message was filtered from 0xffffffff
WARN | ??:??:?? 580 [RadioIf] Can not send yet, busyRx
WARN | ??:??:?? 580 [RadioIf] Can not send yet, busyRx
WARN | ??:??:?? 581 [RadioIf] Can not send yet, busyRx
WARN | ??:??:?? 581 [RadioIf] Can not send yet, busyRx
WARN | ??:??:?? 581 [RadioIf] Can not send yet, busyRx
DEBUG | ??:??:?? 581 [RadioIf] (bw=250, sf=11, cr=4/5) packet symLen=8 ms, payloadSize=102, time 993 ms
DEBUG | ??:??:?? 581 [RadioIf] Lora RX (id=0x221eb970 fr=0xd8 to=0xff, WantAck=0, HopLim=3 Ch=0x8 encrypted rxSNR=6.5 rxRSSI=-40 hopStart=3)
DEBUG | ??:??:?? 581 [RadioIf] AirTime - Packet received : 993ms
DEBUG | ??:??:?? 581 [Router] Add packet record (id=0x221eb970 fr=0xd8 to=0xff, WantAck=0, HopLim=3 Ch=0x8 encrypted rxSNR=6.5 rxRSSI=-40 hopStart=3)
DEBUG | ??:??:?? 581 [Router] Using channel 0 (hash 0x8)
DEBUG | ??:??:?? 581 [Router] Expanding short PSK #1
DEBUG | ??:??:?? 581 [Router] Using AES128 key!
DEBUG | ??:??:?? 581 [Router] decoded message (id=0x221eb970 fr=0xd8 to=0xff, WantAck=0, HopLim=3 Ch=0x0 Portnum=4 WANTRESP rxSNR=6.5 rxRSSI=-40 hopStart=3)
DEBUG | ??:??:?? 581 [Router] handleReceived(REMOTE) (id=0x221eb970 fr=0xd8 to=0xff, WantAck=0, HopLim=3 Ch=0x0 Portnum=4 WANTRESP rxSNR=6.5 rxRSSI=-40 hopStart=3)
DEBUG | ??:??:?? 581 [Router] Module 'nodeinfo' wantsPacket=1
INFO | ??:??:?? 581 [Router] Received nodeinfo from=0x43578bd8, id=0x221eb970, portnum=4, payloadlen=78
DEBUG | ??:??:?? 581 [Router] old user Meshtastic 8bd8/8bd8, channel=0
DEBUG | ??:??:?? 581 [Router] Incoming Pubkey: : aa 1d c0 2c f7 c3 da 33 f4 5a f0 f1 7f fa c1 65 9a 6f 3f 0a 57 a5 fc 96 7e 0b 9d fa 74 ca c2 31
INFO | ??:??:?? 581 [Router] Public Key set for node, not updating!
DEBUG | ??:??:?? 581 [Router] Saved Pubkey: : aa 1d c0 2c f7 c3 da 33 f4 5a f0 f1 7f fa c1 65 9a 6f 3f 0a 57 a5 fc 96 7e 0b 9d fa 74 ca c2 31
DEBUG | ??:??:?? 581 [Router] updating changed=0 user Meshtastic 8bd8/8bd8, channel=0
DEBUG | ??:??:?? 581 [Router] Skip sending NodeInfo since we just sent it less than 5 minutes ago.
INFO | ??:??:?? 581 [Router] Asked module 'nodeinfo' to send a response
DEBUG | ??:??:?? 581 [Router] Module 'routing' wantsPacket=1
INFO | ??:??:?? 581 [Router] Received routing from=0x43578bd8, id=0x221eb970, portnum=4, payloadlen=78
DEBUG | ??:??:?? 581 [Router] Routing sniffing (id=0x221eb970 fr=0xd8 to=0xff, WantAck=0, HopLim=3 Ch=0x0 Portnum=4 WANTRESP rxSNR=6.5 rxRSSI=-40 hopStart=3)
INFO | ??:??:?? 581 [Router] Rebroadcasting received floodmsg to neighbors
DEBUG | ??:??:?? 581 [Router] Expanding short PSK #1
DEBUG | ??:??:?? 581 [Router] Using AES128 key!
DEBUG | ??:??:?? 581 [Router] enqueuing for send (id=0x221eb970 fr=0xd8 to=0xff, WantAck=0, HopLim=2 Ch=0x8 encrypted rxSNR=6.5 rxRSSI=-40 hopStart=3 priority=70)
DEBUG | ??:??:?? 581 [Router] txGood=3,rxGood=7,rxBad=0
DEBUG | ??:??:?? 581 [Router] rx_snr found. hop_limit:2 rx_snr:6.500000
DEBUG | ??:??:?? 581 [Router] rx_snr found in packet. Setting tx delay:2926
DEBUG | ??:??:?? 581 [Router] Delivering rx packet (id=0x221eb970 fr=0xd8 to=0xff, WantAck=0, HopLim=3 Ch=0x0 Portnum=4 WANTRESP rxSNR=6.5 rxRSSI=-40 hopStart=3)
DEBUG | ??:??:?? 581 [Router] Update DB node 0x43578bd8, rx_time=0
DEBUG | ??:??:?? 581 [Router] Forwarding to phone (id=0x221eb970 fr=0xd8 to=0xff, WantAck=0, HopLim=3 Ch=0x0 Portnum=4 WANTRESP rxSNR=6.5 rxRSSI=-40 hopStart=3)
INFO | ??:??:?? 581 [Router] Asked module 'routing' to send a response
DEBUG | ??:??:?? 581 [Screen] Screen: Joined: Meshtastic 8bd8
DEBUG | ??:??:?? 581 [RadioIf] Starting low level send (id=0x221eb970 fr=0xd8 to=0xff, WantAck=0, HopLim=2 Ch=0x8 encrypted rxSNR=6.5 rxRSSI=-40 hopStart=3 priority=70)
DEBUG | ??:??:?? 581 [RadioIf] (bw=250, sf=11, cr=4/5) packet symLen=8 ms, payloadSize=102, time 993 ms
DEBUG | ??:??:?? 581 [RadioIf] AirTime - Packet transmitted : 993ms
DEBUG | ??:??:?? 581 [Power] Battery: usbPower=1, isCharging=1, batMv=4290, batPct=100
DEBUG | ??:??:?? 582 [RadioIf] Completed sending (id=0x221eb970 fr=0xd8 to=0xff, WantAck=0, HopLim=2 Ch=0x8 encrypted rxSNR=6.5 rxRSSI=-40 hopStart=3 priority=70)
DEBUG | ??:??:?? 582 [RadioIf] Starting low level send (id=0x8bec5d91 fr=0xac to=0xff, WantAck=0, HopLim=3 Ch=0x8 encrypted hopStart=3 priority=10)
DEBUG | ??:??:?? 582 [RadioIf] (bw=250, sf=11, cr=4/5) packet symLen=8 ms, payloadSize=91, time 911 ms
DEBUG | ??:??:?? 582 [RadioIf] AirTime - Packet transmitted : 911ms
DEBUG | ??:??:?? 583 [RadioIf] Completed sending (id=0x8bec5d91 fr=0xac to=0xff, WantAck=0, HopLim=3 Ch=0x8 encrypted hopStart=3 priority=10)
I do not know when this behavior was introduced, but any node running firmware older than 2.5.6 is probably affected. No user interaction or privileges are required to execute such an attack. The only impact is to availability. There is no impact to scope, confidentiality, or integrity.
Summary
The Meshtastic firmware does not check for packets claiming to be from the special broadcast address (0xFFFFFFFF) which could result in unexpected behavior and potential for DDoS attacks on the network. A malicious actor could craft a packet to be from that address which would result in an amplification of this one message into every node on the network sending multiple messages. Such an attack could result in degraded network performance for all users as the available bandwidth is consumed.
Details
When a Meshtastic node hears from an address which has not previously been seen the standard behavior is to send a request to that node for information about it. Therefore if a node hears a message from the broadcast address, it will send a message back to the broadcast address requesting information about it. However, sending such a request to the broadcast address has special meaning in Meshtastic. Such a message is normally sent when a node first joins the network and indicates that every other node should send their node information to the sender.
Therefore a malicious actor could send one packet which results in every node which receives it requesting that every other node tell them who they are. The impact of the malicious message would also spread beyond the original number of hops because each receiving node would request to all nodes within their range. Such an attack in traditional networks could be called an amplification attack because of the exponential increase in traffic. This scenario could result in an effective DDoS which degrades the available bandwidth of the network.
The firmware does contain certain protections against amplification, such as only allowing node information to be sent every so often or not when the channel utilization is too high. However, these protections being activated would also prevent non-malicious nodes from discovering each other and degrade the overall service.
I believe the most immediate solution is to update the firmware to drop any messages coming from the broadcast address. However, I am not familiar with all of the inter workings of the firmware so there may be other potential scenarios in which the special behavior associated with the broadcast address could be exploited. It should be analyzed if any other related vulnerabilities also exist.
PoC
The following logs demonstrates the behavior that a message is received from the broadcast address and it is treated as an unknown node which should be discovered. This node then receives from another node requesting node info because it also received the malicious message. This test was only done with a few nodes so it does not show the potential impact on a large network of nodes.
Impact
I do not know when this behavior was introduced, but any node running firmware older than 2.5.6 is probably affected. No user interaction or privileges are required to execute such an attack. The only impact is to availability. There is no impact to scope, confidentiality, or integrity.