【发布时间】:2014-10-15 15:07:05
【问题描述】:
几个月以来,我的应用程序中出现大量异常并显示错误消息:添加窗口失败 (android.os.TransactionTooLargeException)
我知道 IPC 缓冲区事务大小限制为 1024KB,但我只是将 id 发送到我的服务(长值)。 奇怪的是,这些异常只发生在装有 Android 4.4.2 的三星设备上(超过 50K 崩溃中的每一个)。 您知道最新的三星 ROM 中的特定错误吗?
java.lang.RuntimeException: Adding window failed
at android.view.ViewRootImpl.setView(ViewRootImpl.java:738)
at android.view.WindowManagerGlobal.addView(WindowManagerGlobal.java:278)
at android.view.WindowManagerImpl.addView(WindowManagerImpl.java:69)
at android.widget.Toast$TN.handleShow(Toast.java:478)
at android.widget.Toast$TN$1.run(Toast.java:374)
at android.os.Handler.handleCallback(Handler.java:733)
at android.os.Handler.dispatchMessage(Handler.java:95)
at android.os.Looper.loop(Looper.java:136)
at android.app.ActivityThread.main(ActivityThread.java:5476)
at java.lang.reflect.Method.invokeNative(Method.java)
at java.lang.reflect.Method.invoke(Method.java:515)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1268)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1084)
at dalvik.system.NativeStart.main(NativeStart.java)
Caused by: android.os.TransactionTooLargeException
at android.os.BinderProxy.transact(Binder.java)
at android.view.IWindowSession$Stub$Proxy.addToDisplay(IWindowSession.java:710)
at android.view.ViewRootImpl.setView(ViewRootImpl.java:727)
at android.view.WindowManagerGlobal.addView(WindowManagerGlobal.java:278)
at android.view.WindowManagerImpl.addView(WindowManagerImpl.java:69)
at android.widget.Toast$TN.handleShow(Toast.java:478)
at android.widget.Toast$TN$1.run(Toast.java:374)
at android.os.Handler.handleCallback(Handler.java:733)
at android.os.Handler.dispatchMessage(Handler.java:95)
at android.os.Looper.loop(Looper.java:136)
at android.app.ActivityThread.main(ActivityThread.java:5476)
at java.lang.reflect.Method.invokeNative(Method.java)
at java.lang.reflect.Method.invoke(Method.java:515)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1268)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1084)
at dalvik.system.NativeStart.main(NativeStart.java)
或
java.lang.RuntimeException: Adding window failed
at android.view.ViewRootImpl.setView(ViewRootImpl.java:726)
at android.view.WindowManagerGlobal.addView(WindowManagerGlobal.java:278)
at android.view.WindowManagerImpl.addView(WindowManagerImpl.java:69)
at android.app.ActivityThread.handleResumeActivity(ActivityThread.java:3038)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2368)
at android.app.ActivityThread.access$900(ActivityThread.java:161)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1265)
at android.os.Handler.dispatchMessage(Handler.java:102)
at android.os.Looper.loop(Looper.java:157)
at android.app.ActivityThread.main(ActivityThread.java:5356)
at java.lang.reflect.Method.invokeNative(Method.java)
at java.lang.reflect.Method.invoke(Method.java:515)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1265)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1081)
at dalvik.system.NativeStart.main(NativeStart.java)
Caused by: android.os.TransactionTooLargeException
at android.os.BinderProxy.transact(Binder.java)
at android.view.IWindowSession$Stub$Proxy.addToDisplay(IWindowSession.java:710)
at android.view.ViewRootImpl.setView(ViewRootImpl.java:715)
at android.view.WindowManagerGlobal.addView(WindowManagerGlobal.java:278)
at android.view.WindowManagerImpl.addView(WindowManagerImpl.java:69)
at android.app.ActivityThread.handleResumeActivity(ActivityThread.java:3038)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2368)
at android.app.ActivityThread.access$900(ActivityThread.java:161)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1265)
at android.os.Handler.dispatchMessage(Handler.java:102)
at android.os.Looper.loop(Looper.java:157)
at android.app.ActivityThread.main(ActivityThread.java:5356)
at java.lang.reflect.Method.invokeNative(Method.java)
at java.lang.reflect.Method.invoke(Method.java:515)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1265)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1081)
at dalvik.system.NativeStart.main(NativeStart.java)
【问题讨论】:
-
这来自您或某人正在展示的
Toast。你有没有显示任何Toasts?有比短字符串更复杂的吗? -
是的,我在一些 Toast 消息中使用了一些 SpannableString 内容: SpannableString span = new SpannableString(builder.toString()); if (!isEmptyErrorMessage) { span.setSpan(new ForegroundColorSpan(this.service.getResources().getColor(R.color.orange_logo)), pos, builder.toString().length(), Spannable.SPAN_EXCLUSIVE_EXCLUSIVE); span.setSpan(new StyleSpan(Typeface.BOLD), pos, builder.toString().length(), Spannable.SPAN_EXCLUSIVE_EXCLUSIVE); } 但结果不超过 200 个字符
-
事实上,我添加了第二个堆栈跟踪,它比第一个更频繁地发生。仍然只在三星设备上......
-
"您知道最新的三星 ROM 中的特定错误吗?"你已经在统计上证明了存在一个。 - 据我了解,1MB 事务缓冲区必须在事务未完成时保持所有数据缓冲,例如这种情况:stackoverflow.com/a/16895870/995891。因此,也许这些设备上的某些东西没有正确清理,只留下比平时更小的缓冲区,而您的应用恰好使用了更多。尽管 IPC 缓冲区可能在本机代码中,但可能有机会通过堆转储查看使用缓冲区的内容。
-
你的问题到底是什么?