netfilter: fix looped (broad|multi)cast's MAC handling
By default, when broadcast or multicast packet are sent from a local application, they are sent to the interface then looped by the kernel to other local applications, going throught netfilter hooks in the process. These looped packet have their MAC header removed from the skb by the kernel looping code. This confuse various netfilter's netlink queue, netlink log and the legacy ip_queue, because they try to extract a hardware address from these packets, but extracts a part of the IP header instead. This patch prevent NFQUEUE, NFLOG and ip_QUEUE to include a MAC header if there is none in the packet. Signed-off-by: Nicolas Cavallari <cavallar@lri.fr> Signed-off-by: Patrick McHardy <kaber@trash.net>
This commit is contained in:
Родитель
db898aa2ef
Коммит
2c38de4c1f
|
@ -203,7 +203,8 @@ ipq_build_packet_message(struct nf_queue_entry *entry, int *errp)
|
||||||
else
|
else
|
||||||
pmsg->outdev_name[0] = '\0';
|
pmsg->outdev_name[0] = '\0';
|
||||||
|
|
||||||
if (entry->indev && entry->skb->dev) {
|
if (entry->indev && entry->skb->dev &&
|
||||||
|
entry->skb->mac_header != entry->skb->network_header) {
|
||||||
pmsg->hw_type = entry->skb->dev->type;
|
pmsg->hw_type = entry->skb->dev->type;
|
||||||
pmsg->hw_addrlen = dev_parse_header(entry->skb,
|
pmsg->hw_addrlen = dev_parse_header(entry->skb,
|
||||||
pmsg->hw_addr);
|
pmsg->hw_addr);
|
||||||
|
|
|
@ -204,7 +204,8 @@ ipq_build_packet_message(struct nf_queue_entry *entry, int *errp)
|
||||||
else
|
else
|
||||||
pmsg->outdev_name[0] = '\0';
|
pmsg->outdev_name[0] = '\0';
|
||||||
|
|
||||||
if (entry->indev && entry->skb->dev) {
|
if (entry->indev && entry->skb->dev &&
|
||||||
|
entry->skb->mac_header != entry->skb->network_header) {
|
||||||
pmsg->hw_type = entry->skb->dev->type;
|
pmsg->hw_type = entry->skb->dev->type;
|
||||||
pmsg->hw_addrlen = dev_parse_header(entry->skb, pmsg->hw_addr);
|
pmsg->hw_addrlen = dev_parse_header(entry->skb, pmsg->hw_addr);
|
||||||
}
|
}
|
||||||
|
|
|
@ -456,7 +456,8 @@ __build_packet_message(struct nfulnl_instance *inst,
|
||||||
if (skb->mark)
|
if (skb->mark)
|
||||||
NLA_PUT_BE32(inst->skb, NFULA_MARK, htonl(skb->mark));
|
NLA_PUT_BE32(inst->skb, NFULA_MARK, htonl(skb->mark));
|
||||||
|
|
||||||
if (indev && skb->dev) {
|
if (indev && skb->dev &&
|
||||||
|
skb->mac_header != skb->network_header) {
|
||||||
struct nfulnl_msg_packet_hw phw;
|
struct nfulnl_msg_packet_hw phw;
|
||||||
int len = dev_parse_header(skb, phw.hw_addr);
|
int len = dev_parse_header(skb, phw.hw_addr);
|
||||||
if (len > 0) {
|
if (len > 0) {
|
||||||
|
|
|
@ -335,7 +335,8 @@ nfqnl_build_packet_message(struct nfqnl_instance *queue,
|
||||||
if (entskb->mark)
|
if (entskb->mark)
|
||||||
NLA_PUT_BE32(skb, NFQA_MARK, htonl(entskb->mark));
|
NLA_PUT_BE32(skb, NFQA_MARK, htonl(entskb->mark));
|
||||||
|
|
||||||
if (indev && entskb->dev) {
|
if (indev && entskb->dev &&
|
||||||
|
entskb->mac_header != entskb->network_header) {
|
||||||
struct nfqnl_msg_packet_hw phw;
|
struct nfqnl_msg_packet_hw phw;
|
||||||
int len = dev_parse_header(entskb, phw.hw_addr);
|
int len = dev_parse_header(entskb, phw.hw_addr);
|
||||||
if (len) {
|
if (len) {
|
||||||
|
|
Загрузка…
Ссылка в новой задаче