问题与设置使用WifiManager静态IP配置

问题描述 投票:0回答:1

我想改变我的设备上的DNS服务器。我非常希望有WiFi和3G / 4G做两个,但我看到移动网络带来了另一个复杂,所以我开始WifiManager通过设置静态IP。

该代码似乎工作正常,但手机不改变IP(查看设置 - > Wifi-> SSID-> IP地址),并没有从我的Linux PC响应ping(ARP是不完整的),并没有显示了在WiFi路由器(DHCP配置至192.168.1.230)。

你觉得我做错了什么?

他们是改变DNS服务器的其他方式(除了vpnservices;))?

我使用下面的代码主要来源于杨在How to configue a static IP address, netmask, gateway programmatically on Android 3.x or 4.x

我使用的是Android 6.0

logcat的输出:

11-01 09:45:17.167 12890-12890/com.narb.dns I/DNS: config:
                                                   * ID: 17 SSID: "Livebox-FB64" PROVIDER-NAME: null BSSID: any FQDN: null PRIO: 4777
                                                    numAssociation 72
                                                    validatedInternetAccess
                                                    KeyMgmt: WPA_PSK Protocols: WPA RSN WAPI
                                                    AuthAlgorithms:
                                                    PairwiseCiphers: TKIP CCMP SMS4
                                                    GroupCiphers: TKIP CCMP SMS4
                                                    PSK: *
                                                    Limited: 0
                                                   IP config:
                                                   IP assignment: STATIC
                                                   Static configuration: IP address 192.168.1.236/24 Gateway 192.168.1.1  DNS servers: [ 8.8.8.8 192.168.1.1 ] Domains
                                                   Proxy settings: NONE
                                                    autoJoinBSSID=any cuid=1000 cname=android.uid.system:1000 luid=1000 lname=android.uid.system:1000 lcuid=-1 userApproved=USER_APPROVED noInternetAccessExpected=false roamingFailureBlackListTimeMilli: 1000
                                                   triggeredLow: 0 triggeredBad: 0 triggeredNotHigh: 0
                                                   ticksLow: 0 ticksBad: 0 ticksNotHigh: 7
                                                   triggeredJoin: 0
                                                   autoJoinBailedDueToLowRssi: false
                                                   autoJoinUseAggressiveJoinAttemptThreshold: 0
11-01 09:45:17.237 12890-12965/com.narb.dns I/Adreno: QUALCOMM build                   : 8249e7b, Iacb76f3f7d
                                                      Build Date                       : 03/22/16
                                                      OpenGL ES Shader Compiler Version: XE031.06.00.05
                                                      Local Branch                     : 
                                                      Remote Branch                    : refs/tags/AU_LINUX_ANDROID_LA.BR.1.2.6_RB1.06.00.01.179.016
                                                      Remote Branch                    : NONE
                                                      Reconstruct Branch               : NOTHING
11-01 09:45:17.307 12890-12890/com.narb.dns W/art: Before Android 4.1, method int android.support.v7.widget.ListViewCompat.lookForSelectablePosition(int, boolean) would have incorrectly overridden the package-private method in android.widget.ListView

代码:我评论manager.saveconfiguration,因为它是过时和文档是说,updatenetwork是足够了(反正我试图与saveconfig的,重新连接,联想 - 同样的结果)

package com.narb.dns;

import android.content.Context;
import android.net.wifi.WifiConfiguration;
import android.net.wifi.WifiInfo;
import android.net.wifi.WifiManager;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.util.Log;

import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.net.InetAddress;
import java.util.ArrayList;
import java.util.List;


