android - 严格模式 java.lang.Throwable : Untagged socket detected

标签 android android-trafficstats android-strictmode

在启用 StrictMode 的情况下,我刚开始遇到这个异常:

java.lang.Throwable: Untagged socket detected; use TrafficStats.setThreadSocketTag() to track all network usage

最佳答案

有几种方法可以处理这个异常。首先,您必须检查堆栈跟踪并确保报告违规的是您的代码。例如,看看下面的跟踪。

D/StrictMode: StrictMode policy violation: android.os.strictmode.UntaggedSocketViolation: Untagged socket detected; use TrafficStats.setThreadSocketTag() to track all network usage
    at android.os.StrictMode.onUntaggedSocket(StrictMode.java:2124)
    at com.android.server.NetworkManagementSocketTagger.tag(NetworkManagementSocketTagger.java:82)
    at libcore.io.BlockGuardOs.tagSocket(BlockGuardOs.java:52)
    at libcore.io.BlockGuardOs.socket(BlockGuardOs.java:372)
    at libcore.io.ForwardingOs.socket(ForwardingOs.java:217)
    at libcore.io.IoBridge.socket(IoBridge.java:658)
    at java.net.PlainSocketImpl.socketCreate(PlainSocketImpl.java:128)
    at java.net.AbstractPlainSocketImpl.create(AbstractPlainSocketImpl.java:128)
    at java.net.ServerSocket.createImpl(ServerSocket.java:306)
    at java.net.ServerSocket.getImpl(ServerSocket.java:259)
    at java.net.ServerSocket.bind(ServerSocket.java:377)
    at java.net.ServerSocket.<init>(ServerSocket.java:237)
    at java.net.ServerSocket.<init>(ServerSocket.java:128)
    at com.java42.android03.binder.peer.messaging.J42PM_ServerConnection.run(J42PM_ServerConnection.java:52)
    at com.java42.base.components.utility.impl.Utility_Thread$1.run(Utility_Thread.java:137)
    at java.lang.Thread.run(Thread.java:919)
    at com.java42.utility.base.J42Thread.run(J42Thread.java:38)

违规的应用调用是:

J42PM_ServerConnection.run(J42PM_ServerConnection.java:52)

接下来,看看这段代码:

public void run() {
    try (ServerSocket serverSocket = new ServerSocket(port)) {
        this.serverSocket = serverSocket;
        CallerId.identifyBasic("J42PSC0179D: listening Inbound....");
        while (!Thread.currentThread().isInterrupted()) {
        ...

由于这是服务器端循环,并且线程 ID 在服务器进程的生命周期内不会更改,您可以通过使用当前线程 ID 添加对 TrafficStats.setThreadStatsTag() 的调用来修复违规。

public void run() {
    TrafficStats.setThreadStatsTag((int) Thread.currentThread().getId()); // <---
    try (ServerSocket serverSocket = new ServerSocket(port)) {
        this.serverSocket = serverSocket;
        CallerId.identifyBasic("J42PSC0179D: listening Inbound....");
        while (!Thread.currentThread().isInterrupted()) {
        ...

让我们再看看另一条轨迹:

D/StrictMode: StrictMode policy violation: android.os.strictmode.UntaggedSocketViolation: Untagged socket detected; use TrafficStats.setThreadSocketTag() to track all network usage
    at android.os.StrictMode.onUntaggedSocket(StrictMode.java:2124)
    at com.android.server.NetworkManagementSocketTagger.tag(NetworkManagementSocketTagger.java:82)
    at libcore.io.BlockGuardOs.tagSocket(BlockGuardOs.java:52)
    at libcore.io.BlockGuardOs.socket(BlockGuardOs.java:372)
    at libcore.io.ForwardingOs.socket(ForwardingOs.java:217)
    at libcore.io.IoBridge.socket(IoBridge.java:658)
    at java.net.PlainSocketImpl.socketCreate(PlainSocketImpl.java:128)
    at java.net.AbstractPlainSocketImpl.create(AbstractPlainSocketImpl.java:128)
    at java.net.Socket.createImpl(Socket.java:489)
    at java.net.Socket.<init>(Socket.java:446)
    at java.net.Socket.<init>(Socket.java:218)
    at com.java42.android03.binder.peer.messaging.J42PM_ClientConnection.run(J42PM_ClientConnection.java:54)
    at com.java42.android03.binder.peer.messaging.J42PM_Client$2.run(J42PM_Client.java:86)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1167)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:641)
    at java.lang.Thread.run(Thread.java:919)

与第一个示例一样,您确定了违规的应用调用:

J42PM_ClientConnection.run(J42PM_ClientConnection.java:54)

接下来,看看这段代码:

InetSocketAddress socketAddress = serviceResolver.getSocketAddress();
    connection = new J42PM_ClientConnection(socketAddress, responseHandler);
    executorService.execute(new Runnable() {
        @Override
        public void run() {
        connection.run();
        ...

请注意此代码使用执行程序服务来运行客户端连接。随着连接的创建和销毁,线程 ID 将在进程的生命周期内发生变化。我不确定这是否会影响流量报告,但我认为此时最好使用一个常量值来跟踪使用情况。选择一些唯一的号码。使用文件的行号是一个简单的选择。

    InetSocketAddress socketAddress = serviceResolver.getSocketAddress();
    connection = new J42PM_ClientConnection(socketAddress, responseHandler);
    executorService.execute(new Runnable() {
        @Override
        public void run() {
        TrafficStats.setThreadStatsTag(42); // <--
        connection.run();
        ...

最后一个评论,如果您在堆栈跟踪中没有看到对您的代码的调用,那么您无法阻止违规。问题出在另一个图书馆,除非您可以联系图书馆所有者,否则请忽略违规行为。

关于android - 严格模式 java.lang.Throwable : Untagged socket detected,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47723973/

相关文章:

android - getUidTxBytes(int uid) 在 android 6.0 中总是返回 0

android - Android屏幕中的红色条纹像条纹

java - 严格模式提示资源泄漏

java - 如何将数组解析为数组 JSON

android - 更新小部件中的 textView

android - 如何处理服务器和 native android 应用程序之间的时区差异?

android - 具有 StrictMode 的 MapActivity 不起作用 - 帮助

c# - ContentView Xamarin 表单

android - 如何使用 TrafficStats 分别统计 2G 和 3G 的数据使用量?

java - Android 手机使用历史 NetworkStatsManager