| 1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192 |
- package route
- import (
- "context"
- "net/netip"
- "strings"
- "github.com/sagernet/sing-box/adapter"
- "github.com/sagernet/sing-box/common/process"
- )
- type processCacheKey struct {
- Network string
- Source netip.AddrPort
- Destination netip.AddrPort
- }
- type processCacheEntry struct {
- result *adapter.ConnectionOwner
- err error
- }
- func (r *Router) findProcessInfoCached(ctx context.Context, network string, source netip.AddrPort, destination netip.AddrPort) (*adapter.ConnectionOwner, error) {
- key := processCacheKey{
- Network: network,
- Source: source,
- Destination: destination,
- }
- if entry, ok := r.processCache.Get(key); ok {
- return entry.result, entry.err
- }
- result, err := process.FindProcessInfo(r.processSearcher, ctx, network, source, destination)
- r.processCache.Add(key, processCacheEntry{result: result, err: err})
- return result, err
- }
- func (r *Router) searchProcessInfo(ctx context.Context, metadata *adapter.InboundContext) {
- if r.processSearcher == nil || metadata.ProcessInfo != nil || !r.isLocalSource(metadata.Source.Addr) {
- return
- }
- var originDestination netip.AddrPort
- if metadata.OriginDestination.IsValid() {
- originDestination = metadata.OriginDestination.AddrPort()
- } else if metadata.Destination.IsIP() {
- originDestination = metadata.Destination.AddrPort()
- }
- processInfo, err := r.findProcessInfoCached(ctx, metadata.Network, metadata.Source.AddrPort(), originDestination)
- if err != nil {
- r.logger.InfoContext(ctx, "failed to search process: ", err)
- return
- }
- metadata.ProcessInfo = processInfo
- if processInfo.ProcessPath != "" {
- if processInfo.UserName != "" {
- r.logger.InfoContext(ctx, "found process path: ", processInfo.ProcessPath, ", user: ", processInfo.UserName)
- } else if processInfo.UserId != -1 {
- r.logger.InfoContext(ctx, "found process path: ", processInfo.ProcessPath, ", user id: ", processInfo.UserId)
- } else {
- r.logger.InfoContext(ctx, "found process path: ", processInfo.ProcessPath)
- }
- return
- }
- if len(processInfo.AndroidPackageNames) > 0 {
- r.logger.InfoContext(ctx, "found package name: ", strings.Join(processInfo.AndroidPackageNames, ", "))
- return
- }
- if processInfo.UserId != -1 {
- if processInfo.UserName != "" {
- r.logger.InfoContext(ctx, "found user: ", processInfo.UserName)
- } else {
- r.logger.InfoContext(ctx, "found user id: ", processInfo.UserId)
- }
- }
- }
- func (r *Router) isLocalSource(source netip.Addr) bool {
- if !source.IsValid() {
- return false
- }
- source = source.Unmap()
- if source.IsLoopback() {
- return true
- }
- for _, netInterface := range r.network.InterfaceFinder().Interfaces() {
- for _, prefix := range netInterface.Addresses {
- if prefix.Addr().Unmap() == source {
- return true
- }
- }
- }
- return false
- }
|