1

I've written a custom wireless system/driver which works on top of a wifi card with packet injection and is in monitor mode. My program is based upon libpcap and uses pcap_inject to send packets over the wireless device.

It works just fine with any amounts of incoming traffic and with 1-2 packets per second outgoing (ICMP ping). The issue, however, is that when I start trying to transmit much faster (TCP, more useful protocols at 25+ packets per second) I quickly seem to run out of buffer and my program errors out with Failed to inject packet: send: Resource temporarily unavailable.

This doesn't make any sense to me. I know for a fact that my wireless card can transmit fast enough to handle TCP at rates of over 500Mb/s (so it's not saturating the TX ring buffer of the device) so I assume the issue lies somewhere else. Is packet injection somehow less optimized in drivers/firmware? Is libpcap just sidestepping some sort of important buffer and trying to transmit exclusively itself?

3
  • 1
    pcap is definitely less optimized than the kernel network stack. I don't know details, but my first guess would be that pcap needs system calls for every single packet, and the userspace/kernelspace switch necessary for that won't allow "real use" throughput rates - after all, it's for hacking etc. At what protocol level do you need to inject packets? Can't you use the existing kernel infrastructure, and/or write a kernel module?
    – dirkt
    Jan 2, 2018 at 9:08
  • I'm interfacing with a custom 802.11 protocol system. It's essentially IP glued directly into a beacon frame. Any ideas where/how the kernel would transmit 80211 frames? @dirkt
    – Allison
    Jan 2, 2018 at 9:15
  • Maybe you are just counting on handling one packet at a time, and need to think about implementing a buffer? Jan 2, 2018 at 10:43

2 Answers 2

1

This actually wasn't a libpcap problem but instead a wireless engineering issue. The channel I'm working on is already pretty noisy however since this is an unregulated mesh (meaning nobody to coordinate using RTS/CTS) and so my wifi card, in monitor mode, decided to fall back to the "listen and wait for silence" approach which is obviously slower and more error prone. This meant that I couldn't transmit very fast which meant my TX buffer filled up very quickly, giving the Resource temporarily unavailable error. This is a result of physical carrier sensing (CCA), which causes an exponential backoff.

I switched to an empty channel (with only a packet every two seconds) and I was suddenly able to transmit at over a thousand packets per second which is far better. My transmission speed is still pretty bad (maxing out at roughly 600KB/s) but that's at least fast enough to be usable for me. This blog post seems to suggest that some cards just can't inject that fast

Unfortunately with my wireless card and its drivers there are no easy ways to disable this very timid transmission behavior. Some drivers let you mess with the backoff parameters, others let you actually disable CCA if you have an Atheros card.

0

Sending TCP packets at high rate via pcap_inject does not sound like a performance battle you're likely to win. Consider abusing the high performance TCP machinery to send such packets to a custom kernel module, which adjusts the payload according to your needs and forwards packets out the network interface.

1
  • Hmm, that's what I was afraid of. If you're familiar with kernel dev, could you point me in the direction of what system I'd use for tossing packets into the interface to be TX'd? I've been reading through mac80211 and thinking I could use ieee80211_tx to throw raw frames into the driver instead writing my own kernel driver
    – Allison
    Jan 6, 2018 at 23:48

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.