8个版本 (破坏性更新)

使用旧的Rust 2015

0.7.0 2023年1月22日
0.6.0 2022年7月16日
0.5.0 2020年5月3日
0.4.0 2019年11月15日
0.1.1 2019年8月27日

#14 in #udp-packet

每月40次下载
用于 2 crates

MIT/Apache

27KB
499

packet_builder

Crates.io - packet_builder Build Status License: MIT License: Apache-2.0

packet_builder 是一个高级Rust库,用于低级网络,它使用宏来提供类似python的dpkt/scapy的“kwargs-like”接口。

使用 packet_builder 您可以构建和修改任意的数据包,并尝试通过NIC发送,它底层使用 libpnet

sendpacket 已停止维护,因此作为一个学习Rust的练习,我将其分叉以创建 packet_builder。对于未由调用者设置的域,使用合理的默认值,并为您计算校验和。目前支持以下协议:

  • 以太网
  • ARP
  • 802.1Q
  • IPv4
  • ICMP
  • UDP
  • TCP

示例

所有宏实际上都是libpnet中的数据包结构和函数的包装,所以libpnet中各种数据包类型的所有设置函数都是有效的。请参阅示例目录以获取完整的示例。

生成一个目标不可达的ICMP数据包并发送它

let mut pkt_buf = [0u8; 1500];
let pkt = packet_builder!(
     pkt_buf,
     ether({set_source => MacAddr(10,1,1,1,1,1)}) / 
     ipv4({set_source => ipv4addr!("127.0.0.1"), set_destination => ipv4addr!("127.0.0.1") }) /
     icmp_dest_unreach({set_icmp_type => IcmpTypes::DestinationUnreachable}) / 
     ipv4({set_source => ipv4addr!("10.8.0.1"), set_destination => ipv4addr!("127.0.0.1") }) /
     udp({set_source => 53, set_destination => 5353}) /
     payload({"hello".to_string().into_bytes()})
);

let if_name = env::args().nth(1)
    .expect("Usage: ./packet_builder <interface name>");
let (mut sender, _receiver) = build_channel!(if_name);
sender.send_to(pkt.packet(), None).unwrap().unwrap();

生成带有数据的TCP PSH|ACK数据包

let mut pkt_buf = [0u8; 1500];
let pkt = packet_builder!(
     pkt_buf,
     ether({set_destination => MacAddr(1,2,3,4,5,6), set_source => MacAddr(10,1,1,1,1,1)}) / 
     ipv4({set_source => ipv4addr!("127.0.0.1"), set_destination => ipv4addr!("127.0.0.1") }) /
     tcp({set_source => 43455, set_destination => 80, set_flags => (TcpFlags::PSH | TcpFlags::ACK)}) /
     payload({"hello".to_string().into_bytes()})
);

在VLAN ID 10上生成带有mss和wscale选项的TCP SYN数据包

let mut pkt_buf = [0u8; 1500];
let pkt = packet_builder!(
   pkt_buf,
   ether({set_destination => MacAddr(1,2,3,4,5,6), set_source => MacAddr(10,1,1,1,1,1)}) /
   vlan({set_vlan_identifier => 10}) /
   ipv4({set_source => ipv4addr!("192.168.1.1"), set_destination => ipv4addr!("127.0.0.1") }) /
   tcp({set_source => 43455, set_destination => 80, set_options => &[TcpOption::mss(1200), TcpOption::wscale(2)]}) /
   payload({[0; 0]})
);

生成带有数据的UDP数据包

let mut pkt_buf = [0u8; 1500];
let pkt = packet_builder!(
     pkt_buf,
     ether({set_destination => MacAddr(1,2,3,4,5,6), set_source => MacAddr(10,1,1,1,1,1)}) / 
     ipv4({set_source => ipv4addr!("127.0.0.1"), set_destination => ipv4addr!("127.0.0.1") }) /
     udp({set_source => 12312, set_destination => 143}) /
     payload({"hello".to_string().into_bytes()})
);

生成ICMP Echo Request数据包

let mut pkt_buf = [0u8; 1500];
let pkt = packet_builder!(
     pkt_buf,
     ether({set_destination => MacAddr(1,2,3,4,5,6), set_source => MacAddr(10,1,1,1,1,1)}) / 
     ipv4({set_source => ipv4addr!("127.0.0.1"), set_destination => ipv4addr!("127.0.0.1") }) /
     icmp_echo_req({set_icmp_type => IcmpTypes::EchoRequest}) / 
     payload({"hello".to_string().into_bytes()})
);

许可证

许可协议为以下之一:

任选其一。

贡献

除非您明确声明,否则任何有意提交以包含在您的工作中的贡献,如Apache-2.0许可证中定义的,均应如上双许可,而无需任何额外条款或条件。

依赖关系

~4–5.5MB
~108K SLoC