| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118 |
- package fakeip
- import (
- "context"
- "net/netip"
- "github.com/sagernet/sing-box/adapter"
- E "github.com/sagernet/sing/common/exceptions"
- "github.com/sagernet/sing/common/logger"
- "github.com/sagernet/sing/service"
- )
- var _ adapter.FakeIPStore = (*Store)(nil)
- type Store struct {
- ctx context.Context
- logger logger.Logger
- inet4Range netip.Prefix
- inet6Range netip.Prefix
- storage adapter.FakeIPStorage
- inet4Current netip.Addr
- inet6Current netip.Addr
- }
- func NewStore(ctx context.Context, logger logger.Logger, inet4Range netip.Prefix, inet6Range netip.Prefix) *Store {
- return &Store{
- ctx: ctx,
- logger: logger,
- inet4Range: inet4Range,
- inet6Range: inet6Range,
- }
- }
- func (s *Store) Start() error {
- var storage adapter.FakeIPStorage
- cacheFile := service.FromContext[adapter.CacheFile](s.ctx)
- if cacheFile != nil && cacheFile.StoreFakeIP() {
- storage = cacheFile
- }
- if storage == nil {
- storage = NewMemoryStorage()
- }
- metadata := storage.FakeIPMetadata()
- if metadata != nil && metadata.Inet4Range == s.inet4Range && metadata.Inet6Range == s.inet6Range {
- s.inet4Current = metadata.Inet4Current
- s.inet6Current = metadata.Inet6Current
- } else {
- if s.inet4Range.IsValid() {
- s.inet4Current = s.inet4Range.Addr().Next().Next()
- }
- if s.inet6Range.IsValid() {
- s.inet6Current = s.inet6Range.Addr().Next().Next()
- }
- _ = storage.FakeIPReset()
- }
- s.storage = storage
- return nil
- }
- func (s *Store) Contains(address netip.Addr) bool {
- return s.inet4Range.Contains(address) || s.inet6Range.Contains(address)
- }
- func (s *Store) Close() error {
- if s.storage == nil {
- return nil
- }
- return s.storage.FakeIPSaveMetadata(&adapter.FakeIPMetadata{
- Inet4Range: s.inet4Range,
- Inet6Range: s.inet6Range,
- Inet4Current: s.inet4Current,
- Inet6Current: s.inet6Current,
- })
- }
- func (s *Store) Create(domain string, isIPv6 bool) (netip.Addr, error) {
- if address, loaded := s.storage.FakeIPLoadDomain(domain, isIPv6); loaded {
- return address, nil
- }
- var address netip.Addr
- if !isIPv6 {
- if !s.inet4Current.IsValid() {
- return netip.Addr{}, E.New("missing IPv4 fakeip address range")
- }
- nextAddress := s.inet4Current.Next()
- if !s.inet4Range.Contains(nextAddress) {
- nextAddress = s.inet4Range.Addr().Next().Next()
- }
- s.inet4Current = nextAddress
- address = nextAddress
- } else {
- if !s.inet6Current.IsValid() {
- return netip.Addr{}, E.New("missing IPv6 fakeip address range")
- }
- nextAddress := s.inet6Current.Next()
- if !s.inet6Range.Contains(nextAddress) {
- nextAddress = s.inet6Range.Addr().Next().Next()
- }
- s.inet6Current = nextAddress
- address = nextAddress
- }
- s.storage.FakeIPStoreAsync(address, domain, s.logger)
- s.storage.FakeIPSaveMetadataAsync(&adapter.FakeIPMetadata{
- Inet4Range: s.inet4Range,
- Inet6Range: s.inet6Range,
- Inet4Current: s.inet4Current,
- Inet6Current: s.inet6Current,
- })
- return address, nil
- }
- func (s *Store) Lookup(address netip.Addr) (string, bool) {
- return s.storage.FakeIPLoad(address)
- }
- func (s *Store) Reset() error {
- return s.storage.FakeIPReset()
- }
|