简体   繁体   English

Linux NFQUEUE处理问题

[英]Linux NFQUEUE handling issue

I am trying to write a userspace application that binds to an NFQUEUE socket to which a kernel module will forward incoming packets (by tagging them NF_QUEUE). 我正在尝试编写一个绑定到NFQUEUE套接字的用户空间应用程序,内核模块将转发传入的数据包(通过标记它们为NF_QUEUE)。 This is accomplised by using an iptables rule like: 这是通过使用iptables规则来实现的,例如:

iptables -­A INPUT -j NFQUEUE --­­queue­-num 0

The iptables ACCEPT chain looks like this: iptables ACCEPT链看起来像这样:

iptables -L
Chain INPUT (policy ACCEPT)
target     prot opt source               destination        
ACCEPT     all  --  anywhere             anywhere            state    RELATED,ESTABLISHED
ACCEPT     icmp --  anywhere             anywhere           
ACCEPT     all  --  anywhere             anywhere           
ACCEPT     tcp  --  anywhere             anywhere            state NEW tcp dpt:ssh
REJECT     all  --  anywhere             anywhere            reject-with icmp-host-prohibited
NFQUEUE    all  --  anywhere             anywhere            NFQUEUE num 0

This is the code that polls the NFQUEUE socket (QNUM is 0): 这是轮询NFQUEUE套接字的代码(QNUM为0):

printf("binding nfnetlink_queue as nf_queue handler for AF_INET\n");
if (nfq_bind_pf(h, AF_INET) < 0)
{   
    fprintf(stderr, "error during nfq_bind_pf()\n");
    return 1;
}   

/* Register a  callback function for our queue number */
qh = nfq_create_queue(h, QNUM, &cb_func, NULL);

if (!qh)
{   
    fprintf(stderr, "error during creating nf_queue\n");
    return 1;
}   

/* See if we have received a packet and send it to our cb func */
fd = nfq_fd(h);
if (fd < 0)
   return 1;

#if 1    
for (;;)
{
    if ((rv = recv(fd, buf, sizeof(buf), 0)) >= 0) {
        nfq_handle_packet(h, buf, sizeof(buf)); /* send packet to callback */
        continue;
    }
}
#endif

The problem is that /proc/net/netfilter/nf_queue lists queue number 2 instead of number 0 as being used and thus my userspace program does not detect any incoming packet in the associated socket. 问题是/ proc / net / netfilter / nf_queue列出了正在使用的队列号2而不是数字0,因此我的用户空间程序没有检测到相关套接字中的任何传入数据包。 Why is that? 这是为什么?

cat /proc/net/netfilter/nf_queue
0 NONE
1 NONE
2 nf_queue
3 NONE
4 NONE
5 NONE
6 NONE
7 NONE
8 NONE
9 NONE
10 NONE
11 NONE
12 NONE

I figured it out. 我想到了。 After all, I didn't even need a kernel module to do this, just the iptables rule. 毕竟,我甚至不需要内核模块来执行此操作,只需要iptables规则。 The problem was that the rule was not the first in the chain. 问题是规则不是链中的第一个。 Moving it first, with 首先移动它,用

sudo iptables -I INPUT -j NFQUEUE --queue-num 0

solved it. 解决了它。

You may want to adjust NFQUEUE to target only specific ports, else you may end up accidentally locking yourself out of your system. 您可能希望调整NFQUEUE以仅定位特定端口,否则您可能会意外地将自己锁定在系统之外。

For example, a typical use of NFQUEUE is suricata IPS. 例如,NFQUEUE的典型用途是suricata IPS。 If suricata goes into a failed state, ssh access will go with it. 如果suricata进入失败状态,ssh访问将继续使用它。

You can target a specific port with the following IP tables rule: 您可以使用以下IP表规则来定位特定端口:

-A INPUT -p tcp --dport <port> -j NFQUEUE --queue-num 0
-A OUTPUT -p tcp --sport <port> -j NFQUEUE --queue-num 0

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM