golang 捕获 C/C++ 错误并做善后处理
cgo 里 crash
cgo 中的 crash ,在 golang 中是捕获不到信号量的,诸如信号量 SIGSEGV
未曾逆向思维,考虑过是否在 cgo 里做信号量捕获,今日试了下,是可以的
即,golang 调用 c 代码,可以保证进程不会无故消失,以及做不少善后处理:
- 告警
- coredump 捕获
例子
本人实验了下,例子如下
https://github.com/fananchong/test_cgo_coredump/blob/master/main2.go
分 2 步走:
1. C 代码捕获异常并导出
#include "catch_except.h"
#include <stdio.h>
#include <signal.h>
#include <stdlib.h>
#include <string.h>static void print_core(int signum, siginfo_t *info, void *secret, struct sigaction *oldact) {printf("crash signum:%d si_code:%d\n", signum, info->si_code);// do something ...oldact->sa_sigaction(signum, info, secret);
}static struct sigaction oldabrtact;
static void abrtsigaction(int signum, siginfo_t *info, void *secret) {print_core(signum, info, secret, &oldabrtact);
}static struct sigaction oldsegvact;
static void segvsigaction(int signum, siginfo_t *info, void *secret) {print_core(signum, info, secret, &oldsegvact);
}void sigsetup(void)
{struct sigaction act;memset(&act, 0, sizeof act);act.sa_flags = SA_ONSTACK | SA_SIGINFO;act.sa_sigaction = segvsigaction;sigaction(SIGSEGV, &act, &oldsegvact);act.sa_sigaction = abrtsigaction;sigaction(SIGABRT, &act, &oldabrtact);
}
#pragma once#if __cplusplus
extern "C"
{#endifextern void sigsetup(void);#if __cplusplus
}
#endif
2. golang 代码中安装异常捕获
func main() {C.sigsetup()// ... 略 ...
}
测试输出
[fananchong@qa3-haidao test_cgo_coredump]$ ./main2
sigsetup ...
test_crash from C and here the str is from Go: From Golang
Argument deadbeef
main2: test.cpp:11: void fn2(char*): Assertion `1 == 2' failed.
crash !!!!
其他
使用中,发现几个细节:
- 这种方式可以完美的捕获 C++ 调用栈
- cgo 中处理异常,无法区分来自 golang 还是 c
- 因此,若要线上跑,可以把使用 cgo 模块单独拎出来做成无状态服务
- 使用它的服务与他放在同一个 pod 中,使用 unix socket 通信
- 举例如, battle server 与 c battle api server
参考
- https://www.zhihu.com/column/p/24023766
- https://github.com/rtxu/articles/tree/master/2016-11-08-signal-handler-bug-in-golang-runtime
golang 捕获 C/C++ 错误并做善后处理相关推荐
- Handling Errors Exceptionally Well in C++ 在C++中良好地捕获意外的错误
Handling Errors Exceptionally Well in C++ 在C++中良好地捕获意外的错误 from:http://www.cprogramming.com/tutorial/ ...
- php捕获Fatal error错误与异常处理
php捕获Fatal error错误与异常处理 参考文章: (1)php捕获Fatal error错误与异常处理 (2)https://www.cnblogs.com/jkko123/p/108403 ...
- UncaughtExceptionHandler:java未捕获的异常/错误默认处理方式
UncaughtExceptionHandler:java未捕获的异常/错误 @(JAVA)[java] java有一部分异常属于运行时异常,这类异常发生时通过会导致程序发生错误,导致退出.如数据下标 ...
- js捕获网络请求错误,获取http状态码等信息
js捕获网络请求错误,获取http状态码等信息 第一种:使用$.ajax $(".login").click(function(){$.ajax({type: "POST ...
- Golang tcp转发 remoteAddr错误
Golang tcp 转发 第一版本 accept获取的Conn里的localAddr做为源地址,remoteAddr来做为目的地址 // tcpForward package mainimport ...
- 1、ThinkPHP源码学习-致命错误捕获及自定义错误输出
首先在 Think\Think::start() 静态方法中,使用 register_shutdown_function 函数注册致命错误处理方法. register_shutdown_functio ...
- php类方法语法错误捕获,php语法错误捕获
PHP语法错误捕获处理 一般捕获错误使用的方法是:try{ ... }catch(Exception $e){ echo $e->getMessage(); } 或者set_exception_ ...
- 如何优化Golang中重复的错误处理
在看<Go入门指南>的一种用闭包处理错误的模式时,里面提到了一种错误的优雅处理方式,减少我们重复写if err:=f(); err != nil{}式的代码,感觉很心动,做了下测试,结论如 ...
- laravel 异常捕获_Laravel框架捕获各种类型错误
Laravel 中的所有异常都由类App\Exceptions\Handler集中处理,这个类有两个方法:report 和 render. [report 方法] report 方法用于记录异常并将其 ...
最新文章
- Pytorch | BERT模型实现,提供转换脚本【横扫NLP】
- Python报错:IndentationError: unindent does not match any outer indentation level解决办法
- 图论 —— 最短路 —— Floyd 算法
- 解决 maps to localhost, but this does not map back to the address
- 【Kubernetes】浅析基本概念和原理
- golang for range原理(转载)
- (转)Struts2快速入门
- linux 内核空间与用户空间
- 【Codeforces	1344	A】Hilbert‘s Hotel,哈希表,set维护
- iOS打包需要注意的事项
- mysql2 connector_2.升级mysql-connector 5到8遇到的问题
- 企业级的Java快速开发平台,首选iMatrix平台。
- scrapy爬虫总结
- Word VBA 表格宏处理
- android 阻尼动画,Android阻尼效果 | 自定义进阶之实现MIUI的拖动视差效果
- HDU 2154 跳舞毯
- Git取消add 、 commit、push的命令
- Django:在DDTCMS中使用Photologue做相册并增加封面的探索
- OpenCV_Viz——OpenCV中Viz的模块编译的无法解析的外部符号BUG
- 【LaTeX教程】九.Latex常见数学公式模板
热门文章
- jQuery MiniUI 快速入门:Hollo, world!(二)_nikofan-ChinaUnix博客
- 用python实现新年祝福微信的自动回复
- 网页设计与制作第三节文字(页面设计与制作答案)
- Vue 中 v-if 和 v-show 的区别和用法
- 炒股第一招【看盘技巧】
- liunx关闭端口命令
- 前端HTML5视频_CSS3-张晓飞-专题视频课程
- jupyter notebook如何查看函数
- 在System.Timers.Timer的处理程序中调用MessageBox.Show()弹出的确是非模态的
- 【AIGC使用教程】AutoGPT 安装使用完全教程