public class MainActivity extends AppCompatActivity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        Context context = getApplicationContext();


        WifiManager manager = (WifiManager)context.getSystemService(Context.WIFI_SERVICE);

        WifiConfiguration wifiConf = null;
        WifiManager wifiManager = (WifiManager)getSystemService(Context.WIFI_SERVICE);
        WifiInfo connectionInfo = wifiManager.getConnectionInfo();
        List<WifiConfiguration> configuredNetworks = wifiManager.getConfiguredNetworks();
        for (WifiConfiguration conf : configuredNetworks){
            if (conf.networkId == connectionInfo.getNetworkId()){
                wifiConf = conf;
                break;
            }
        }

        if (wifiConf != null)
        {
            try
            {
                setStaticIpConfiguration(manager, wifiConf,
                        InetAddress.getByName("192.168.1.236"), 24,
                        InetAddress.getByName("192.168.1.1"),
                        new InetAddress[] { InetAddress.getByName("8.8.8.8"),
                                InetAddress.getByName("192.168.1.1") });

                Log.i("DNS","config:\n"+wifiConf);
            }
            catch (Exception e)
            {
                e.printStackTrace();
            }
        }
    }

    private static void setStaticIpConfiguration(WifiManager manager, WifiConfiguration config,
                InetAddress ipAddress, int prefixLength, InetAddress gateway,
                InetAddress[] dns) throws ClassNotFoundException,
                IllegalAccessException, IllegalArgumentException, InvocationTargetException,
                NoSuchMethodException, NoSuchFieldException, InstantiationException    {

        // First set up IpAssignment to STATIC.
        Object ipAssignment = getEnumValue("android.net.IpConfiguration$IpAssignment", "STATIC");
        callMethod(config, "setIpAssignment", new String[] { "android.net.IpConfiguration$IpAssignment" },
                new Object[] { ipAssignment });

        // Then set properties in StaticIpConfiguration.
        Object staticIpConfig = newInstance("android.net.StaticIpConfiguration");
        Object linkAddress = newInstance("android.net.LinkAddress", new Class<?>[] {
                InetAddress.class, int.class }, new Object[] { ipAddress, prefixLength });

        setField(staticIpConfig, "ipAddress", linkAddress);
        setField(staticIpConfig, "gateway", gateway);
        getField(staticIpConfig, "dnsServers", ArrayList.class).clear();
        for (int i = 0; i < dns.length; i++)
            getField(staticIpConfig, "dnsServers", ArrayList.class).add(dns[i]);

        callMethod(config, "setStaticIpConfiguration", new String[] {
                "android.net.StaticIpConfiguration" }, new Object[] { staticIpConfig });
        manager.updateNetwork(config);
     //   manager.reassociate();
     //   manager.saveConfiguration();
    }

    private static Object newInstance(String className) throws ClassNotFoundException, InstantiationException, IllegalAccessException, NoSuchMethodException, IllegalArgumentException, InvocationTargetException
    {
        return newInstance(className, new Class<?>[0], new Object[0]);
    }

    private static Object newInstance(String className, Class<?>[] parameterClasses, Object[] parameterValues) throws NoSuchMethodException, InstantiationException, IllegalAccessException, IllegalArgumentException, InvocationTargetException, ClassNotFoundException
    {
        Class<?> clz = Class.forName(className);
        Constructor<?> constructor = clz.getConstructor(parameterClasses);
        return constructor.newInstance(parameterValues);
    }

    @SuppressWarnings({ "unchecked", "rawtypes" })
    private static Object getEnumValue(String enumClassName, String enumValue) throws ClassNotFoundException
    {
        Class<Enum> enumClz = (Class<Enum>)Class.forName(enumClassName);
        return Enum.valueOf(enumClz, enumValue);
    }

    private static void setField(Object object, String fieldName, Object value) throws IllegalAccessException, IllegalArgumentException, NoSuchFieldException
    {
        Field field = object.getClass().getDeclaredField(fieldName);
        field.set(object, value);
    }

    private static <T> T getField(Object object, String fieldName, Class<T> type) throws IllegalAccessException, IllegalArgumentException, NoSuchFieldException
    {
        Field field = object.getClass().getDeclaredField(fieldName);
        return type.cast(field.get(object));
    }

    private static void callMethod(Object object, String methodName, String[] parameterTypes, Object[] parameterValues) throws ClassNotFoundException, IllegalAccessException, IllegalArgumentException, InvocationTargetException, NoSuchMethodException
    {
        Class<?>[] parameterClasses = new Class<?>[parameterTypes.length];
        for (int i = 0; i < parameterTypes.length; i++)
            parameterClasses[i] = Class.forName(parameterTypes[i]);

        Method method = object.getClass().getDeclaredMethod(methodName, parameterClasses);
        method.invoke(object, parameterValues);
    }
}

表现:

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.narb.dns">

    <uses-permission android:name="android.permission.ACCESS_WIFI_STATE" />
    <uses-permission android:name="android.permission.CHANGE_WIFI_STATE" />

    <application
        android:allowBackup="true"
        android:icon="@mipmap/ic_launcher"
        android:label="@string/app_name"
        android:roundIcon="@mipmap/ic_launcher_round"
        android:supportsRtl="true"
        android:theme="@style/AppTheme">
        <activity android:name=".MainActivity">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />

                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
    </application>

</manifest>
android dns wifi wifimanager static-ip-address
1个回答
0
投票

我想通了,你必须单独的方法调用并等待调用下一个之前成功的响应。这是牛轧糖。

callMethod(config, "setIpAssignment", new String[] { "android.net.IpConfiguration$IpAssignment" },
                new Object[] { ipAssignment });
int updateNetworkResult = manager.updateNetwork(config);

if (updateNetworkResult == -1) return;

callMethod(config, "setStaticIpConfiguration", new String[] {
                "android.net.StaticIpConfiguration" }, new Object[] { staticIpConfig });
manager.updateNetwork(config);
© www.soinside.com 2019 - 2024. All rights reserved.