Το VPN για Android δουλεύει με IPv6, αλλά το πρόγραμμα περιήγησης επιλέγει ακόμα IPv4
Ακολουθήστε τα τέσσερα στάδια όπου μια ιδιωτική διεύθυνση IPv6 εξαφανίζεται: resolver, δήλωση VpnService, έλεγχος υποψηφίων από το πρόγραμμα περιήγησης και παράδοση διαδρομής.
Το VPN είναι ενεργό, η ιδιωτική διεπαφή ιστού απαντά μέσω IPv6 από φορητό υπολογιστή, και το τηλέφωνο Android εξακολουθεί να ανοίγει την ίδια σελίδα μέσω IPv4 ή αρνείται να τη φορτώσει εντελώς. Η εγγραφή AAAA υπάρχει. Η σήραγγα αναφέρει διεύθυνση IPv6. Τίποτα στον πελάτη δεν φαίνεται λάθος. Τέσσερις χωριστές αποφάσεις καθορίζουν το αποτέλεσμα: ποιος resolver απάντησε, τι δήλωσε το VpnService στο Android, ποια οικογένεια διευθύνσεων ήταν διατεθειμένο να δοκιμάσει το πρόγραμμα περιήγησης και αν ένα πακέτο μπορεί να κάνει τη διαδρομή μετ' επιστροφής. Δουλέψτε τις με αυτή τη σειρά αντί να προσθέσετε μια προεπιλεγμένη διαδρομή και να ελπίζετε ότι το σύμπτωμα θα μετακινηθεί.
Βήμα 1: αποδείξτε ποιος resolver απάντησε στο ερώτημα AAAA
Το Android δεν έχει μία μόνο διαδρομή DNS. Ένα VPN μπορεί να προωθήσει διακομιστή DNS για το δίκτυό του, το σύστημα μπορεί να χρησιμοποιήσει Private DNS για ονόματα υπολογιστών που κρίνει κατάλληλα, και το Chrome μπορεί να εκτελέσει τον δικό του κρυπτογραφημένο resolver από το chrome://settings/security. Σε ένα τηλέφωνο όπου η σήραγγα προωθεί το 10.61.0.1 αλλά το Private DNS δείχνει σε δημόσιο πάροχο, το όνομα μέσα στην ιδιωτική σας ζώνη δεν επιλύεται από το μηχάνημα που κατέχει τη ζώνη. Το πρόγραμμα περιήγησης παίρνει απάντηση από resolver χωρίς αρμοδιότητα για αυτό το όνομα και τη θεωρεί απούσα, και το κείμενο του σφάλματος δεν αναφέρει ποτέ το DNS.
Ρωτήστε απευθείας τον resolver της σήραγγας πριν αλλάξετε οτιδήποτε άλλο. Οι δύο πρώτες εντολές δείχνουν ποιους διακομιστές DNS προσάρτησε το Android στο ενεργό δίκτυο και αν το Private DNS είναι σε αυτόματη ή αυστηρή λειτουργία· η τρίτη εκτελείται από οποιονδήποτε πελάτη μέσα στη σήραγγα, όχι από το τηλέφωνο.
adb shell dumpsys connectivity | grep -A3 "DnsAddresses"
adb shell settings get global private_dns_mode
nslookup -type=AAAA nas.lan 10.61.0.1
Βήμα 2: διαβάστε τι δήλωσε στην πραγματικότητα το VpnService
Η πλευρά του Android είναι ρητή και όχι συμπερασματική. Ένα VpnService.Builder προσθέτει διευθύνσεις με addAddress, διαδρομές με addRoute, διακομιστές DNS με addDnsServer, και μπορεί να περιορίσει ολόκληρη τη σήραγγα σε μία οικογένεια διευθύνσεων με allowFamily. Ένας builder που κάλεσε allowFamily(AF_INET) και αργότερα πρόσθεσε διαδρομή IPv6 έχει πει στο σύστημα δύο αντιφατικά πράγματα, και ο περιορισμός οικογένειας είναι αυτό που κρατά το σύστημα. Μια διαδρομή που καλύπτει το fd00:61::/64 σε συνδυασμό με διεύθυνση διεπαφής σε διαφορετικό πρόθεμα αποτυγχάνει για παρόμοιο λόγο: η διεύθυνση υπάρχει, αλλά δεν είναι on-link για αυτή τη διαδρομή.
Διαβάστε τη δήλωση αντί να εμπιστεύεστε τον διακόπτη στην εφαρμογή. Το dumpsys netd εκτυπώνει τις διευθύνσεις και τις διαδρομές που είναι προσαρτημένες στη διεπαφή tun, και το LinkProperties ανά δίκτυο μέσα στο dumpsys connectivity δείχνει τη λίστα DNS δίπλα στις οικογένειες που ισχυρίζεται το δίκτυο.
adb shell ip -6 addr show tun0
adb shell ip -6 route show table all | grep tun0
adb shell dumpsys connectivity | grep -E "LinkAddresses|Routes"
Αν η διεπαφή tun έχει διεύθυνση IPv6 αλλά καμία διαδρομή δεν ταιριάζει με το πρόθεμα της υπηρεσίας, η παράδοση IPv6 είναι ήδη σπασμένη πριν μπει πρόγραμμα περιήγησης στη μέση. Αυτό είναι διαφορετικό σφάλμα από ένα πρόγραμμα περιήγησης που αρνείται να δοκιμάσει, και χρειάζεται διαφορετική διόρθωση.
Βήμα 3: το πρόγραμμα περιήγησης αποφασίζει αν θα δοκιμάσει καθόλου IPv6
Το Chromium δεν χρησιμοποιεί κάθε εγγραφή AAAA που λαμβάνει. Ο resolver υπολογιστών του φέρει ελέγχους προσβασιμότητας IPv6 και φιλτράρισμα υποψηφίων που μπορούν να απορρίψουν ή να υποβαθμίσουν το IPv6 όταν το δίκτυο κριθεί ανίκανο να το μεταφέρει, και ο πηγαίος κώδικας του resolver δείχνει αυτόν τον έλεγχο μαζί με τις συνθήκες γύρω του. Η λογική εξαρτάται από την έκδοση και τις σημαίες, και γι' αυτό ακριβώς δύο τηλέφωνα στην ίδια σήραγγα μπορούν να συμπεριφέρονται διαφορετικά. Μόλις υπάρξουν υποψήφιοι, το Happy Eyeballs βάζει τις οικογένειες να συναγωνίζονται ανά σύνδεση, οπότε μια διαδρομή IPv6 που απαντά αργά μπορεί να χάσει από IPv4 που απαντά γρήγορα.
Παρατηρήστε την απόφαση αντί να τη συμπεράνετε. Μια συνεδρία που καταγράφηκε μέσω του chrome://net-export και αναπαράγεται στον προβολέα netlog δείχνει κάθε επίλυση και την οικογένεια που επιλέχθηκε· το chrome://net-internals/#dns δείχνει τα αποθηκευμένα αποτελέσματα. Μια επίλυση που επιστρέφει μόνο εγγραφές A για όνομα που έχει AAAA στον δικό σας resolver δείχνει κατευθείαν σε αυτό το στάδιο.
Βήμα 4: επαληθεύστε ότι ένα πακέτο μπορεί να κάνει τη διαδρομή μετ' επιστροφής
Η επιλογή διεύθυνσης δεν είναι παράδοση. Το Android κρατά πίνακες δρομολόγησης και κανόνες πολιτικής ανά δίκτυο που επιλέγουν πίνακα με βάση το fwmark, οπότε μια διαδρομή ορατή στον κύριο πίνακα δεν είναι αυτόματα η διαδρομή που χρησιμοποιεί ένα socket. Η ανάγνωση των κανόνων και το αίτημα στον πυρήνα να επιλύσει προορισμό για διεύθυνση προέλευσης χωρίζουν τα δύο.
adb shell ip -6 rule show
adb shell ip -6 route get fd00:61::20 from fd00:61::10
Η έξοδος του route get είναι αυτή που απαντά στο ερώτημα. Αν ονομάζει tun0 και τα πακέτα εξακολουθούν να πεθαίνουν, πηγαίνετε στο MTU της σήραγγας και στην προώθηση IPv6 της πύλης αντί να επιστρέψετε στο τηλέφωνο.
Γιατί η προσθήκη του ::/0 συνήθως τα κάνει χειρότερα
Η προσθήκη του ::/0 αλλάζει την αξίωση της σήραγγας από ένα πρόθεμα σε κάθε προορισμό IPv6. Στο τηλέφωνο αυτό μπορεί να ικανοποιήσει έναν έλεγχο προσβασιμότητας, επειδή μια διεύθυνση δοκιμής έξω από το πρόθεμά σας τώρα φαίνεται δρομολογήσιμη. Δεν δημιουργεί χωρητικότητα IPv6 προς τα πάνω στην πύλη, και πολλές οικιακές πύλες δεν έχουν καθόλου λειτουργικό uplink IPv6. Το αποτέλεσμα είναι μια μαύρη τρύπα για το δημόσιο IPv6: ονόματα που παλιά έπεφταν πίσω σε IPv4 τώρα κρέμονται, και η ιδιωτική σελίδα μπορεί να φαίνεται καλύτερη μόνο επειδή ο έλεγχος μετρά κάτι διαφορετικό.
Υπάρχει και κόστος πολιτικής. Με το ::/0 στη σήραγγα, όλη η κίνηση IPv6 φεύγει μέσω του VPN, συμπεριλαμβανομένης κίνησης που ο ιδιοκτήτης του δικτύου δεν συμφώνησε ποτέ να μεταφέρει. Αντιμετωπίστε το ως απόφαση ανάπτυξης με ονομασμένο ιδιοκτήτη, όχι ως βήμα αποσφαλμάτωσης που κάνετε στη 1 τα ξημερώματα.
Η σειρά εργασίας που το τελειώνει
Επιβεβαιώστε ότι η απάντηση AAAA έρχεται από τον resolver που κατέχει τη ζώνη, διαβάστε την κατάσταση VpnService και netd για τη διεπαφή tun, καταγράψτε ένα ίχνος net-export για να δείτε αν το Chromium απέρριψε τον υποψήφιο, και μετά δοκιμάστε τη διαδρομή μετ' επιστροφής με το ip -6 route get. Διορθώστε το επίπεδο που πραγματικά απέτυχε και αφήστε την πολιτική διαχωρισμού ήσυχη. Αν τα ιδιωτικά ονόματα χρειάζονται διαφορετικές απαντήσεις από τα δημόσια, γι' αυτό υπάρχει το split tunneling.
Σημειώστε το build του τηλεφώνου, την έκδοση του προγράμματος περιήγησης και τον resolver που ρωτήσατε. Αυτά τα τρία γεγονότα μετατρέπουν το "IPv6 is broken" σε κάτι που ο επόμενος μπορεί να αναπαραγάγει.