mirror of
https://github.com/MetaCubeX/mihomo.git
synced 2025-12-19 08:20:05 +08:00
Some checks are pending
Test / test (1.20, macos-15-intel) (push) Waiting to run
Test / test (1.20, macos-latest) (push) Waiting to run
Test / test (1.20, ubuntu-24.04-arm) (push) Waiting to run
Test / test (1.20, ubuntu-latest) (push) Waiting to run
Test / test (1.20, windows-latest) (push) Waiting to run
Test / test (1.21, macos-15-intel) (push) Waiting to run
Test / test (1.21, macos-latest) (push) Waiting to run
Test / test (1.21, ubuntu-24.04-arm) (push) Waiting to run
Test / test (1.21, ubuntu-latest) (push) Waiting to run
Test / test (1.21, windows-latest) (push) Waiting to run
Test / test (1.22, macos-15-intel) (push) Waiting to run
Test / test (1.22, macos-latest) (push) Waiting to run
Test / test (1.22, ubuntu-24.04-arm) (push) Waiting to run
Test / test (1.22, ubuntu-latest) (push) Waiting to run
Test / test (1.22, windows-latest) (push) Waiting to run
Test / test (1.23, macos-15-intel) (push) Waiting to run
Test / test (1.23, macos-latest) (push) Waiting to run
Test / test (1.23, ubuntu-24.04-arm) (push) Waiting to run
Test / test (1.23, ubuntu-latest) (push) Waiting to run
Test / test (1.23, windows-latest) (push) Waiting to run
Test / test (1.24, macos-15-intel) (push) Waiting to run
Test / test (1.24, macos-latest) (push) Waiting to run
Test / test (1.24, ubuntu-24.04-arm) (push) Waiting to run
Test / test (1.24, ubuntu-latest) (push) Waiting to run
Test / test (1.24, windows-latest) (push) Waiting to run
Test / test (1.25, macos-15-intel) (push) Waiting to run
Test / test (1.25, macos-latest) (push) Waiting to run
Test / test (1.25, ubuntu-24.04-arm) (push) Waiting to run
Test / test (1.25, ubuntu-latest) (push) Waiting to run
Test / test (1.25, windows-latest) (push) Waiting to run
Trigger CMFA Update / trigger-CMFA-update (push) Waiting to run
78 lines
2.2 KiB
Go
78 lines
2.2 KiB
Go
package proxydialer
|
|
|
|
import (
|
|
"context"
|
|
"fmt"
|
|
"net"
|
|
"net/netip"
|
|
"strings"
|
|
|
|
N "github.com/metacubex/mihomo/common/net"
|
|
C "github.com/metacubex/mihomo/constant"
|
|
"github.com/metacubex/mihomo/tunnel"
|
|
"github.com/metacubex/mihomo/tunnel/statistic"
|
|
)
|
|
|
|
type proxyDialer struct {
|
|
proxy C.ProxyAdapter
|
|
dialer C.Dialer
|
|
statistic bool
|
|
}
|
|
|
|
func New(proxy C.ProxyAdapter, dialer C.Dialer, statistic bool) C.Dialer {
|
|
return proxyDialer{proxy: proxy, dialer: dialer, statistic: statistic}
|
|
}
|
|
|
|
func NewByName(proxyName string, dialer C.Dialer) (C.Dialer, error) {
|
|
proxies := tunnel.Proxies()
|
|
if proxy, ok := proxies[proxyName]; ok {
|
|
return New(proxy, dialer, true), nil
|
|
}
|
|
return nil, fmt.Errorf("proxyName[%s] not found", proxyName)
|
|
}
|
|
|
|
func (p proxyDialer) DialContext(ctx context.Context, network, address string) (net.Conn, error) {
|
|
currentMeta := &C.Metadata{Type: C.INNER}
|
|
if err := currentMeta.SetRemoteAddress(address); err != nil {
|
|
return nil, err
|
|
}
|
|
if strings.Contains(network, "udp") { // using in wireguard outbound
|
|
pc, err := p.listenPacket(ctx, currentMeta)
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
if !currentMeta.Resolved() { // should not happen, maybe by a wrongly implemented proxy, but we can handle this (:
|
|
err = pc.ResolveUDP(ctx, currentMeta)
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
}
|
|
return N.NewBindPacketConn(pc, currentMeta.UDPAddr()), nil
|
|
}
|
|
conn, err := p.proxy.DialContext(ctx, currentMeta)
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
if p.statistic {
|
|
conn = statistic.NewTCPTracker(conn, statistic.DefaultManager, currentMeta, nil, 0, 0, false)
|
|
}
|
|
return conn, err
|
|
}
|
|
|
|
func (p proxyDialer) ListenPacket(ctx context.Context, network, address string, rAddrPort netip.AddrPort) (net.PacketConn, error) {
|
|
currentMeta := &C.Metadata{Type: C.INNER, DstIP: rAddrPort.Addr(), DstPort: rAddrPort.Port()}
|
|
return p.listenPacket(ctx, currentMeta)
|
|
}
|
|
|
|
func (p proxyDialer) listenPacket(ctx context.Context, currentMeta *C.Metadata) (C.PacketConn, error) {
|
|
currentMeta.NetWork = C.UDP
|
|
pc, err := p.proxy.ListenPacketContext(ctx, currentMeta)
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
if p.statistic {
|
|
pc = statistic.NewUDPTracker(pc, statistic.DefaultManager, currentMeta, nil, 0, 0, false)
|
|
}
|
|
return pc, nil
|
|
}
|