iOS安全–不同平台的崩溃收集

发布的app难免会出现一些奇葩的bug,为了能够实时跟踪app的崩溃,需要接管系统的异常捕获接口,自己来收集保存崩溃现场信息。

下面简单说一下几个平台的异常崩溃捕获。

1.iOS

1.1 Exception

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
- (BOOL )install {
     if (NSGetUncaughtExceptionHandler ( )  != custom_exceptionHandler )
        oldhandler  = NSGetUncaughtExceptionHandler ( ) ;
    
     if (self ->_handlerEnable ) {
        NSSetUncaughtExceptionHandler ( &custom_exceptionHandler ) ;
     } else {
        DDLogWarning (@ "NSEXception handler disable" ) ;
     }
     return YES ;
}

- (BOOL )uninstall {
    NSSetUncaughtExceptionHandler (oldhandler ) ;
     return YES ;
}

1.2 Signal

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
- (BOOL )install {
     if (installed ) {
        DDLogError (@ "signal handler has been installed" ) ;
         return NO ;
     }
    
    custom_crash_stk. ss_size  = MAX (MINSIGSTKSZ ,  64 * 1024 ) ;
    custom_crash_stk. ss_sp  =  malloc (custom_crash_stk. ss_size ) ;
    custom_crash_stk. ss_flags  =  0 ;
    
     if (custom_crash_stk. ss_sp  == NULL ) {
         return NO ;
     }
    
     //替换信号处理函数栈,避免栈已经耗尽,导致进程退出
     if (sigaltstack ( &custom_crash_stk ,  0 )  <  0 )
         return NO ;
    
     if ( !sa_preHandlers ) {
        sa_preHandlers  =  ( struct sigaction * ) malloc ( sizeof ( struct sigaction )  * monitored_signals_count ) ;
         memset (sa_preHandlers ,  0 ,  sizeof ( struct sigaction )  * monitored_signals_count ) ;
     }
    
     struct sigaction sa ;
     memset ( &sa ,  0 ,  sizeof (sa ) ) ;
    sa. sa_flags  = SA_SIGINFO  | SA_ONSTACK ;
    sigemptyset ( &sa. sa_mask ) ;
    sa. sa_sigaction  =  &custom_signalHandler ;
    
     for  ( int i  =  0 ; i  < monitored_signals_count ; i ++ )  {
         if (sigaction (monitored_signals [i ] ,  &sa ,  ( struct sigaction * ) (sa_preHandlers +i ) )  !=  0 ) {
            DDLogError (@ "install signalHandler failed, uninstall it!" ) ;
             [self uninstall ] ;
             return NO ;
         }
     }
    
    installed  =  1 ;
    
     return YES ;
}

- (BOOL )uninstall {
     if (installed ) {
         if (custom_crash_stk. ss_sp ) {
             free (custom_crash_stk. ss_sp ) ;
            custom_crash_stk. ss_sp  = nil ;
         }
        
         for  ( int i  =  0 ; i  < monitored_signals_count ; i ++ )  {
             if (sigaction (monitored_signals [i ] ,  ( struct sigaction * ) (sa_preHandlers +i ) ,  0 )  !=  0 ) {
                 return NO ;
             }
         }
        
         if (sa_preHandlers )
             free (sa_preHandlers ) ;
        
        installed  =  0 ;
        
         return YES ;
     } else {
        DDLogError (@ "signalHandler already uninstalled!" ) ;
         return NO ;
     }
}

2.Cocos

2.1 Cocos-Lua

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
local  function handleLuaException (msg )
     if msg == nil  then  return  end

     local targetPlatform  = cc .Application :getInstance ( ) :getTargetPlatform ( )
     local supportObjectCBridge   =  false
     if  (cc .PLATFORM_OS_IPHONE  == targetPlatform )  or  (cc .PLATFORM_OS_IPAD  == targetPlatform )  or  (cc .PLATFORM_OS_MAC  == targetPlatform )   then
        supportObjectCBridge  =  true
     end

     local supportJavaBridge  =  false
     if  (cc .PLATFORM_OS_ANDROID  == targetPlatform )  then
        supportJavaBridge  =  true
     end

     if  (supportJavaBridge  ==  true )  then
         //...
     elseif  (supportObjectCBridge  ==  true )  then
         //...
     end
end

function __G__TRACKBACK__ (msg )
    handleLuaException (msg )
     return msg
end

2.2 Cocos-JS

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
//注册异常处理回调函数
void JSExceptionHandler ::registerJSExceptionHandler (JSContext  *cx )  {
    JS_SetErrorReporter (cx , JSExceptionHandler ::reportError ) ;
}

void JSExceptionHandler ::reportError (JSContext  *cx ,  const char  *message , JSErrorReport  *report )
{
     const char * format  =  "%s:%u:%s\n" ;
     const char * fileName  = report ->filename  ? report ->filename  :  "no filename" ;
    
    int bufLen  = strlen (format )  + strlen (fileName )  + strlen (message )  +  16 ;
    char * traceback  =  (char * )malloc (bufLen ) ;
    memset (traceback ,  0 , bufLen ) ;
    sprintf (traceback , format , fileName ,  (unsigned int ) report ->lineno , message ) ;
    
    
     //....
    
    free (traceback ) ;
} ;

3.U3D

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
//注册未处理异常回调
System . AppDomain . CurrentDomain . UnhandledException  += _OnUnhandledExceptionHandler ;

//注册日志回调
Application . RegisterLogCallback (_OnLogCallbackHandler ) ;

static  private  void _OnLogCallbackHandler ( string name,  string stack, LogType type )
{

      //…
}

private  static  void _OnUnhandledExceptionHandler ( object sender,  System . UnhandledExceptionEventArgs args )
{
     if  (args . ExceptionObject . GetType ( )  ==  typeof ( System . Exception ) )
     {
            //…      

     }
}


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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值