簡體   English   中英

在 Android 上檢測 USB 網絡共享

[英]Detect USB tethering on android

有沒有辦法在您的活動/應用程序中(以編程方式)知道用戶已在其手機上啟用 USB 網絡共享?

您還可以使用反射來訪問用於設置 USB 網絡共享的隱藏功能。 這是我的代碼。

    ConnectivityManager cm =
        (ConnectivityManager)getSystemService(Context.CONNECTIVITY_SERVICE);
    Log.d(TAG,"test enable usb tethering");
    String[] available = null;
    int code=-1;
    Method[] wmMethods = cm.getClass().getDeclaredMethods();

    for(Method method: wmMethods){
      if(method.getName().equals("getTetherableIfaces")){
        try {
            available = (String[]) method.invoke(cm);
            break;
        } catch (IllegalArgumentException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
            return;
        } catch (IllegalAccessException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
            return;
        } catch (InvocationTargetException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
            return;
        }
      }
    }

    for(Method method: wmMethods){
          if(method.getName().equals("tether")){                  
              try {
                code = (Integer) method.invoke(cm, available[0]);


            } catch (IllegalArgumentException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
                return;
            } catch (IllegalAccessException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
                return;
            } catch (InvocationTargetException e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
                return;
            }
            break;
          }
    }

    if (code==0) 
        Log.d(TAG,"Enable usb tethering successfully!");
    else
        Log.d(TAG,"Enable usb tethering failed!");

要禁用 USB 網絡共享,您只需將反射方法名稱“getTetherableIfaces”更改為“getTetheredIfaces”,將“tether”更改為“untether”。

請檢查。

查看 Settings.System 文檔指出答案是否定的,這是不可能的。

鏈接到上述文檔

這應該適用於所有手機,在某些 Android 7,6 和 5 設備上得到確認;

方法:接口 rndisX(通常為 rndis0)僅在啟用 USB 網絡共享時顯示。

代碼示例:

private static boolean isTetheringActive(Context context){
    try{
        for(Enumeration<NetworkInterface> en = NetworkInterface.getNetworkInterfaces(); en.hasMoreElements();){
            NetworkInterface intf=en.nextElement();
            for(Enumeration<InetAddress> enumIpAddr = intf.getInetAddresses(); enumIpAddr.hasMoreElements();){
                InetAddress inetAddress=enumIpAddr.nextElement();
                if(!intf.isLoopback()){
                    if(intf.getName().contains("rndis")){
                        return true;
                    }
                }
            }
        }
    }catch(Exception e){e.printStackTrace();}
    return false;
}

這是偵聽網絡共享狀態更改的解決方案:

首先你需要熟悉 BroadcastReceiver。 你可以找到很多教程(谷歌:如何監聽連接變化......)

為了獲得 Tethering 狀態更新,您需要使用 Android 的隱藏過濾器操作(請參閱 ConnectivityManager)

並在您的 BroadcastReceiver 類中:

IntentFilter filter = new IntentFilter("android.net.conn.TETHER_STATE_CHANGED");

然后將過濾器注冊到您的 BroadcastReceiver :

myApplicationContext.registerReceiver(this, filter);

在您的 onReceive(final Context context,final Intent intent) 方法中,Intent.extras 信息包含 3 個填充有相應網絡接口的數組:erroredArray / availableArray / activeArray

這有點棘手,但您可以獲得網絡共享狀態信息。

另外,你可以對Android代碼的隱藏功能做一些反思:

在連接管理器中搜索getTetherableIfaces()

這是一個鏈接: https : //github.com/android/platform_frameworks_base/blob/master/core/java/android/net/ConnectivityManager.java#L1604

您可以獲取網絡接口並檢查活動的內容,如下所示:

Enumeration<NetworkInterface> interfaces = NetworkInterface.getNetworkInterfaces();
NetworkInterface rndis = null;
NetworkInterface wlan = null;

while(interfaces.hasMoreElements()) {
     NetworkInterface nif = interfaces.nextElement();
     if(hasIP4Address(nif)) {
          if(nif.getDisplayName().startsWith("rndis"))
              rndis = nif;
          else if (nif.getDisplayName().startsWith("wlan"))
              wlan = nif;
     }
}
// Let the user choose Wi-Fi or rndis connect
if (rndis != null) {
    socket.setNetworkInterface(rndis);
    Log.i(TAG, "Subscribe: with interface rndis");
} else if(wlan != null) {
    socket.setNetworkInterface(wlan);
    Log.i(TAG, "Subscribe: with interface wlan");
}

我發現如果我檢查 usb0 網絡接口,一旦設置了網絡共享,它只有一個 IP 地址。

public static String getIPAddressUsb(final boolean useIPv4) {
    try {
        final List<NetworkInterface> interfaces = Collections.list(NetworkInterface.getNetworkInterfaces());
        for (final NetworkInterface intf : interfaces) {
            if (intf.getDisplayName().startsWith("usb")) {
                final List<InetAddress> addrs = Collections.list(intf.getInetAddresses());
                for (final InetAddress addr : addrs) {
                    final String sAddr = addr.getHostAddress().toUpperCase();
                    final boolean isIPv4 = InetAddressUtils.isIPv4Address(sAddr);
                    if (useIPv4) {
                        if (isIPv4) { return sAddr; }
                    } else {
                        if (!isIPv4) {
                            final int delim = sAddr.indexOf('%');
                            return delim < 0 ? sAddr : sAddr.substring(0, delim);
                        }
                    }
                }
            }
        }
    } catch (final Exception ex) {
        // for now eat exceptions
    }
    return "";
}


boolean isUsbTethered(){
String ipAddr = MipnAndroidApplication.getIPAddressUsb(true);
    if (ipAddr.length() == 0) {
        Log.i(LOG_TAG, "tethering not enabled");
    return false;
    } else {
        Log.i(LOG_TAG, "tethering enabled :)");
    return true;
    }
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM