linux 内核 发送数据,使用Linux内核模块发送的UDP数据包不使用套...

您不需要套接字就可以在内核中发送UDP数据包,只需分配一个skb,自己构造IP报头和UDP报头,最后通过dev_queue_xmit()将其发送出去.

skb = alloc_skb(len, GFP_ATOMIC);

if (!skb)

return;

skb_put(skb, len);

skb_push(skb, sizeof(*udph));

skb_reset_transport_header(skb);

udph = udp_hdr(skb);

udph->source = htons(....);

udph->dest = htons(...);

udph->len = htons(udp_len);

udph->check = 0;

udph->check = csum_tcpudp_magic(local_ip,

remote_ip,

udp_len, IPPROTO_UDP,

csum_partial(udph, udp_len, 0));

if (udph->check == 0)

udph->check = CSUM_MANGLED_0;

skb_push(skb, sizeof(*iph));

skb_reset_network_header(skb);

iph = ip_hdr(skb);

/* iph->version = 4; iph->ihl = 5; */

put_unaligned(0x45, (unsigned char *)iph);

iph->tos = 0;

put_unaligned(htons(ip_len), &(iph->tot_len));

iph->id = htons(atomic_inc_return(&ip_ident));

iph->frag_off = 0;

iph->ttl = 64;

iph->protocol = IPPROTO_UDP;

iph->check = 0;

put_unaligned(local_ip, &(iph->saddr));

put_unaligned(remote_ip, &(iph->daddr));

iph->check = ip_fast_csum((unsigned char *)iph, iph->ihl);

eth = (struct ethhdr *) skb_push(skb, ETH_HLEN);

skb_reset_mac_header(skb);

skb->protocol = eth->h_proto = htons(ETH_P_IP);

memcpy(eth->h_source, dev->dev_addr, ETH_ALEN);

memcpy(eth->h_dest, remote_mac, ETH_ALEN);

skb->dev = dev;

dev_queue_xmit(skb);

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值