トピックは他の人にとっても興味深いようですので、現在の解決策について説明します。
- ソフトウェアは、IPv6 が機能しているかどうかを検出し、状態を記憶します -> これは、既知の IPv6 アドレスに TCP 接続することによって行われます (isReachable() の Ping は信頼できません。次のバグ レポートを参照してください: https://josm. openstreetmap.de/ticket/11452 )。
- 記憶された状態に基づいて、ソフトウェアは「java.net.preferIPv6Addresses」を「true」に設定して開始します。
- これは、IPv4 から IPv6 ネットワークへの切り替えの場合、次の再起動まで IPv4 を使用することを意味します。
- IPv6 が有効なネットワークから IPv4 のみのネットワークへの切り替えでは、まったく機能しません。これは、ソフトウェアを再起動することで解決されます。
- 疑わしい場合は、IPv6 が機能しないと想定します。
- 検出を行った後に「java.net.preferIPv6Addresses」を変更することはできません。その値は、最初のネットワーク接続の前にのみ読み取られるように見えるためです。実行時にその状態をリセットする方法があれば、それについて知りたいです。
このソリューションは機能しているように見えます。ログ ATM には約 4% の IPv6 接続がありますが、実際には満足のいくソリューションではありません。
/**
* Check if IPv6 can be safely enabled and do so. Because this cannot be done after network activation,
* disabling or enabling IPV6 may only be done with next start.
*/
private static void checkIPv6() {
if ("auto".equals(Main.pref.get("prefer.ipv6", "auto"))) {
new Thread(new Runnable() { /* this may take some time (DNS, Connect) */
public void run() {
boolean hasv6 = false;
boolean wasv6 = Main.pref.getBoolean("validated.ipv6", false);
try {
/* Use the check result from last run of the software, as after the test, value
changes have no effect anymore */
if (wasv6) {
Utils.updateSystemProperty("java.net.preferIPv6Addresses", "true");
}
for (InetAddress a : InetAddress.getAllByName("josm.openstreetmap.de")) {
if (a instanceof Inet6Address) {
if (a.isReachable(1000)) {
/* be sure it REALLY works */
Socket s = new Socket();
s.connect(new InetSocketAddress(a, 80), 1000);
s.close();
Utils.updateSystemProperty("java.net.preferIPv6Addresses", "true");
if (!wasv6) {
Main.info(tr("Detected useable IPv6 network, prefering IPv6 over IPv4 after next restart."));
} else {
Main.info(tr("Detected useable IPv6 network, prefering IPv6 over IPv4."));
}
hasv6 = true;
}
break; /* we're done */
}
}
} catch (IOException | SecurityException e) {
if (Main.isDebugEnabled()) {
Main.debug("Exception while checking IPv6 connectivity: "+e);
}
}
if (wasv6 && !hasv6) {
Main.info(tr("Detected no useable IPv6 network, prefering IPv4 over IPv6 after next restart."));
Main.pref.put("validated.ipv6", hasv6); // be sure it is stored before the restart!
new RestartAction().actionPerformed(null);
}
Main.pref.put("validated.ipv6", hasv6);
}
}, "IPv6-checker").start();
}
}