安卓java 获取当前日志 判断_Android上如何在发生崩溃时抓取日志

一、java层未处理异常

未处理异常定义:没有被try…catch 住的异常(这里说的异常包括Exception和Error)

Java层默认未处理异常的Handler,都是调用Thread.setDefaultUncaughtExceptionHandler,注册一个UncaughtExceptionHandler来实现的。可以抓到所有线程的未处理异常

final Thread.UncaughtExceptionHandler oldHandler = Thread.getDefaultUncaughtExceptionHandler();

Thread.setDefaultUncaughtExceptionHandler(new Thread.UncaughtExceptionHandler() {

@Override

public void uncaughtException(Thread thread, Throwable throwable) {

// 编写崩溃前的处理逻辑

// ...

// 此回调既可以收到Exception, 也可以收到Error

/*调用默认处理,杀死进程*/

oldHandler.uncaughtException(thread, throwable);

}

});

当然也可以注册针对指定线程的未处理异常的Handler,如:

Thread.currentThread().setUncaughtExceptionHandler(new Thread.UncaughtExceptionHandler() {

@Override

public void uncaughtException(Thread thread, Throwable throwable) {

// 编写崩溃前的处理逻辑

// ...

// 此回调既可以收到Exception, 也可以收到Error

if( /*这是一个致命错误*/ ) {

//调用默认处理,杀死进程

Thread.getDefaultUncaughtExceptionHandler().uncaughtException(thread, throwable);

} else {

// 什么也不处理的话, 当前线程被终止,但是整个进程可以继续运行

}

}

});

另外发现,有一种捕获不到的exception,可以尝试adb log捕获所有信息,然后删选有用信息

二、native层异常

native异常是通过信号来通知的。所以要想抓到native异常,需要注册信号回调。

注册方法:

static struct sigaction g_oldCSSigAction[8] = {0};

void CrashSaver_handleSignal(int sig, siginfo_t* info, void* context);

// 注册信号函数

void CrashSaver_install()

{

// 保存信号的默认行为对象

memset(g_oldCSSigAction, 0, sizeof(g_oldCSSigAction));

sigaction(SIGTRAP, NULL, &g_oldCSSigAction[0]);

sigaction(SIGABRT, NULL, &g_oldCSSigAction[1]);

sigaction(SIGILL, NULL, &g_oldCSSigAction[2]);

sigaction(SIGSEGV, NULL, &g_oldCSSigAction[3]);

sigaction(SIGFPE, NULL, &g_oldCSSigAction[4]);

sigaction(SIGBUS, NULL, &g_oldCSSigAction[5]);

sigaction(SIGPIPE, NULL, &g_oldCSSigAction[6]);

sigaction(SIGSYS, NULL, &g_oldCSSigAction[7]);

// 创建 信号行为对象

struct sigaction newSigAction;

sigemptyset(&newSigAction.sa_mask);

newSigAction.sa_flags = SA_SIGINFO;

/*设置信号处理函数*/

newSigAction.sa_sigaction = CrashSaver_handleSignal;

// 注册信号新的行为对象

sigaction(SIGTRAP, &newSigAction, NULL);

sigaction(SIGABRT, &newSigAction, NULL);

sigaction(SIGILL, &newSigAction, NULL);

sigaction(SIGSEGV, &newSigAction, NULL);

sigaction(SIGFPE, &newSigAction, NULL);

sigaction(SIGBUS, &newSigAction, NULL);

sigaction(SIGPIPE, &newSigAction, NULL);

sigaction(SIGSYS, &newSigAction, NULL);

}

编写回调处理函数:

void CrashSaver_handleSignal(int sig, siginfo_t* info, void* context)

{

// sig 触发的信号ID 如 SIGABRT、SIGSEGV等

// info 对此信号的描述信息

// context 信号发生的上下文。比如各种寄存器信息。此结构和具体的CPU平台有关

// 此处增加处理逻辑

CrashSaver_uninstall(); /*反注册*/

raise(signum); /*调用系统默认信号处理*/

}

反注册函数:

void CrashSaver_uninstall()

{

sigaction(SIGTRAP, &g_oldCSSigAction[0], NULL);

sigaction(SIGABRT, &g_oldCSSigAction[1], NULL);

sigaction(SIGILL , &g_oldCSSigAction[2], NULL);

sigaction(SIGSEGV, &g_oldCSSigAction[3], NULL);

sigaction(SIGFPE, &g_oldCSSigAction[4], NULL);

sigaction(SIGBUS, &g_oldCSSigAction[5], NULL);

sigaction(SIGPIPE, &g_oldCSSigAction[6], NULL);

sigaction(SIGSYS, &g_oldCSSigAction[7], NULL);

memset(g_oldCSSigAction, 0, sizeof(g_oldCSSigAction));

}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值