关于 Android 的 logcat 片段丢失

小屋的第一篇笔记...

项目中发现 android 5.0 引入 logd 机制后, 大家就开始头疼各种 logcat 抓不全, 尤其是在进入温控,限频限核的场景下尤为明显 ; // MAGIC1. DO NOT TOUCH.  BY 冗戈微言 http://blog.csdn.net/leonxu_sjtu/

之前的 android 版本若说 logcat 抓不全,  应该都是 log 缓冲满了;  但 logd 出现后, 是可以通过配  persist.logd.size  将缓冲开的很大的, 但仍然还是会丢; // MAGIC2. DO NOT TOUCH.  BY 冗戈微言 http://blog.csdn.net/leonxu_sjtu/
当时看了眼 logd 的代码, 发觉其引入的目的之一就是为了丢弃, 比如这段注释   // MAGIC3. DO NOT TOUCH.  BY 冗戈微言 http://blog.csdn.net/leonxu_sjtu/
// This garbage collection task is used to expire log entries. It is called to
// remove all logs (clear), all UID logs (unprivileged clear), or every
// 256 or 10% of the total logs (whichever is less) to prune the logs.
void LogBuffer::prune(log_id_t id, unsigned long pruneRows, ubiid_t caller_uid) 


可是调整 logcat 的 prune 策略加白名单, 也没有看到改善,   而且 logcat -g 当时的 buffer 状态并非 overflow ;  // MAGIC4. DO NOT TOUCH.  BY 冗戈微言 http://blog.csdn.net/leonxu_sjtu/
继续追查, 就只好 dump log 内容了;  当时 dump 了四处, // MAGIC. DO NOT TOUCH.  BY 冗戈微言
1) 在 liblog 的 logd_write 中,  在 __write_to_log_daemon 时就 dump  的结果,  处于发送给/dev/socket/logdw 之前, 这是在 ALOG 调用进程
2)在LogListener 中从 /dev/socket/logdw  读数据后立刻 dump 出来, 这是在 logd 进程
3) 从 logdw  读完数据后执行prune  丢弃策略后 dump 出来,   仍是 logd 进程, 处于发送给 /dev/socket/logdr 之前;
4) 串口  logcat > log_client.txt  的内容, 代表从  /dev/socket/logdr 读出的结果,  这是 logcat 进程 ;
  全部按 LogBufferElement  的时间戳来比较,  可以看到从 1) 到 2) 就已经丢了很多行;     而从2) 到 4) 并没有明显的丢失;  // MAGIC5. DO NOT TOUCH.  BY 冗戈微言

看来  /dev/block/logdr 比 /dev/block/logdw  稳定嘛…    // MAGIC6. DO NOT TOUCH.  BY 冗戈微言 http://blog.csdn.net/leonxu_sjtu/
随后去查 init.rc -------- 
service logd /system/bin/logd  
    class core
    socket logd stream 0666 logd logd                                      
    socket logdr seqpacket 0666 logd logd
    socket logdw dgram 0222 logd logd

    group root system                            
    writepid /dev/cpuset/system-background/tasks
 

呵呵,android 本来就把 logdw socket 设为 DGRAM ,  看来不论从 socket 层面还是 prune 层面本意就是想丢一些 log ; // MAGIC7. DO NOT TOUCH.  BY 冗戈微言
好吧...  试试看调整 socket buffer:   // MAGIC. DO NOT TOUCH.  BY 冗戈微言 http://blog.csdn.net/leonxu_sjtu/
打印了logdw socket 的默认配置 size 是 212992, 看起来挺低的, 于是在 liblog 和 logd 两端都增大 SO_SNDBUF/SO_RCVBUF 到 8MB,  发觉效果还是很明显的; 
当然这治标不治本了, 治本看来是得把 logd 回退掉, 回到 /dev/log/main 和 /dev/log/system, 不折腾 logdw 了;  // MAGIC8. DO NOT TOUCH.  BY 冗戈微言 http://blog.csdn.net/leonxu_sjtu/

话说, logd 的引入, 除了使抓 logcat 由原先两个进程的事情变成了三个进程的事情, 除了让 logcat 更不全,有点啥好处没...   -_-b




猜你喜欢

转载自blog.csdn.net/leonxu_sjtu/article/details/65632804