@@ -537,51 +537,70 @@ func (r *autoRedirect) nftablesCreateDNSHijackRulesForFamily(
537
537
dnsServer = r .tunOptions .Inet6Address [0 ].Addr ().Next ()
538
538
}
539
539
}
540
- nft .AddRule (& nftables.Rule {
541
- Table : table ,
542
- Chain : chain ,
543
- Exprs : []expr.Any {
544
- & expr.Meta {
545
- Key : expr .MetaKeyNFPROTO ,
546
- Register : 1 ,
547
- },
548
- & expr.Cmp {
549
- Op : expr .CmpOpEq ,
550
- Register : 1 ,
551
- Data : []byte {uint8 (family )},
552
- },
540
+ exprs := []expr.Any {
541
+ & expr.Meta {
542
+ Key : expr .MetaKeyNFPROTO ,
543
+ Register : 1 ,
544
+ },
545
+ & expr.Cmp {
546
+ Op : expr .CmpOpEq ,
547
+ Register : 1 ,
548
+ Data : []byte {uint8 (family )},
549
+ },
550
+ }
551
+ if chain .Hooknum == nftables .ChainHookOutput {
552
+ // It looks like we can't hijack DNS requests sent to loopback.
553
+ // https://serverfault.com/questions/363899/iptables-dnat-from-loopback
554
+ // and tproxy is not available in output
555
+ exprs = append (exprs ,
553
556
& expr.Meta {
554
- Key : expr .MetaKeyL4PROTO ,
557
+ Key : expr .MetaKeyOIFNAME ,
555
558
Register : 1 ,
556
559
},
557
- & expr.Lookup {
558
- SourceRegister : 1 ,
559
- SetID : ipProto .ID ,
560
- SetName : ipProto .Name ,
561
- },
562
- & expr.Payload {
563
- OperationType : expr .PayloadLoad ,
564
- DestRegister : 1 ,
565
- Base : expr .PayloadBaseTransportHeader ,
566
- Offset : 2 ,
567
- Len : 2 ,
568
- },
569
560
& expr.Cmp {
570
- Op : expr .CmpOpEq ,
561
+ Op : expr .CmpOpNeq ,
571
562
Register : 1 ,
572
- Data : binaryutil .BigEndian .PutUint16 (53 ),
573
- },
574
- & expr.Counter {},
575
- & expr.Immediate {
576
- Register : 1 ,
577
- Data : dnsServer .AsSlice (),
578
- },
579
- & expr.NAT {
580
- Type : expr .NATTypeDestNAT ,
581
- Family : uint32 (family ),
582
- RegAddrMin : 1 ,
563
+ Data : nftablesIfname ("lo" ),
583
564
},
565
+ )
566
+ }
567
+ exprs = append (exprs ,
568
+ & expr.Meta {
569
+ Key : expr .MetaKeyL4PROTO ,
570
+ Register : 1 ,
584
571
},
572
+ & expr.Lookup {
573
+ SourceRegister : 1 ,
574
+ SetID : ipProto .ID ,
575
+ SetName : ipProto .Name ,
576
+ },
577
+ & expr.Payload {
578
+ OperationType : expr .PayloadLoad ,
579
+ DestRegister : 1 ,
580
+ Base : expr .PayloadBaseTransportHeader ,
581
+ Offset : 2 ,
582
+ Len : 2 ,
583
+ },
584
+ & expr.Cmp {
585
+ Op : expr .CmpOpEq ,
586
+ Register : 1 ,
587
+ Data : binaryutil .BigEndian .PutUint16 (53 ),
588
+ },
589
+ & expr.Immediate {
590
+ Register : 1 ,
591
+ Data : dnsServer .AsSlice (),
592
+ },
593
+ & expr.NAT {
594
+ Type : expr .NATTypeDestNAT ,
595
+ Family : uint32 (family ),
596
+ RegAddrMin : 1 ,
597
+ },
598
+ & expr.Counter {},
599
+ )
600
+ nft .AddRule (& nftables.Rule {
601
+ Table : table ,
602
+ Chain : chain ,
603
+ Exprs : exprs ,
585
604
})
586
605
return nil
587
606
}
0 commit comments