From d9a2a3b7d29b8a5b271c893a86ef09e1e9d57ae8 Mon Sep 17 00:00:00 2001 From: MaxFan Date: Sun, 17 May 2026 19:34:10 +0330 Subject: [PATCH] Prepare release v1.2.28 Co-authored-by: Cursor --- AppTunnel/AppTunnel.csproj | 6 +-- .../TrafficRouterService.RouteManagement.cs | 35 +++++++++++-- AppTunnel/Views/HelpTabView.xaml | 17 +++++-- CHANGELOG.md | 12 +++++ README.fa.md | 47 +++++++++++++++++ README.md | 51 ++++++++++++++++++- 6 files changed, 157 insertions(+), 11 deletions(-) diff --git a/AppTunnel/AppTunnel.csproj b/AppTunnel/AppTunnel.csproj index afd4a94..630dfc6 100644 --- a/AppTunnel/AppTunnel.csproj +++ b/AppTunnel/AppTunnel.csproj @@ -21,9 +21,9 @@ GPL-3.0-or-later fa-IR - 1.2.27 - 1.2.27.0 - 1.2.27.0 + 1.2.28 + 1.2.28.0 + 1.2.28.0 diff --git a/AppTunnel/Services/TrafficRouterService.RouteManagement.cs b/AppTunnel/Services/TrafficRouterService.RouteManagement.cs index 8b3dd2f..f2bda73 100644 --- a/AppTunnel/Services/TrafficRouterService.RouteManagement.cs +++ b/AppTunnel/Services/TrafficRouterService.RouteManagement.cs @@ -5,6 +5,8 @@ namespace AppTunnel.Services; public partial class TrafficRouterService { + private bool _vpnServerPhysicalRouteAdded; + public bool IsFullRouteEnabled => _fullRouteEnabled; public bool SetFullRouteEnabled(bool enabled) @@ -17,9 +19,19 @@ public partial class TrafficRouterService if (!AddVpnServerPhysicalRoute()) Logger.Warning("[FULL-ROUTE] Could not pin VPN server to the physical gateway; enabling full-route may fail."); - if (!TryRunRouteCommand($"add 0.0.0.0 mask 0.0.0.0 0.0.0.0 IF {_vpnInterfaceIndex} METRIC 1", out var stderr)) + RemoveFullRouteDefault(); + var gateway = GetVpnRouteGateway(); + var added = TryRunRouteCommand($"add 0.0.0.0 mask 0.0.0.0 {gateway} IF {_vpnInterfaceIndex} METRIC 1", out var stderr); + if (!added && gateway != "0.0.0.0") + { + Logger.Warning($"[FULL-ROUTE] Failed to add VPN default route via {gateway}; retrying on-link gateway. stderr={stderr.Trim()}"); + added = TryRunRouteCommand($"add 0.0.0.0 mask 0.0.0.0 0.0.0.0 IF {_vpnInterfaceIndex} METRIC 1", out stderr); + } + + if (!added) { Logger.Warning($"[FULL-ROUTE] Failed to add VPN default route: {stderr}"); + RemoveVpnServerPhysicalRoute(); return false; } @@ -32,6 +44,7 @@ public partial class TrafficRouterService RemoveExcludedDirectRoutes(); RemoveFullRouteDefault(); + RemoveVpnServerPhysicalRoute(); _fullRouteEnabled = false; MarkPolicyTransitionGrace(TimeSpan.FromSeconds(25)); CleanupRoutesForCurrentMode(dropStaleNat: true); @@ -42,15 +55,28 @@ public partial class TrafficRouterService private bool AddVpnServerPhysicalRoute() { + _vpnServerPhysicalRouteAdded = false; if (string.IsNullOrWhiteSpace(_vpnServerIp) || _vpnServerIp == "0.0.0.0") return false; if (string.IsNullOrWhiteSpace(_physicalGatewayIp) || _physicalInterfaceIndex <= 0) return false; TryRunRouteCommand($"delete {_vpnServerIp}", out _); - return TryRunRouteCommand( + var added = TryRunRouteCommand( $"add {_vpnServerIp} mask 255.255.255.255 {_physicalGatewayIp} IF {_physicalInterfaceIndex} METRIC 1", out _); + _vpnServerPhysicalRouteAdded = added; + return added; + } + + private void RemoveVpnServerPhysicalRoute() + { + if (!_vpnServerPhysicalRouteAdded) + return; + + if (!string.IsNullOrWhiteSpace(_vpnServerIp) && _vpnServerIp != "0.0.0.0") + TryRunRouteCommand($"delete {_vpnServerIp}", out _); + _vpnServerPhysicalRouteAdded = false; } private void RemoveFullRouteDefault() @@ -59,6 +85,9 @@ public partial class TrafficRouterService RemoveDefaultRouteOnVpn(); } + private string GetVpnRouteGateway() + => string.IsNullOrWhiteSpace(_vpnGatewayIp) ? "0.0.0.0" : _vpnGatewayIp; + /// /// Remove default routes (0.0.0.0/0) on the VPN interface so only /// explicitly added /32 host routes use the tunnel. Without this, @@ -357,7 +386,7 @@ public partial class TrafficRouterService /// private bool TryAddRouteViaCommandLine(IPAddress dstIp) { - var gateway = string.IsNullOrWhiteSpace(_vpnGatewayIp) ? "0.0.0.0" : _vpnGatewayIp; + var gateway = GetVpnRouteGateway(); var ok = TryRunRouteCommand($"add {dstIp} mask 255.255.255.255 {gateway} IF {_vpnInterfaceIndex} METRIC 1", out var stderr); if (!ok && Interlocked.Read(ref _statRoutesFailed) <= 10) Logger.Warning($"[ROUTE!] route.exe add {dstIp} via {gateway} stderr='{stderr.Trim()}'"); diff --git a/AppTunnel/Views/HelpTabView.xaml b/AppTunnel/Views/HelpTabView.xaml index 840446e..987f4b9 100644 --- a/AppTunnel/Views/HelpTabView.xaml +++ b/AppTunnel/Views/HelpTabView.xaml @@ -157,7 +157,7 @@ - @@ -222,6 +222,17 @@ Foreground="{StaticResource TextSecondaryBrush}" Margin="0,4,0,10"/> + + + -پروکسی داخلی روی 127.0.0.1 اجرا می‌شود. پورت را قبل از اتصال انتخاب کنید؛ پورت‌های سیستم، رزرو و پورت‌های رایج توسعه محدود شده‌اند. +پروکسی داخلی روی 127.0.0.1 اجرا می‌شود و برای ابزارهایی است که آدرس پراکسی محلی می‌خواهند. پورت را قبل از اتصال انتخاب کنید؛ پورت‌های سیستم، رزرو و پورت‌های رایج توسعه محدود شده‌اند. - diff --git a/CHANGELOG.md b/CHANGELOG.md index 8ebb3e3..18d1abf 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -6,6 +6,18 @@ ### فارسی +## 1.2.28 - 2026-05-17 + +### English + +- Fixed Full Route default-route installation by preferring the VPN gateway, retrying with an on-link gateway when needed, and cleaning up the pinned physical route to the tunnel server when Full Route is disabled. +- Updated English/Persian README and in-app Help content for the new SOCKS/Proxy profile flow, connection types, routing notes, local data, and troubleshooting guidance. + +### فارسی + +- نصب default route در حالت Full Route اصلاح شد؛ ابتدا gateway تونل استفاده می‌شود، در صورت نیاز با gateway روی‌لینک دوباره تلاش می‌شود، و route فیزیکی ثابت‌شده برای سرور تونل هنگام خاموش شدن Full Route پاک‌سازی می‌شود. +- README فارسی/انگلیسی و محتوای راهنمای داخل برنامه برای جریان جدید SOCKS/Proxy، نوع‌های اتصال، نکته‌های مسیر، داده‌های محلی و عیب‌یابی به‌روز شد. + ## 1.2.27 - 2026-05-17 ### English diff --git a/README.fa.md b/README.fa.md index 289adfd..ccd85c8 100644 --- a/README.fa.md +++ b/README.fa.md @@ -14,22 +14,69 @@ - Split tunneling بر اساس برنامه‌های انتخاب‌شده در ویندوز - حالت Full-route برای تونل کردن کل سیستم +- پشتیبانی از پروفایل‌های L2TP/IPsec ویندوز - پشتیبانی از جریان‌های V2Ray بر پایه Xray-core و sing-box +- پشتیبانی از پروفایل‌های اختصاصی SOCKS5/HTTP Proxy با سرور، پورت، نام کاربری و رمز عبور جداگانه - پشتیبانی از OpenVPN Community با فایل‌های `.ovpn` برای Split tunneling برنامه‌های انتخاب‌شده - پروکسی SOCKS5 محلی روی `127.0.0.1` برای ابزارهایی که تنظیم پروکسی داخلی دارند - تغییر مسیر DNS، مسدودسازی IPv6، محافظ نشت، عیب‌یابی route و تاریخچه مصرف تونل +- مدیریت چند پروفایل، کپی/ویرایش کانفیگ‌ها، تست سرور، تشخیص IP خروجی و اعلان بروزرسانی - رابط کاربری فارسی‌محور برای ویندوز +## شروع سریع + +1. آخرین فایل standalone را از بخش GitHub Releases دانلود کنید. +2. برنامه را با دسترسی Administrator اجرا کنید؛ قابلیت‌های تغییر مسیر، WinDivert و مدیریت ترافیک به سطح دسترسی بالا نیاز دارند. +3. از تب اتصال، یک کانفیگ جدید بسازید یا کانفیگ موجود را انتخاب کنید. +4. نوع اتصال را انتخاب کنید: L2TP/IPsec، V2Ray/Xray، SOCKS5/HTTP Proxy یا OpenVPN. +5. قبل از اتصال، تست سرور را اجرا کنید و سپس برنامه‌هایی را که باید از تونل عبور کنند در تب برنامه‌ها فعال کنید. +6. در صورت نیاز، مقصدهای لزومی یا استثنا را اضافه کنید و بعد از اتصال کارت سلامت ترافیک، DNS، IPv6 و Route را بررسی کنید. + +## انواع اتصال + +### L2TP/IPsec + +برای اتصال‌های L2TP/IPsec، آدرس سرور، نام کاربری، رمز عبور و Pre-Shared Key را وارد کنید. TunnelX اتصال ویندوز را ایجاد می‌کند و سپس مسیرها را بر اساس حالت انتخابی یا Full-route مدیریت می‌کند. + +### V2Ray / Xray + +لینک یا کانفیگ V2Ray/Xray را در پروفایل وارد کنید. برنامه برای کانفیگ‌های معمول از sing-box استفاده می‌کند و برای کانفیگ‌هایی که به قابلیت‌های خاص Xray مثل xhttp نیاز دارند، Xray-core را انتخاب می‌کند. + +### SOCKS5/HTTP Proxy + +اگر از پراکسی آماده استفاده می‌کنید، نوع پروفایل SOCKS5/HTTP Proxy را انتخاب کنید و سرور، پورت و در صورت نیاز نام کاربری و رمز عبور را وارد کنید. این حالت برای عبور برنامه‌های انتخاب‌شده از یک پراکسی خارجی مناسب است و با پراکسی محلی `127.0.0.1` تفاوت دارد. + ## پشتیبانی از OpenVPN TunnelX می‌تواند نسخه نصب‌شده OpenVPN Community و فایل انتخابی `.ovpn` کاربر را اجرا کند و سپس سیاست Split tunneling خودش را اعمال کند؛ یعنی فقط برنامه‌ها و مقصدهای انتخاب‌شده از تونل OpenVPN عبور می‌کنند. OpenVPN همراه TunnelX توزیع نمی‌شود. برای این حالت باید OpenVPN Community را جداگانه نصب کنید، فایل `.ovpn` را در TunnelX انتخاب کنید و در صورت نیاز نام کاربری و رمز عبور OpenVPN را داخل برنامه وارد کنید. نصب بودن OpenVPN Connect به‌تنهایی برای این حالت کافی نیست، چون آن برنامه مسیرها و DNS را با کلاینت خودش مدیریت می‌کند. +TunnelX برای سازگاری با Split tunneling، تنظیمات مسیر و DNS تحمیلی فایل `.ovpn` را کنترل می‌کند و در صورت تغییر IP تونل، gateway، interface یا مقصد ریموت هنگام reconnect، مسیر‌دهی داخلی خودش را دوباره راه‌اندازی می‌کند. + ## نکته‌های مسیر و دامنه قانون‌های Include و Exclude هم خود دامنه واردشده و هم زیردامنه‌های آن را پوشش می‌دهند. برای نمونه، افزودن `githubusercontent.com` پس از resolve شدن DNS شامل `raw.githubusercontent.com` هم می‌شود. اگر یک کلاینت HTTPS در مرحله بررسی certificate revocation خطا داد، ممکن است میزبان‌های OCSP/CRL آن از مسیر انتخابی قابل دسترسی نباشند؛ در این حالت خود برنامه دانلودکننده یا دامنه‌های revocation مربوطه را هم در لیست لزومی قرار دهید. +- مقصدهای استثناشده حتی برای برنامه‌های انتخاب‌شده مستقیم می‌مانند. +- مقصدهای لزومی حتی اگر برنامه مربوطه انتخاب نشده باشد از تونل عبور می‌کنند. +- برای برنامه‌های Store/MSIX، WebView2 یا برنامه‌های چندپردازشی، برنامه را باز نگه دارید و فهرست برنامه‌ها را دوباره بارگذاری کنید. +- اگر Full-route روشن باشد، کل ترافیک سیستم از تونل عبور می‌کند و قانون‌های مستقیم/استثنا همچنان برای نگه داشتن مقصدهای خاص روی مسیر عادی کاربرد دارند. + +## تنظیمات و داده‌های محلی + +پروفایل‌ها، برنامه‌های انتخاب‌شده، مقصدهای لزومی/استثنا، تاریخچه اتصال و لاگ‌ها روی دستگاه کاربر نگهداری می‌شوند و معمولاً در مسیر `%LOCALAPPDATA%\TunnelX` یا کنار برنامه قرار می‌گیرند. TunnelX عمداً تحلیل آماری یا telemetry برای نگهدارنده ارسال نمی‌کند. + +لاگ‌ها ممکن است شامل نام پردازش‌ها، نام دامنه‌ها، آدرس‌های IP، پورت‌ها و وضعیت اتصال باشند. قبل از ارسال عمومی لاگ در GitHub Issues، اطلاعات حساس مثل آدرس سرور خصوصی، کلیدها، UUID، رمزها و endpointهای شخصی را حذف کنید. + +## عیب‌یابی سریع + +- اگر اتصال برقرار نمی‌شود، اجرای برنامه با دسترسی Administrator، فایروال، درستی کانفیگ، پورت‌های پراکسی و نصب بودن پیش‌نیازهای مربوط به همان نوع اتصال را بررسی کنید. +- اگر ترافیک یک برنامه از تونل عبور نمی‌کند، برنامه را در تب برنامه‌ها فعال کنید، برنامه را باز نگه دارید و فهرست برنامه‌ها را دوباره بارگذاری کنید. +- اگر فقط یک سایت یا دامنه باید از تونل عبور کند، آن را به مقصدهای لزومی اضافه کنید؛ اگر باید مستقیم بماند، آن را به استثناها اضافه کنید. +- اگر خطای DNS یا IPv6 می‌بینید، کارت سلامت بعد از اتصال را بررسی کنید و در صورت نیاز یک‌بار قطع و وصل کنید تا مسیرها و قانون‌های DNS دوباره ساخته شوند. +- اگر از OpenVPN استفاده می‌کنید و اتصال طولانی می‌شود، فایل `.ovpn`، نام کاربری/رمز و نصب بودن OpenVPN Community را بررسی کنید. + ## تصاویر برنامه | داشبورد اتصال | تنظیم پروفایل و سرور | diff --git a/README.md b/README.md index ed25e1e..eead739 100644 --- a/README.md +++ b/README.md @@ -8,22 +8,69 @@ TunnelX is a free and open-source Windows split-tunneling client built by **MaxF - App-based split tunneling for selected Windows processes - Full-route mode for whole-system tunneling +- Windows L2TP/IPsec profile support - Xray-core / sing-box based V2Ray workflows +- Dedicated SOCKS5/HTTP Proxy profiles with separate server, port, username, and password fields - OpenVPN Community support via user-provided `.ovpn` files for app-based split tunneling - Local SOCKS5 proxy for tools that need `127.0.0.1` - DNS redirect, IPv6 blocking, leak guard, route diagnostics, and traffic history +- Multiple profiles, duplicate/edit flows, server tests, public exit IP detection, and release update checks - Persian-first Windows desktop UI +## Quick Start + +1. Download the latest standalone release from GitHub Releases. +2. Run TunnelX as Administrator. Route management, WinDivert, and packet interception require elevated privileges. +3. Create a new profile or select an existing profile from the connection tab. +4. Choose the connection type: L2TP/IPsec, V2Ray/Xray, SOCKS5/HTTP Proxy, or OpenVPN. +5. Test the server, then enable the Windows apps that should use the tunnel. +6. Add include or exclude destinations when needed, connect, and check the traffic health cards for DNS, IPv6, leaks, and route status. + +## Connection Types + +### L2TP/IPsec + +Enter the server address, username, password, and pre-shared key. TunnelX creates the Windows VPN connection and manages routes according to the selected-app policy or full-route mode. + +### V2Ray / Xray + +Paste a V2Ray/Xray link or JSON config into the profile. TunnelX uses sing-box for regular configs and switches to Xray-core for configs that require Xray-specific behavior such as `xhttp`. + +### SOCKS5/HTTP Proxy + +Use a SOCKS5/HTTP Proxy profile when you already have an external proxy endpoint. Enter the proxy server, port, and optional credentials. This is different from the local `127.0.0.1` SOCKS5 proxy, which is exposed after connection for tools that need a local proxy address. + ## OpenVPN TunnelX can run an installed **OpenVPN Community** `openvpn.exe` with a user-selected `.ovpn` profile, then apply its own split-tunneling policy so only selected apps and included destinations use the OpenVPN tunnel. OpenVPN is not bundled with TunnelX. Install OpenVPN Community separately, select the `.ovpn` file in TunnelX, and enter the OpenVPN username/password if the server requires credentials. OpenVPN Connect alone is not enough for this mode because it manages routes and DNS through its own client. +For split-tunnel compatibility, TunnelX prepares the OpenVPN config by controlling pushed route and DNS behavior. If OpenVPN reconnects and changes the tunnel IP, gateway, interface, or remote endpoint, TunnelX restarts its packet routing with the new values. + ## Routing Notes Destination include/exclude rules match both the entered domain and its subdomains. For example, adding `githubusercontent.com` also covers `raw.githubusercontent.com` after DNS resolves it. Some HTTPS clients may still fail during certificate revocation checks if their OCSP/CRL hosts are not reachable through the selected route; add the downloader app or the relevant revocation domains to the include list when that happens. +- Excluded destinations stay direct even for selected apps. +- Included destinations use the tunnel even when the matching app is not selected. +- For Store/MSIX, WebView2, or multi-process apps, keep the app open and refresh the app list. +- In full-route mode, the whole system uses the tunnel; direct/exclude rules are still useful for keeping specific destinations on the normal route. + +## Local Data and Logs + +Profiles, selected apps, include/exclude destinations, connection history, and logs are stored on the user's Windows machine, typically under `%LOCALAPPDATA%\TunnelX` or next to the app depending on the feature. TunnelX does not intentionally send analytics or telemetry to the maintainer. + +Logs can contain process names, hostnames, IP addresses, ports, and connection state. Before posting logs publicly, remove server credentials, UUIDs, private keys, private endpoints, and other sensitive data. + +## Troubleshooting + +- If connection fails, check Administrator privileges, firewall rules, config validity, proxy ports, and prerequisites for the selected connection type. +- If an app does not use the tunnel, enable it in the apps tab, keep it running, and refresh the app list. +- If only one site or domain should use the tunnel, add it to include destinations. If it should stay direct, add it to exclusions. +- If DNS or IPv6 status looks wrong, check the health cards after connection and reconnect once to rebuild routes and DNS rules. +- For OpenVPN connection delays, verify the `.ovpn` file, credentials, and OpenVPN Community installation. + ## Screenshots | Connection dashboard | Profile and server setup | @@ -36,9 +83,9 @@ Destination include/exclude rules match both the entered domain and its subdomai ## Download -Public downloads should be attached to GitHub Releases after release validation is complete: +Public downloads are published through GitHub Releases: -[GitHub project](https://github.com/MaxiFan/TunnelX) +[Download the latest release](https://github.com/MaxiFan/TunnelX/releases/latest) Release assets are built and uploaded by GitHub Actions. Each published standalone executable includes a `.sha256` checksum file, and the release notes link back to the workflow run that produced the artifact.