You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Cocos2d-x iOS项目集成Firebase Crashlytics捕获C++崩溃求助

解决Cocos2d-x C项目Firebase Crashlytics无法捕获C崩溃的方案

1. 实现C++信号与异常捕获逻辑

Firebase Crashlytics默认仅处理Objective-C/Swift层面崩溃,C++的信号异常(如SIGSEGV、SIGABRT)和未捕获std::exception需手动捕获后上报。

在项目中添加C++信号处理模块(如CrashHandler.cpp):

#include <signal.h>
#include <execinfo.h>
#include <unistd.h>
#include <string>
#include "CrashReporterBridge.h"

void signalHandler(int signal) {
    // 获取调用栈信息
    void* callstack[128];
    int frames = backtrace(callstack, 128);
    char** strs = backtrace_symbols(callstack, frames);
    
    std::string crashLog;
    for (int i = 0; i < frames; ++i) {
        crashLog += strs[i];
        crashLog += "\n";
    }
    free(strs);
    
    // 通过桥接层上报到Crashlytics
    reportCrashToFirebase(crashLog, signal);
    
    // 恢复默认信号处理,让程序正常终止
    signal(signal, SIG_DFL);
    raise(signal);
}

void setupCrashHandlers() {
    // 注册常见崩溃信号
    signal(SIGSEGV, signalHandler);
    signal(SIGABRT, signalHandler);
    signal(SIGILL, signalHandler);
    signal(SIGFPE, signalHandler);
    signal(SIGBUS, signalHandler);
}

2. 编写Objective-C++桥接层

创建CrashReporterBridge.mm作为C++与Firebase Crashlytics OC API的桥接:

#include "CrashReporterBridge.h"
#import <FirebaseCrashlytics/FirebaseCrashlytics.h>

extern "C" void reportCrashToFirebase(const std::string& crashLog, int signal) {
    NSString* logStr = [NSString stringWithUTF8String:crashLog.c_str()];
    NSString* signalStr = [NSString stringWithFormat:@"Signal Code: %d", signal];
    
    // 记录自定义崩溃日志
    [[FIRCrashlytics crashlytics] logWithFormat:@"%@\nCall Stack:\n%@", signalStr, logStr];
    
    // 主动上报异常模型到Crashlytics
    [[FIRCrashlytics crashlytics] recordExceptionModel:[[FIRExceptionModel alloc] 
        initWithName:@"C++ Runtime Crash" 
        reason:@"Uncaught signal or exception" 
        userInfo:@{@"CallStack": logStr, @"Signal": @(signal)}]];
}

配套头文件CrashReporterBridge.h:

#ifndef CrashReporterBridge_h
#define CrashReporterBridge_h

#include <string>

extern "C" void reportCrashToFirebase(const std::string& crashLog, int signal);

#endif

3. 整合到Cocos2d-x启动流程

在AppDelegate.cpp的applicationDidFinishLaunching方法中,初始化Firebase后启动崩溃捕获:

#include "CrashHandler.h"

bool AppDelegate::applicationDidFinishLaunching() {
    // 初始化Firebase(已完成步骤)
    [FIRApp configure];
    
    // 启动C++崩溃捕获
    setupCrashHandlers();
    
    // 其他Cocos2d-x初始化逻辑...
    return true;
}

4. 捕获未处理C++异常

修改Cocos2d-x主循环代码(如iOS平台的CCApplication-ios.mm中的run方法),添加异常捕获:

int Application::run() {
    // ... 原有代码
    
    while (!m_bExit) {
        try {
            mainLoop();
        } catch (const std::exception& e) {
            std::string crashLog = "Uncaught std::exception: " + std::string(e.what());
            reportCrashToFirebase(crashLog, 0);
            throw; // 重新抛出以触发程序终止,确保Crashlytics捕获完整事件
        } catch (...) {
            reportCrashToFirebase("Uncaught unknown C++ exception", 0);
            throw;
        }
    }
    
    // ... 原有代码
}

5. 测试注意事项

  • 必须在Release模式下测试,Debug模式下Xcode调试器会拦截崩溃,导致Crashlytics无法上报。
  • 崩溃后需重启App,Crashlytics会在下次启动时同步崩溃日志。
  • 可手动触发测试崩溃(如*(int*)0 = 0;),验证Firebase控制台是否能收到崩溃信息。

内容的提问来源于stack exchange,提问作者Shiv

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.01 11:57:19