mirror of
https://github.com/nxtrace/NTrace-core.git
synced 2025-08-12 06:26:39 +00:00
improve: rootless trace on macOS
This commit is contained in:
@@ -12,6 +12,7 @@ import (
|
||||
"sync"
|
||||
"time"
|
||||
|
||||
"github.com/xgadget-lab/nexttrace/trace/internal"
|
||||
"golang.org/x/net/context"
|
||||
"golang.org/x/net/icmp"
|
||||
"golang.org/x/net/ipv4"
|
||||
@@ -64,7 +65,7 @@ func (t *ICMPTracer) Execute() (*Result, error) {
|
||||
|
||||
var err error
|
||||
|
||||
t.icmpListen, err = net.ListenPacket("ip4:1", t.SrcAddr)
|
||||
t.icmpListen, err = internal.ListenICMP("ip4:1", t.SrcAddr)
|
||||
if err != nil {
|
||||
return &t.res, err
|
||||
}
|
||||
|
||||
@@ -10,6 +10,7 @@ import (
|
||||
"sync"
|
||||
"time"
|
||||
|
||||
"github.com/xgadget-lab/nexttrace/trace/internal"
|
||||
"golang.org/x/net/context"
|
||||
"golang.org/x/net/icmp"
|
||||
"golang.org/x/net/ipv6"
|
||||
@@ -65,7 +66,7 @@ func (t *ICMPTracerv6) Execute() (*Result, error) {
|
||||
|
||||
var err error
|
||||
|
||||
t.icmpListen, err = net.ListenPacket("ip6:58", t.SrcAddr)
|
||||
t.icmpListen, err = internal.ListenICMP("ip6:58", t.SrcAddr)
|
||||
if err != nil {
|
||||
return &t.res, err
|
||||
}
|
||||
|
||||
49
trace/internal/icmp_darwin.go
Normal file
49
trace/internal/icmp_darwin.go
Normal file
@@ -0,0 +1,49 @@
|
||||
//go:build darwin
|
||||
|
||||
package internal
|
||||
|
||||
import (
|
||||
"context"
|
||||
"errors"
|
||||
"net"
|
||||
"os"
|
||||
"syscall"
|
||||
"unsafe"
|
||||
)
|
||||
|
||||
//go:linkname internetSocket net.internetSocket
|
||||
func internetSocket(ctx context.Context, net string, laddr, raddr interface{}, sotype, proto int, mode string, ctrlCtxFn func(context.Context, string, string, syscall.RawConn) error) (fd unsafe.Pointer, err error)
|
||||
|
||||
//go:linkname newIPConn net.newIPConn
|
||||
func newIPConn(fd unsafe.Pointer) *net.IPConn
|
||||
|
||||
var (
|
||||
errUnknownNetwork = errors.New("unknown network type")
|
||||
|
||||
networkMap = map[string]string{
|
||||
"ip4:icmp": "udp4",
|
||||
"ip4:1": "udp4",
|
||||
"ip6:icmp": "udp6",
|
||||
"ip6:58": "udp6",
|
||||
}
|
||||
)
|
||||
|
||||
func ListenICMP(network string, laddr string) (net.PacketConn, error) {
|
||||
if os.Getuid() == 0 { // root
|
||||
return net.ListenPacket(network, laddr)
|
||||
} else {
|
||||
if nw, ok := networkMap[network]; ok {
|
||||
proto := syscall.IPPROTO_ICMP
|
||||
if nw == "udp6" {
|
||||
proto = syscall.IPPROTO_ICMPV6
|
||||
}
|
||||
isock, err := internetSocket(context.Background(), nw, nil, nil, syscall.SOCK_DGRAM, proto, "listen", nil)
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
return newIPConn(isock), nil
|
||||
} else {
|
||||
return nil, errUnknownNetwork
|
||||
}
|
||||
}
|
||||
}
|
||||
0
trace/internal/icmp_darwin.s
Normal file
0
trace/internal/icmp_darwin.s
Normal file
9
trace/internal/icmp_general.go
Normal file
9
trace/internal/icmp_general.go
Normal file
@@ -0,0 +1,9 @@
|
||||
//go:build !darwin
|
||||
|
||||
package internal
|
||||
|
||||
import "net"
|
||||
|
||||
func ListenICMP(network string, laddr string) (net.PacketConn, error) {
|
||||
return net.ListenPacket(network, laddr)
|
||||
}
|
||||
@@ -2,12 +2,12 @@ package trace
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"github.com/xgadget-lab/nexttrace/util"
|
||||
"net"
|
||||
"sync"
|
||||
"time"
|
||||
|
||||
"github.com/xgadget-lab/nexttrace/ipgeo"
|
||||
"github.com/xgadget-lab/nexttrace/util"
|
||||
)
|
||||
|
||||
var (
|
||||
|
||||
Reference in New Issue
Block a user