• VPN+Psiphon+ProxyBridge & Psiphon+ProxyBridge+VPN now both work!

    From Marian@3:633/10 to All on Mon Dec 1 15:47:38 2025
    Hooray!

    VPN now works reliably first or last in the VPN+Psiphon+ProxyBridge
    or Psiphon+ProxyBridge+VPN encryption chain of events on Windows.

    I finally fixed a huge problem in that I could never (until now) get VPN to work *last* in the chain (i.e., psiphon + proxybridge + VPN) even as VPN worked fine *first* in the chain (i.e., VPN + psiphon + proxybridge).

    MULTIPLE problems needed to be identified:
    1. Windows TAP adapter race condition ("Waiting for TUN/TAP interface to come up")
    2. Psiphon SOCKS5 proxy lacks UDP ASSOCIATE
    3. TAP adapter DHCP failures -> APIPA fallback
    4. VPNGate server variability (static IP vs DHCP push)

    Now VPN works fine whether it's first or last in they encryption chain.

    MULTIPLE problems needed to be identified, but these were the main ones:
    1. Windows is too slow so we get "Waiting for TUN/TAP interface to come up"
    2. The Psiphon SOCKS5 proxy supports TCP ASSOCIATE but not UDP ASSOCIATE

    What took a while to identify was WHY both UDP & TCP OpenVPN configs failed (where the VPN error for TCP was DIFFERENT than the error for UDP configs).
    TCP: "Waiting for TUN/TAP interface to come up"
    UDP: AIPA fallback "Initialization Sequence Completed With Errors"

    What first needed to be modified in order for both TCP & UDP configs to
    work (whether or not VPN was first or last in the encryption chain) was
    each OpenVPN config file needed to tell OpenVPN.exe to employ adaptive commands to set up the TAP interface, and to wait longer before route injection occurs.
    # Adaptively choose how Windows OpenVPN configures the TAP adapter
    ip-win32 adaptive
    # Give Windows 10 seconds longer before route injection begins
    route-delay 10

    In addition to that TAP adapter setup race with route injection, there is
    no way around the fact that Psiphon's SOCKS5 proxy doesn't support UDP.

    So the Psiphon rules.txt file needed to be modified extensively.

    The rules.txt file had to be modified so that OpenVPN traffic
    was handled correctly depending on protocol type. Before, both
    TCP and UDP configs failed when VPN was placed last in the chain.

    Here are the key changes between version 1p7 & 2p0 rules.txt:
    a. Explicitly route OpenVPN.exe TCP traffic through Psiphon
    Rule added:
    openvpn.exe:*:443:TCP -> PROXY
    This ensures that TCP VPN configs are proxied through
    Psiphon's SOCKS5 tunnel.

    b. Explicitly allow OpenVPN.exe UDP traffic to bypass Psiphon
    Rule added:
    openvpn.exe:*:*:UDP -> DIRECT
    Because Psiphon's SOCKS5 proxy does not support UDP ASSOCIATE,
    UDP VPN configs must go direct to the server.

    c. Allow TAP/DHCP/DNS setup traffic to go DIRECT
    Rules added:
    svchost.exe:*:53:UDP -> DIRECT
    svchost.exe:*:67,68:UDP -> DIRECT
    system:*:*:UDP -> DIRECT
    These ensure that Windows can perform DNS lookups and DHCP
    lease negotiation for the TAP adapter without being blocked
    or forced through Psiphon.

    d. Block unwanted UDP traffic from browsers and apps
    Rules added such as:
    chrome.exe:*:443:UDP -> BLOCK
    firefox.exe:*:443:UDP -> BLOCK
    brave.exe:*:443:UDP -> BLOCK
    This prevents browsers from leaking QUIC/UDP traffic outside
    the encrypted chain.

    e. Maintain TCP direct access for system processes
    Rules like:
    svchost.exe:*:*:TCP -> DIRECT
    services.exe:*:*:TCP -> DIRECT
    system:*:*:TCP -> DIRECT
    These allow Windows core services to function normally while
    keeping user applications proxied.

    Here is the current status as of version 2p0 of the rules.txt file:
    1. TCP OpenVPN configs now work when VPN is last in the chain,
    because their traffic is correctly proxied through Psiphon.
    2. UDP OpenVPN configs now work when VPN is last in the chain,
    because their traffic bypasses Psiphon and goes direct.
    3. TAP adapter setup traffic (DNS, DHCP) is allowed direct, so
    Windows no longer fails with APIPA addresses.
    4. Browser UDP traffic (QUIC) is blocked, preventing leaks.

    The critical changes in rules.txt were:
    1. Split handling of OpenVPN.exe traffic: TCP -> PROXY, UDP -> DIRECT.
    2. Allow svchost/system UDP traffic direct for TAP setup.
    3. Block browser UDP traffic to prevent leaks.
    4. Keep system TCP traffic direct for stability.

    Together with the OpenVPN config additions
    (ip-win32 adaptive + route-delay 10), these rules fixed the
    longstanding problem which had prevented VPN from being used after ProxyBridge. Now VPN works reliably whether it is first or last in the encryption chain.

    Here is the version 2p0 of the rules.txt file to donate to the team.
    # C:\app\network\proxy\proxybridge\rules.txt v1p0 20251023
    # This is version 2p0
    # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # #
    # Load this into ProxyBridge using the pb.bat script.
    # Syntax: --rule <process>:<hosts>:<ports>:<protocol>:<action>
    # Rules are case insensitive, # indicates comments, blank lines ignored.
    # v1p1 20251023
    # Added useful examples of block, direct & proxy for others to benefit
    # Added usable inline comments (requires pb.bat v2p6 or higher to handle)
    # v1p2 20251023
    # Added usability explanations of dns complexity & QUIC/HTTPS3 issues.
    # Added UDP block to handle Brave using experimental protocols above.
    # v1p3 20251023
    # Added clarification that TCP & UDP rules are not overridden
    # v1p4 20251024
    # Added Tor SOCKS5 proxy server (in addition to Psiphon's)
    # v1p5 20251024
    # Note that Tor cannot proxy UDP, so I had to add specific rules for that.
    # v1p6 20251025
    # Added Chrome, Brave, Edge & FF browser rules due to phoning home.
    # v1p7 20251024
    # Fixed error that Psiphon doesn't support UDP ASSOCIATE
    # This is to avoid proxying UDP (Psiphon doesn't support UDP ASSOCIATE)
    # Cleaned up DNS section because DNS via proxy is enabled by default
    # v1p8 20251130
    # Added DIRECT rules for svchost.exe, route.exe, and system UDP.
    # So that TAP setup traffic bypasses ProxyBridge.
    # Tunnel traffic (openvpn.exe on TCP 443) still goes through Psiphon.
    # This separation allowed DHCP and ARP to succeed but Windows was slow
    # to set up the tunnel until I added two directives to TCP config files.
    # ip-win32 adaptive
    # route-delay = 10
    # Remaining issue:
    # Even with bypasses, Windows was slow to mark TAP up.
    # OpenVPN kept looping "Waiting for TUN/TAP interface to come up"
    # v1p9 20251201
    # Combined both TCP/UDP cases in a single rules.txt file by
    # explicitly allowing UDP traffic from OpenVPN to go DIRECT,
    # while still proxying TCP 443 through Psiphon
    # Now TCP tunnel traffic is proxied through Psiphon
    # While UDP tunnel traffic bypasses ProxyBridge (DIRECT)
    # And TAP setup traffic (DHCP, ARP, route injection) is always DIRECT so
    # OpenVPN can bring the interface up in time given ProxyBridge delays.
    # v2p0 20251201
    # The rules bypassed ProxyBridge, but the TAP adapter still failed DHCP.
    # Windows gave it a fallback 169.254.x.x address, so OpenVPN reported
    # "Completed With Errors." For UDP VPNGate configs to work, they must run
    # DIRECT without Psiphon, and the network must allow the TAP adapter
    # to obtain a proper 10.x.x.x lease from the VPN server.
    # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # #

    --proxy socks5://127.0.0.1:1080 # Psiphon local SOCKS5 listener
    # --proxy socks5://127.0.0.1:9150 # Tor Browser SOCKS5 listener (optional)

    # Applications that should always use the proxy
    --rule telegram.exe:*:*:TCP:PROXY
    --rule MemoryHogs.exe:*:*:TCP:PROXY
    --rule dialog.exe:*:*:TCP:PROXY

    # Block QUIC/HTTP3 globally
    --rule *:*:443:UDP:BLOCK

    # Brave rules
    --rule brave.exe:*:*:TCP:PROXY
    --rule brave.exe:*:443:UDP:BLOCK
    --rule BraveUpdate.exe:*:*:TCP:BLOCK
    --rule brave.exe:*:5228:TCP:BLOCK
    --rule brave.exe:*:53:UDP:BLOCK

    # Chromium rules
    --rule chrome.exe:*:*:TCP:PROXY
    --rule chrome.exe:*:443:UDP:BLOCK
    --rule chrome.exe:*:5228:TCP:BLOCK
    --rule chrome.exe:*:53:UDP:BLOCK

    # Firefox rules
    --rule firefox.exe:*:*:TCP:PROXY
    --rule firefox.exe:*:443:UDP:BLOCK

    # Block telemetry and unwanted processes
    --rule OneDrive.exe:*:*:TCP:BLOCK
    --rule CompatTelRunner.exe:*:*:TCP:BLOCK
    --rule SearchApp.exe:*:*:TCP:BLOCK

    # Core system processes bypass proxy
    --rule svchost.exe:*:*:TCP:DIRECT
    --rule services.exe:*:*:TCP:DIRECT
    --rule system:*:*:TCP:DIRECT

    # Utility
    --rule curl.exe:*:*:TCP:PROXY

    # DNS and TAP setup bypass
    --rule svchost.exe:*:53:UDP:DIRECT
    --rule svchost.exe:*:67,68:UDP:DIRECT
    --rule svchost.exe:*:*:UDP:DIRECT
    --rule system:*:*:UDP:DIRECT
    --rule route.exe:*:*:TCP:DIRECT
    --rule route.exe:*:*:UDP:DIRECT

    # OpenVPN rules
    --rule openvpn.exe:*:443:TCP:PROXY # TCP tunnel proxied through Psiphon
    --rule openvpn.exe:*:*:UDP:DIRECT # UDP tunnel bypasses ProxyBridge
    # NOTE: For UDP OpenVPN configs to work, they must run DIRECT without Psiphon,
    # and the network must allow the TAP adapter to obtain a proper 10.x.x.x lease.
    # Otherwise OpenVPN will report "Initialization Sequence Completed With Errors"
    # and the TAP adapter will fall back to a 169.254.x.x APIPA address.

    # Log level
    --verbose 3

    # end of C:\app\network\proxy\proxybridge\rules.txt


    @echo off
    REM ============================================================
    REM C:\app\network\proxy\proxybridge\pb.bat 20251022
    REM This is version 3p0 (WIP)
    REM ============================================================
    REM Runs FOSS ProxyBridge to proxy any desired Windows program
    REM <github.com/InterceptSuite/ProxyBridge/releases/tag/v2.0>
    REM Requires a proxy server (e.g., free Psiphon or Tor browser)
    REM <https://www.torproject.org/download/> anonymity
    REM <https://psiphon.ca/en/download-store.html> censorship
    REM ============================================================
    REM ProxyBridge hooks into the Windows networking stack to
    REM observe all TCP/UDP connections to decide to proxy, block,
    REM or to allow the connection to go direct to the Internet.
    REM ============================================================
    REM ProxyBridge has two flaws which are solved with this script:
    REM 1. ProxyBridge has no import/export capability for rules
    REM 2. ProxyBridge has no persistent file-logging capability
    REM ============================================================
    REM v1p0 20251022 15L
    REM Launches ProxyBridge CLI using Psiphon or Tor SOCKS5 proxy.
    REM Uses the CLI to apply rules for Brave, Chromium & stunnel.
    REM Brave is sending UDP/443 traffic directly bypassing the proxy.
    REM We can further disable QUIC in Brave?s settings (msedge also).
    REM chrome://flags/#enable-quic (set to disabled)
    REM Exits with control-C
    REM v1p1 20251022 22L
    REM Added process:hosts:ports:protocol:action format.
    REM EXAMPLE: --rule stunnel.exe:*:119,563:TCP:PROXY
    REM Test with curl https://icanhazip.com
    REM v1p2 20251022 39L
    REM Added "--dns-via-proxy" & "--verbose 3" flags.
    REM DNS is actually handled directly by svchost.exe apparently.
    REM v1p3 20251022 52L
    REM Added a prompt for UAC since ProxyBridges requires admin.
    REM v1p4 20251022 65L
    REM Added automatic external IP check via curl after launch.
    REM v1p5 20251022 108L
    REM Added logging of all output to with timestamped files.
    REM But exiting out of multiple consoles is inefficient.
    REM v1p6 20251022 115L
    REM Simplified: single console window, inline ProxyBridge run,
    REM Added a graceful quit with Ctrl+C, with logging intact.
    REM v1p7 20251022 94L
    REM Further simplified: one Ctrl+C stops ProxyBridge and exits,
    REM removed pause and post-run commands for clean quit.
    REM Cleaned up the formatting to remove blank lines.
    REM v1p8 20251022 107L
    REM Added cleanup section to ensure ProxyBridge is killed.
    REM v1p9 20251022 101L
    REM Simplified logging: one log file per run, no tmp clutter,
    REM Modified the flow so one Ctrl+C stops everything cleanly.
    REM v2p0 20251022 107L
    REM Corrected logging: live console + single log file,
    REM one Ctrl+C exits cleanly, cleanup guaranteed.
    REM v2p1 20251022 103L
    REM Live streaming fixed by having PowerShell read
    REM stdout/stderr in real time, mirrors to console
    REM and appends to one log file.
    REM v2p2 20251022 74L
    REM This became a mess so I started over with version 1p3
    REM Changed ProxyBridge launch to "start /wait" so one Ctrl+C
    REM stops ProxyBridge cleanly without the Y/N batch prompt.
    REM v2p3 20251022 92L (whew, got it working again by backtracking)
    REM Added timestamped log file with live console output.
    REM One console, one Ctrl+C to stop ProxyBridge.
    REM v2p4 20251022
    REM Added back UAC elevation block
    REM v2p5 20251023
    REM Moved rules to a rules.txt file for easier maintenance
    REM Added a safety check to ensure rules.txt exists
    REM Maintained logging and UAC elevation
    REM Preserved the single-console, Ctrl+C exit behavior
    REM PowerShell invocation uses %PBARGS% instead of a
    REM nonexistent ProxyBridge --config flag to break lines up
    REM v2p6 20251023
    REM Modified so that only one control-C is needed (sans YES)
    REM v2p7 20251023 146L
    REM Added usability of handling inline comments in rules.txt
    REM Added common examples of block/proxy/direct/port rules.
    REM This is to help others come up to speed faster than I did.
    REM Syntax: --rule <process>:<hosts>:<ports>:<protocol>:<action>
    REM --proxy socks5://127.0.0.1:1080 # Psiphon's SOCKS5 listener
    REM --proxy socks5://127.0.0.1:9150 # Tor's SOCKS5 listener
    REM --rule telegram.exe:*:*:TCP:PROXY # Example of proxy
    REM --rule OneDrive.exe:*:*:TCP:BLOCK # Example of block
    REM --rule brave.exe:*:443:UDP:DIRECT # Example of passthru
    REM --rule stunnel.exe:*:119,563:TCP:PROXY # Example of ports
    REM v2p8 20251024 161L
    REM Made the rules filespec a user-defined variable
    REM v2p9 20251025 151L
    REM Improved comments to make it easier for others to understand
    REM v3p0 20251026 WIP
    REM ============================================================
    REM REM This is the ultimate nested path being enabled here:
    REM OUT: binary -> proxifier -> proxy -> VPN -> ISP -> net
    REM BACK: net -> ISP -> VPN -> proxy -> proxifier -> binary
    REM ============================================================
    :: --- User-configurable rules file ---
    :: set RULESFILE=rules_psiphon.txt
    :: set RULESFILE=rules_tor.txt
    set RULESFILE=rules.txt

    :: Delayed expansion is required for building %PBARGS%
    :: %PBARGS% is needed because ProxyBridge has no --config option
    setlocal enabledelayedexpansion

    :: --- UAC Elevation Check ---
    net session >nul 2>&1
    if %errorLevel% neq 0 (
    echo Requesting Administrator privileges...
    powershell -Command "Start-Process '%~f0' -Verb RunAs"
    exit /b
    )
    :: --- End UAC Elevation Check ---

    :: --- Logging setup ---
    set "LOGDIR=C:\data\sys\log"
    if not exist "%LOGDIR%" md "%LOGDIR%" 2>nul
    for /f "tokens=1-4 delims=/ " %%a in ("%DATE%") do (
    set YYYY=%%d
    set MM=%%b
    set DD=%%c
    )
    for /f "tokens=1-3 delims=:." %%a in ("%TIME%") do (
    set HH=%%a
    set Min=%%b
    set Sec=%%c
    )
    if "%HH:~0,1%"==" " set HH=0%HH:~1,1%
    set LOGSTAMP=%YYYY%%MM%%DD%_%HH%%Min%%Sec%
    set "LOGFILE=%LOGDIR%\pb_%LOGSTAMP%.log"
    echo Logging to %LOGFILE%
    :: --- End logging setup ---

    cd /d C:\app\network\proxy\proxybridge
    if not exist "%RULESFILE%" (
    echo ERROR: %RULESFILE% not found in %CD%
    exit /b
    )

    :: In version 2p5, rules were moved to a rules.txt file
    set "PBARGS="
    for /f "usebackq delims=" %%A in ("%RULESFILE%") do (
    set "LINE=%%A"
    if not "!LINE!"=="" if /i not "!LINE:~0,1!"=="#" (
    rem Strip inline comments: take everything before first #
    for /f "tokens=1 delims=#" %%B in ("!LINE!") do (
    set "PBARGS=!PBARGS! %%B"
    )
    )
    )

    taskkill /im ProxyBridge_CLI.exe /f >nul 2>&1

    echo ProxyBridge starting... Press Ctrl+C to stop.

    :: Wrapped with cmd /c to avoid "Terminate batch job (Y/N)?" prompt.
    cmd /c powershell -NoLogo -NoProfile -Command "Set-Location '%CD%'; & '%CD%\ProxyBridge_CLI.exe' %PBARGS% | Tee-Object -File '%LOGFILE%'"

    echo ProxyBridge exited.
    endlocal
    :: end of C:\app\network\proxy\proxybridge\pb.bat

    @echo off
    REM This is v2p4 of C:\data\sys\batch\psiphon.bat
    REM v1p0 20250916
    REM Runs Psiphon SOCKS5 encrypted proxy
    REM Syncs WinINET & static WinHTTP proxy settings
    REM Sets AutoConfigURL and AutoDetect registry keys
    REM Syncs PAC from file:///C:/data/sys/batch/proxy.pac
    REM Runs Mongoose to serve PAC at http://127.0.0.1/proxy.pac
    REM PAC bypasses Gmail, Amazon, Copilot, etc.
    REM Routes other traffic via SOCKS 127.0.0.1:1080
    REM Limitation: WinHTTP can't use PAC or SOCKS
    REM WIP: Add Privoxy to bridge HTTP to SOCKS
    REM v1p1 20250916
    REM Added automatic PAC sync/apply after Psiphon launch
    REM v1p2 psiphon.bat version 1.2 20250916
    REM Added logging to proxy.log when PAC is triggered from psiphon
    REM v1p3 20250916
    REM Added optional pause for viewing output before closing
    REM v1p4 20250916
    REM Changed to never close parent cmd window and always pause at end
    REM v1p5 20250916
    REM Added self-elevation to request UAC if not already admin
    REM v1p6 20250916
    REM Added final PAC URL + Auto-Detect set to ensure persistence
    REM after Psiphon/proxy changes
    REM v1p7 20250917
    REM Added launch of mongoose.vbs to serve proxy.pac before PAC logic
    REM v1p8 20250917
    REM Reordered launch sequence: Mongoose now starts BEFORE Psiphon
    REM Added PAC availability check using curl
    REM Added 2-second wait after Mongoose launch to ensure readiness
    REM v1p9 20250917
    REM Error: PAC file not available. Aborting. Press any key to continue
    REM Increased delay from 2 to 4 to give Mongoose more time to bind & serve
    REM v2p0 20250917 (111 lines)
    REM Decreased delay back to 2 as it didn't make a difference
    REM Added echo message during Mongoose wait to indicate progress
    REM v2p1 20250917 (118 lines)
    REM Expanded Psiphon's reach to WinHTTP apps without compromising WinINET apps
    REM By adding Automatic Sync of WinINET to WinHTTP (e.g., for Windows Update)
    REM Transfers only the Psiphon-injected static HTTP/HTTPS proxy address
    REM Does not transfer PAC logic and SOCKS settings from WinInet to WinHTTP
    REM v2p2 20251101
    REM Had to back up due to unknown errors creeping in
    REM v2p3 20251103
    REM Added warning that WinHTTP apps (e.g., Windows update) do not use
    REM PAC/SOCKS and will and will connect direct unless polipo is used.
    REM v2p4 20251107
    REM Added improved final status summary output
    REM
    :: --- Elevate to admin if not already ---
    >nul 2>&1 net session
    if %errorlevel% neq 0 (
    echo Requesting administrative privileges...
    powershell -Command "Start-Process '%~f0' -Verb RunAs"
    exit /b
    )

    REM Launch Mongoose silently to serve proxy.pac
    cscript //nologo "C:\data\sys\batch\launchmongoose.vbs"

    REM Wait for Mongoose to initialize (added in v1.8)
    echo waiting for mongoose... (added in v2.0)
    timeout /t 2 /nobreak >nul

    REM Verify PAC file is available before proceeding (added in v1.8)
    curl --silent --fail http://127.0.0.1/proxy.pac >nul || (
    echo PAC file not available. Aborting.
    pause
    exit /b
    )

    REM Launch Psiphon in SOCKS mode
    start "" /D "C:\app\network\psiphon" psiphon3.exe -mode=socks

    REM Wait a few seconds for Psiphon to initialize
    timeout /t 5 /nobreak >nul

    REM Log that PAC is being run from psiphon
    echo [%DATE% %TIME%] pac.cmd triggered from psiphon.bat >> C:\data\sys\log\proxy.log

    REM Apply PAC logic automatically (silent mode)
    call "C:\data\sys\batch\pac.cmd" /silent

    REM Force PAC URL and Auto-Detect to desired values at the very end
    REM This ensures Psiphon or proxy sync cannot leave them unset
    reg add "HKCU\Software\Microsoft\Windows\CurrentVersion\Internet Settings" /v AutoConfigURL /t REG_SZ /d http://127.0.0.1/proxy.pac /f >nul
    reg add "HKCU\Software\Microsoft\Windows\CurrentVersion\Internet Settings" /v AutoDetect /t REG_DWORD /d 1 /f >nul

    REM Sync WinINET proxy settings into WinHTTP (added in v2.1)
    netsh winhttp import proxy source=ie

    REM Always pause so you can see output if run from a console
    echo ============================================
    echo Psiphon Proxy Final Status
    echo ============================================
    echo WinINET: PAC enabled at http://127.0.0.1/proxy.pac
    echo WinHTTP: Direct access (no proxy server)
    echo SOCKS: 127.0.0.1:1080
    echo PAC served locally via Mongoose at http://127.0.0.1/proxy.pac
    echo PAC Logic: Bypass Gmail, Amazon, Copilot
    echo Other traffic via SOCKS proxy
    echo Note: WinHTTP apps (e.g. Windows Update) do not use PAC/SOCKS
    echo WIP: Chain Privoxy OR ProxyBridge to tunnel WinHTTP via Psiphon SOCKS.
    echo (Tor SOCKS not required unless anonymity chaining is desired.)
    echo ============================================
    echo Press any key to close...
    pause >nul

    REM End batch without killing the shell
    exit /b

    REM end of C:\data\sys\batch\psiphon.bat

    @echo off
    REM v2p1 C:\data\sys\batch\psiphonstop.bat
    REM
    REM Run psiphonstop.bat to:
    REM 1. Check for any lingering processes (Psiphon or Mongoose).
    REM 2. Kill any lingering processes (Psiphon or Mongoose).
    REM 3. Reset WinINET and WinHTTP proxy settings.
    REM 4. Log the shutdown for traceability in mongoose & proxy logs.
    REM
    REM v1p0 20250819 (41 lines)
    REM As admin, it stops Psiphon GUI, Mongoose, and resets proxy settings
    REM Logs shutdown event to proxy.log and mongoose.log for lifecycle tracking
    REM v1p1 20250819 (46 lines)
    REM Added Psiphon GUI termination step (v1.1)
    REM Added [STOP] prefix to log entries for clarity (v1.1)
    REM v1p2 20250818 (56 lines)
    REM Added conditional checks for running processes before attempting kill/log
    REM Only logs shutdown events if process was found running
    REM v1p3 20250820 (68 lines)
    REM Fixed Registry Key Not Found error when run with nothing to do
    REM Fixed "reset" not a command error by removing the ampersand in the echo
    REM v1p4 20250920 (79 lines)
    REM Added better error checking to see if Psiphon or Mongoose are running
    REM Added a closer line in the console
    REM v1p5 20250920 (89 lines)
    REM Added better explanation of the registry changes in the console output
    REM v1p6 20250920 (108 lines)
    REM Set ProxyEnable to 0 so the system knows to bypass proxies (v1.6)
    REM Clear ProxyOverride if Psiphon used custom bypass rules (v1.6)
    REM Flush DNS and restart networking stack (v1.6)
    REM v1p7 20250920 (121 lines)
    REM Exported keys before deletion, just in case (v1.7)
    REM fully refresh network adaptor (optional) v1.7
    REM v1p8 20250920 (138 lines)
    REM Check for environment proxy settings (v1.8)
    REM add browser cache flush and settings reminder (v1.8)
    REM add summary log entry with system state (v1.8)
    REM Add a success beep or visual cue (v1.8)
    REM v1p9 20250920 (152 lines)
    REM Added version banner
    REM Log envvars (v1.9)
    REM Add browser-specific cleanup reminders (v1.9)
    REM v2p0 20250922 (163 lines)
    REM Added a timed wait of 2 seconds before skipping action (v2.0)
    REM v2p1 20250922 (217 lines)
    REM Added protection from when the PC reboots with psiphon running.
    REM Added winsock detection and remediation block which will
    REM skip live winsock resets when the adapter is offline,
    REM and then it will attempt a safe remediation when netsh reports
    REM Access is denied, and log outcomes.

    echo ----------------------------------------
    echo Psiphonstop.bat v1.9 - Proxy Reset Tool
    echo ----------------------------------------

    :: --- Elevate to admin if not already ---
    >nul 2>&1 net session
    if %errorlevel% neq 0 (
    echo Requesting administrative privileges...
    powershell -Command "Start-Process '%~f0' -Verb RunAs"
    exit /b
    )

    REM Check if Psiphon GUI is running (updated for better errors) v1p4
    tasklist /fi "imagename eq psiphon3.exe" | find /i "psiphon3.exe" >nul
    if %errorlevel%==0 (
    taskkill /f /im psiphon3.exe >nul 2>&1
    echo [%DATE% %TIME%] [STOP] Psiphon GUI terminated by psiphonstop.bat >> C:\data\sys\log\proxy.log
    ) else (
    echo [%DATE% %TIME%] [STOP] No Psiphon GUI process found >> C:\data\sys\log\proxy.log
    )

    REM Check if Mongoose is running (updated checks in v1.4)
    tasklist /fi "imagename eq mongoose.exe" | find /i "mongoose.exe" >nul
    if %errorlevel%==0 (
    taskkill /f /im mongoose.exe >nul 2>&1
    echo [%DATE% %TIME%] [STOP] Mongoose terminated by psiphonstop.bat >> C:\data\sys\batch\mongoose.log
    ) else (
    echo [%DATE% %TIME%] [STOP] No Mongoose process found >> C:\data\sys\batch\mongoose.log
    )

    REM Exported keys before deletion, just in case (v1.7)
    REM reg export "HKCU\Software\Microsoft\Windows\CurrentVersion\Internet Settings" C:\data\sys\log\proxy_before_reset.reg
    REM Added a timed wait of 2 seconds before skipping action (v2.0)
    echo File C:\data\sys\log\proxy_before_reset.reg already exists. Overwrite (Yes/No)?
    choice /c YN /n /t 2 /d N >nul
    if errorlevel 2 if not errorlevel 3 (
    echo The operation was canceled by the user.
    goto :skip_export
    )
    reg export "HKCU\Software\Microsoft\Windows\CurrentVersion\Internet Settings" C:\data\sys\log\proxy_before_reset.reg

    :skip_export

    REM Reset WinINET proxy settings
    echo Resetting WinINET proxy registry values...
    REM Fixed Registry Key Not Found error when run with nothing to do (v1.3)
    :: reg delete "HKCU\Software\Microsoft\Windows\CurrentVersion\Internet Settings" /v AutoConfigURL /f >nul
    reg delete "HKCU\Software\Microsoft\Windows\CurrentVersion\Internet Settings" /v AutoConfigURL /f 2>nul

    echo reg delete "HKCU\Software\Microsoft\Windows\CurrentVersion\Internet Settings" /v AutoConfigURL /f 2>nul

    reg add "HKCU\Software\Microsoft\Windows\CurrentVersion\Internet Settings" /v AutoDetect /t REG_DWORD /d 0 /f >nul

    echo reg add "HKCU\Software\Microsoft\Windows\CurrentVersion\Internet Settings" /v AutoDetect /t REG_DWORD /d 0 /f >nul

    :: reg delete "HKCU\Software\Microsoft\Windows\CurrentVersion\Internet Settings" /v ProxyServer /f >nul
    reg delete "HKCU\Software\Microsoft\Windows\CurrentVersion\Internet Settings" /v ProxyServer /f 2>nul
    echo reg delete "HKCU\Software\Microsoft\Windows\CurrentVersion\Internet Settings" /v ProxyServer /f 2>nul

    :: reg delete "HKCU\Software\Microsoft\Windows\CurrentVersion\Internet Settings" /v ProxyEnable /f >nul
    reg delete "HKCU\Software\Microsoft\Windows\CurrentVersion\Internet Settings" /v ProxyEnable /f 2>nul
    echo reg delete "HKCU\Software\Microsoft\Windows\CurrentVersion\Internet Settings" /v ProxyEnable /f 2>nul

    REM v1p6
    REM Deleting ProxyEnable and ProxyServer does not restore direct access.
    REM Set ProxyEnable to 0 so the system knows to bypass proxies (v1.6)
    REM Windows interprets missing values differently than explicitly set ones.
    REM Explicitly set ProxyEnable to 0 so the system knows to bypass proxies.
    REM Now Windows knows to use direct access, not ?no proxy server defined.?
    reg add "HKCU\Software\Microsoft\Windows\CurrentVersion\Internet Settings" /v ProxyEnable /t REG_DWORD /d 0 /f

    REM Clear ProxyOverride if Psiphon used custom bypass rules (v1.6)
    reg delete "HKCU\Software\Microsoft\Windows\CurrentVersion\Internet Settings" /v ProxyOverride /f

    REM Flush DNS and restart networking stack (v1.6)
    ipconfig /flushdns
    netsh int ip reset

    echo Registry operations completed with Proxy settings cleared or updated.

    REM Reset WinHTTP proxy settings
    netsh winhttp reset proxy

    REM Always log proxy reset regardless of process status
    echo [%DATE% %TIME%] [STOP] Proxy settings reset by psiphonstop.bat >> C:\data\sys\log\proxy.log

    REM Fixed "reset" unrecognized command error by removing ampersand (v1p3)
    :: echo Psiphon, proxy settings, and Mongoose have been logged & reset.
    echo "Psiphon, proxy settings and Mongoose have been logged and reset."

    REM Check for environment proxy settings (v1.8)
    set | findstr /i proxy
    REM Log envvars (v1.9)
    set | findstr /i proxy >> C:\data\sys\log\proxy_envvars.log

    :: If a sudden shutdown occurred while psiphon was running
    :: the adapter may be in a partially reset state, so be defensive
    :: If adapter is offline or disabled, skip live winsock reset, require reboot
    for /f "tokens=3 delims= " %%s in ('netsh interface show interface name^="Wi-Fi" ^| findstr /i /c:"Connect" /c:"State" 2^>nul') do set WIFI_STATE=%%s
    echo Adapter state: %WIFI_STATE%
    echo.

    if /i "%WIFI_STATE%"=="Disconnected" (
    echo Adapter offline, skipping live winsock reset. Reboot required to finish cleanup.
    echo [%DATE% %TIME%] [STOP] Adapter offline, winsock reset skipped >> C:\data\sys\log\proxy.log
    goto :finalize
    )
    if /i "%WIFI_STATE%"=="Disabled" (
    echo Adapter disabled, skipping live winsock reset. Reboot required to finish cleanup.
    echo [%DATE% %TIME%] [STOP] Adapter disabled, winsock reset skipped >> C:\data\sys\log\proxy.log
    goto :finalize
    )

    REM Attempt winsock reset with detection and a safe retry
    netsh winsock reset > C:\data\sys\log\winsock_reset_out.txt 2>&1
    findstr /i "Access is denied" C:\data\sys\log\winsock_reset_out.txt >nul
    if %errorlevel%==0 (
    echo Access denied on winsock reset, attempting non destructive remediation...
    echo [%DATE% %TIME%] [WARN] Winsock reset returned Access is denied >> C:\data\sys\log\proxy.log

    REM Try restarting WLAN service and toggling adapter admin state
    net stop WlanSvc >nul 2>&1
    timeout /t 2 /nobreak >nul
    net start WlanSvc >nul 2>&1
    netsh interface set interface "Wi-Fi" admin=disabled >nul 2>&1
    timeout /t 2 /nobreak >nul
    netsh interface set interface "Wi-Fi" admin=enabled >nul 2>&1
    timeout /t 2 /nobreak >nul

    REM Retry winsock reset once more
    netsh winsock reset > C:\data\sys\log\winsock_reset_retry_out.txt 2>&1
    findstr /i "Access is denied" C:\data\sys\log\winsock_reset_retry_out.txt >nul
    if %errorlevel%==0 (
    echo CRITICAL, winsock reset still failed, reboot required to complete cleanup.
    echo [%DATE% %TIME%] [CRITICAL] Winsock reset failed after remediation, reboot required >> C:\data\sys\log\proxy.log
    goto :finalize
    ) else (
    echo Winsock reset succeeded on retry.
    echo [%DATE% %TIME%] [STOP] Winsock reset succeeded on retry >> C:\data\sys\log\proxy.log
    )
    ) else (
    echo Winsock reset completed OK.
    echo [%DATE% %TIME%] [STOP] Winsock reset completed OK >> C:\data\sys\log\proxy.log
    )

    REM add browser cache flush and settings reminder
    echo Reminder: Disable any proxy/VPN browser extensions manually.
    echo Reminder: Clear browser cache or try Incognito mode if issues persist.

    REM Add browser-specific cleanup reminders (v1.9)
    echo Chrome: chrome://settings/system > disable ?Use proxy?
    echo Firefox: about:preferences > Network Settings > ?No proxy?

    REM add summary log entry with system state (v1.8)
    echo [%DATE% %TIME%] [STOP] Proxy teardown complete. System set to direct access. >> C:\data\sys\log\proxy.log

    REM Added a console output for closure (v1.4)
    echo [%DATE% %TIME%] Psiphonstop.bat completed. See logs for details.

    REM Add a success beep or visual cue (v1.8)
    echo Operation complete. System proxy is OFF.
    powershell -c "[console]::beep(1000,300)"

    pause

    :: end of C:\data\sys\batch\psiphonstop.bat

    /*
    proxy.pac C:\data\sys\batch\proxy.pac (20250902)
    file:///C:/data/sys/batch/proxy.pac
    http://127.0.0.1/proxy.pac
    This is version 1p4
    Bypass proxy for sites sensitive to tunneling or IP shifts:
    - Google services (search, mail, etc.)
    - Amazon (especially the Amazon Vine Voice program)
    - Specific Microsoft domains (Copilot)
    All other traffic routed through local SOCKS proxy at 127.0.0.1:1080
    - Including Windows Update

    Useful for split-tunnel setups where trusted domains go direct
    but everything else is encrypted via Psiphon SOCKS5 proxy.

    If needed, test PAC web access and fundamental logic with:
    - https://pactester.brdbnt.com/
    - https://github.com/termsl/WPADChecker
    - curl http://127.0.0.1/proxy.pac

    v1p0 20250902(added Amazon Vine Voice https://amazon.com/vine/about)
    v1p1 20250910(added Google Gmail but I need to add it to Thunderbird)
    v1p2 20250918(added Microsoft sites for practice adding domains)
    v1p3 20251016(removed Microsoft domains for Windows-Update reasons)
    v1p4 20251016(rewrote to eliminate Windows-Update altogether)
    */

    function FindProxyForURL(url, host) {
    // Bypass Gmail & Google
    if (shExpMatch(host, "*.google.com") ||
    shExpMatch(host, "*.gmail.com") ||
    shExpMatch(host, "mail.google.com")) {
    return "DIRECT";
    }

    // Bypass Amazon Vine
    if (shExpMatch(host, "*.amazon.com") ||
    shExpMatch(host, "amazon.com")) {
    return "DIRECT";
    }

    // Keep Copilot direct for stability
    if (shExpMatch(host, "*.copilot.microsoft.com")) {
    return "DIRECT";
    }

    // All other traffic, including Microsoft Update, Bing, etc. ? proxy
    return "SOCKS 127.0.0.1:1080";
    }


    @echo off
    REM C:\data\sys\batch\proxy.cmd 20250902
    REM This is version 2.2
    REM Proxy diagnostic & config tool for WinINET, WinHTTP, PAC
    REM C:\data\sys\batch\proxy.cmd v2.1 - 20250916
    REM Changes in v2.1 (20250916):
    REM Added conditional check before importing WinINET into WinHTTP
    REM to avoid overwriting existing settings unnecessarily
    REM Added PAC file existence check before setting PAC URL
    REM Updated pause prompts to clarify Enter, Spacebar, or any key works
    REM C:\data\sys\batch\proxy.cmd v2.2 - 20250916 (224 lines)
    REM Changed final exit to exit /b to avoid closing parent cmd window

    REM Usage:
    REM Win+R > proxy
    REM Win+R > proxy /help
    REM Win+R > proxy /sync
    REM Win+R > proxy http://url.pac
    REM Win+R > proxy /nopac
    REM Win+R > proxy /status
    REM Win+R > proxy /reset
    REM Win+R > proxy /silent
    REM Win+R > proxy /silent /sync

    REM Proxy types:
    REM Type 1: WinINET - IE, Edge, MS Office, most apps
    REM Type 2: WinHTTP - system services like Windows Update
    REM Type 3: PAC/AutoDetect - Chrome, Edge, Firefox (if set to use system proxy)

    REM Show usage
    if /i "%~1"=="/help" (
    echo Usage:
    echo proxy
    echo proxy /sync
    echo proxy http://...
    echo proxy /nopac
    echo proxy /status
    echo proxy /reset
    echo proxy /silent ...
    exit /b
    )

    REM Log command
    set LOG=C:\data\sys\log\proxy.log
    echo [%DATE% %TIME%] %cmdcmdline% >> %LOG%

    REM Begin scoped env
    setlocal

    set KEY="HKCU\Software\Microsoft\Windows\CurrentVersion\Internet Settings"

    REM Detect /silent flag
    if /i "%~1"=="/silent" (
    set SILENT=1
    shift
    )

    REM /reset flag
    if /i "%~1"=="/reset" (
    echo Reset proxy settings...
    reg delete %KEY% /v ProxyEnable /f >nul 2>&1
    reg delete %KEY% /v ProxyServer /f >nul 2>&1
    reg delete %KEY% /v AutoConfigURL /f >nul
    reg add %KEY% /v AutoDetect /t REG_DWORD /d 0 /f >nul
    netsh winhttp reset proxy >nul 2>&1
    echo Proxy settings cleared.
    goto SHOWCONFIG
    )

    REM /status flag
    if /i "%~1"=="/status" (
    echo Show proxy config...
    goto SHOWCONFIG
    )

    REM /sync flag
    if /i "%~1"=="/sync" (
    echo Sync WinINET into WinHTTP...
    REM Check if WinHTTP proxy is already set before importing
    for /f "tokens=1,* delims=:" %%A in ('netsh winhttp show proxy ^| findstr /R /C:"Proxy Server(s)"') do set curWinHTTP=%%B
    set curWinHTTP=%curWinHTTP:~1%
    if "%curWinHTTP%"=="" (
    netsh winhttp import proxy source=ie
    if errorlevel 1 (
    echo ERROR: Access denied. Run as admin.
    )
    echo Done.
    ) else (
    echo WinHTTP proxy already set, skipping import.
    )
    goto SHOWCONFIG
    )

    REM /nopac flag
    if /i "%~1"=="/nopac" (
    echo Disable PAC & Auto-Detect...
    reg delete %KEY% /v AutoConfigURL /f >nul 2>&1
    reg add %KEY% /v AutoDetect /t REG_DWORD /d 0 /f >nul
    echo PAC & Auto-Detect disabled.
    goto SHOWCONFIG
    )

    REM Set PAC URL
    if not "%~1"=="" (
    echo Set PAC URL: %~1
    REM PAC file existence check if URL is local file or localhost
    for /f "tokens=1 delims=:" %%P in ("%~1") do set PACPROTO=%%P
    if /i "%PACPROTO%"=="http" (
    REM If localhost PAC, check file existence
    echo %~1 | findstr /I "127.0.0.1" >nul
    if not errorlevel 1 (
    for /f "tokens=2 delims=:" %%H in ("%~1") do set PACPORTPATH=%%H
    REM Remove leading slashes
    set PACPORTPATH=%PACPORTPATH:/=%
    REM Adjust path if needed (user must ensure correct mapping)
    if not exist "C:\data\sys\pac\proxy.pac" (
    echo WARNING: PAC file not found at C:\data\sys\pac\proxy.pac
    )
    )
    )
    reg add %KEY% /v AutoConfigURL /t REG_SZ /d %~1 /f >nul
    reg add %KEY% /v AutoDetect /t REG_DWORD /d 1 /f >nul
    )

    REM Diagnostic output
    :SHOWCONFIG
    echo ============================================
    echo WINDOWS PROXY CONFIG CHECK
    REM Avoid slash to prevent parsing bug
    echo ============================================

    REM WinINET status
    echo.
    echo [1] WinINET
    for /f "tokens=2,* skip=2" %%A in ('reg query %KEY% /v ProxyEnable 2^>nul') do set ProxyEnable=%%B
    for /f "tokens=2,* skip=2" %%A in ('reg query %KEY% /v ProxyServer 2^>nul') do set ProxyServer=%%B
    if "%ProxyEnable%"=="0x1" (
    echo Proxy ENABLED
    echo Server: %ProxyServer%
    ) else (
    echo Proxy DISABLED
    )

    REM WinHTTP status
    echo.
    echo [2] WinHTTP
    for /f "tokens=1,* delims=:" %%A in ('netsh winhttp show proxy ^| findstr /R /C:"Proxy Server(s)"') do set curWinHTTP=%%B
    set curWinHTTP=%curWinHTTP:~1%
    if "%curWinHTTP%"=="" (
    echo No WinHTTP proxy - import from WinINET...
    netsh winhttp import proxy source=ie >nul 2>&1
    ) else (
    echo WinHTTP proxy already set
    )
    netsh winhttp show proxy

    REM PAC status
    echo.
    echo [3] PAC / AutoDetect
    for /f "tokens=2,* skip=2" %%A in ('reg query %KEY% /v AutoConfigURL 2^>nul') do set PACurl=%%B
    for /f "tokens=2,* skip=2" %%A in ('reg query %KEY% /v AutoDetect 2^>nul') do set AutoDetect=%%B
    if defined PACurl (
    echo PAC URL: %PACurl%
    ) else (
    echo No PAC URL
    )

    REM PAC logic summary
    if /i "%PACurl%"=="http://127.0.0.1/proxy.pac" (
    echo PAC logic: Bypass Gmail, Amazon, Copilot
    echo Other traffic via SOCKS proxy 127.0.0.1:1080
    )

    if "%AutoDetect%"=="0x1" (
    echo Auto-Detect ENABLED
    ) else (
    echo Auto-Detect DISABLED
    )

    echo.
    echo ============================================
    echo Proxy check complete
    echo ============================================

    endlocal

    REM Final pause unless /silent
    if not defined SILENT (
    echo.
    echo Press Enter, Spacebar, or any key to close...
    pause >nul
    )

    exit /b
    ::START: Win+R -> psiphon (uses App Paths registry key)
    :: |
    :: v
    ::psiphon.bat
    :: - Check if running as admin
    :: - If not, request UAC elevation and restart
    :: - Launch launchmongoose.vbs to start Mongoose HTTP server
    :: - Serve proxy.pac at http://127.0.0.1/proxy.pac
    :: - Wait 2 seconds for Mongoose to initialize
    :: - Verify PAC file is available using curl
    :: - If PAC file is not available, abort
    :: - Launch psiphon3.exe in SOCKS mode
    :: - Wait 5 seconds for Psiphon to initialize
    :: - Log that pac.cmd is being run
    :: - Call pac.cmd /silent
    :: |
    :: v
    :: pac.cmd
    :: - Log run
    :: - Run proxy.cmd /sync to align WinINET -> WinHTTP
    :: - Capture current PAC URL and Auto-Detect status
    :: - If missing or wrong, call proxy.cmd with PAC URL
    :: - Force set PAC URL and Auto-Detect in registry
    :: - Show final PAC and Auto-Detect status
    :: - Return to psiphon.bat
    :: - Force set PAC URL and Auto-Detect again (double guarantee)
    :: - Pause for user to see output
    :: - Exit without closing parent shell
    :: end of C:\data\sys\batch\proxy.cmd

    ' ============================================
    ' launchmongoose.vbs 20250916 version 1.0
    ' This is version 1p6
    ' ============================================
    ' Version History:
    ' 1p0 20250916 Initial silent launch
    ' 1p1 20250916 Added process check and logging
    ' 1p2 20250916 Fixed duplicate End If error
    ' 1p3 20250916 Added version header block, cleaned structure
    ' 1p4 20250916 Removed unconditional launch
    ' Now launches only if not running
    ' 1p5 20250916 Updated launch command to set working directory
    ' 1p6 20251030 Appended comments about Firefox setup
    ' ============================================
    ' Serves C:\data\sys\batch\proxy.pac as http & https
    ' Launch using: cscript //nologo launchmongoose.vbs
    ' Test using: curl http://127.0.0.1/proxy.pac
    ' Testing using: type mongoose.log
    ' Or just use: tasklist /fi "imagename eq mongoose.exe"
    ' Kill using: taskkill /f /im mongoose.exe
    ' Test this script: cscript //nologo "C:\data\sys\batch\launchmongoose.vbs"
    ' ==============================
    ' Added in version 1.1
    ' ==============================
    ' Features:
    ' - Skips launch if mongoose.exe is already running
    ' - Logs launch attempts to mongoose.log
    ' ==============================
    ' Fixed in version 1.2
    ' ==============================
    ' got rid of errors
    ' ==============================
    ' Improved in version 1.4
    ' ==============================
    ' Removed unconditional launch from version 1.0
    ' ==============================
    ' Improved in version 1.5
    ' ==============================
    ' Due to error: PAC file not available.
    ' Added explicit path to Mongoose launch
    ' WshShell.Run """C:\data\sys\batch\mongoose.exe"" -l http://127.0.0.1:80 -d C:\data\sys\batch", 0, False
    ' This ensures proxy.pac is served correctly regardless of current working directory
    ' ==============================

    Set WshShell = CreateObject("WScript.Shell")

    Set execCheck = WshShell.Exec("cmd /c tasklist /fi ""imagename eq mongoose.exe"" | find /i ""mongoose.exe""")
    If execCheck.StdOut.ReadAll = "" Then
    ' Mongoose is not running, launch silently
    WshShell.Run """C:\data\sys\batch\mongoose.exe"" -l http://127.0.0.1:80 -d C:\data\sys\batch", 0, False

    ' Log the launch
    WshShell.Run """cmd.exe"" /c echo [" & Date & " " & Time & "] Mongoose launched >> C:\data\sys\batch\mongoose.log", 0, False
    Else
    ' Mongoose is already running, skip launch
    WshShell.Run """cmd.exe"" /c echo [" & Date & " " & Time & "] Mongoose already running >> C:\data\sys\batch\mongoose.log", 0, False
    End If

    ' Tutorial:
    ' How to Load a PAC File Directly from Disk in Firefox
    ' (without needing a web server such as "mongoose" to serve it)
    '
    ' Firefox is one of the few browsers that allows PAC files to be loaded
    ' directly from disk using a typical file:/// URL instead of a web server.
    '
    ' 1. Firefox:Tools > Settings > Network settings > [Settings...]
    ' 2. In the "Connection Settings" dialog
    ' Select "Automatic proxy configuration URL"
    ' 3. Paste the path to your PAC file, e.g.,
    ' file:///C:/app/network/proxy/proxy.pac
    ' 4. Press [OK] to save
    '
    ' This method works on Windows, Linux, and macOS.
    ' Just adjust the file:/// path format for your operating system.
    ' A. LINUX: file:///home/username/proxy/proxy.pac
    ' B. macOS: file:///Users/username/proxy/proxy.pac
    ' C. Windows: file:///C:/Users/username/proxy/proxy.pac
    '
    ' After setting Firefox to read the PAC file as shown above, we can then test
    ' by visiting about:networking#dns (set "Autorefresh every 3 seconds" & then
    ' we can visit a site that should go through the proxy to watch what happens.
    '
    ' We can also check our IP on a site which reports what it sees in Firefox:
    ' <https://ifconfig.me>
    ' <https://ipleak.net>
    ' <https://icanhazip.com>
    '
    ' Probably better though to check using a dedicated proxy testing site which
    ' can detect whether we're behind a proxy & sometimes even show the type.
    ' <https://www.whatismyproxy.com/>
    ' <https://browserleaks.com/proxy>
    ' <https://www.lagado.com/tools/proxy-test>
    '
    ' If we want to test outside the browser, we can use curl with one of the PAC
    ' testers above or we can manually specify the proxy in the curl command.
    ' C:\> curl --proxy socks5h://127.0.0.1:1080 https://ifconfig.me
    ' If we only configured the PAC file inside Firefox, then only Firefox will
    ' follow the specified PAC (Proxy Auto Config) rules.
    '
    ' Not curl.
    '
    ' Note that if we are configuring the proxy PAC file system-wide in Windows,
    ' we'd likely need to serve it over HTTP (e.g., with Mongoose). In that case,
    ' we'd set Firefox to "Use system proxy settings" instead of the filespec.
    '
    ' But for just Firefox alone, the file:/// approach works just fine.
    '
    ' Below is an example PAC file that I use for my specific needs, which I've
    ' added comments to so that anyone else can pick it up for their own re-use.
    '
    ' ---< cut here for proxy.pac >---
    ' /*
    ' proxy.pac C:\app\network\proxy\proxy.pac (20250902)
    ' file:///C:/app/network/proxy/proxy.pac (for Firefox)
    ' This is version 1.4
    ' Selectively bypass proxy for sites sensitive to IP shifts:
    ' - Google services (search, mail, etc.)
    ' - Amazon (especially the Amazon Vine Voice program)
    ' - Specific Microsoft domains (Copilot)
    ' All other traffic routed through local SOCKS proxy at 127.0.0.1:1080
    ' - Including Windows Update
    '
    ' Useful for split-tunnel setups where trusted domains go direct
    ' but everything else is encrypted via Psiphon SOCKS5 proxy.
    '
    ' If needed, test PAC web access and fundamental logic with:
    ' - https://pactester.brdbnt.com/
    ' - https://github.com/termsl/WPADChecker
    ' - curl http://127.0.0.1/proxy.pac
    '
    ' v1.0 20250902(added Amazon Vine Voice https://amazon.com/vine/about)
    ' v1.1 20250910(added Google Gmail but I need to add it to Thunderbird)
    ' v1.2 20250918(added Microsoft sites for practice adding domains)
    ' v1.3 20251016(removed Microsoft domains for Windows-Update reasons)
    ' v1.4 20251016(rewrote to eliminate Windows-Update altogether)
    ' */
    '
    ' function FindProxyForURL(url, host) {
    ' // Bypass Gmail & Google
    ' if (shExpMatch(host, "*.google.com") ||
    ' shExpMatch(host, "*.gmail.com") ||
    ' shExpMatch(host, "mail.google.com")) {
    ' return "DIRECT";
    ' }
    '
    ' // Bypass Amazon Vine <https://amazon.com/vine/about>
    ' if (shExpMatch(host, "*.amazon.com") ||
    ' shExpMatch(host, "amazon.com")) {
    ' return "DIRECT";
    ' }
    '
    ' // Keep Copilot direct for stability
    ' if (shExpMatch(host, "*.copilot.microsoft.com")) {
    ' return "DIRECT";
    ' }
    '
    ' // All other traffic, including Microsoft Update, Bing, etc. ? proxy
    ' return "SOCKS 127.0.0.1:1080";
    ' }
    ' ---< cut here for proxy.pac >---
    '
    ' Another way to test the proxy from within Firefox is:
    ' a. Go to <about:blank>
    ' b. Press Ctrl+Shift+K to open the web console for that page
    ' c. Paste this
    ' fetch("https://ifconfig.me/ip")
    ' .then(r => r.text())
    ' .then(ip => console.log("Your current IP is:", ip));
    ' d. You should now see your current external IP printed in the console.
    '
    ' A more permissive endpoint would be:
    ' fetch("https://api.ipify.org?format=text")
    ' .then(r => r.text())
    ' .then(ip => console.log("Your current IP is:", ip));
    '
    ' What I see, for example, when I test this out for you, is the following:
    ' Your current IP is: 172.236.227.197
    '
    ' Many thanks to Andy Burns who was the first person in my life to mention
    ' PAC files, which I looked up and found out from that how useful they are.
    '

    --
    The point of Usenet is for smart people to help each other & for results
    to be archived so that anyone can access our immense tribal knowledge.

    --- PyGate Linux v1.5.1
    * Origin: Dragon's Lair, PyGate NNTP<>Fido Gate (3:633/10)