版权声明:本文为原创文章,转载请声明http://www.cnblogs.com/unityExplorer/p/7574569.html

这两天博主在接微信支付SDK的时候碰到一个非常恶心又诡异的问题——proto序列化和反序列化的无辜崩溃

上图就是博主遇到这个问题时正在调试微信支付的核心协议,博主在序列化和反序列化该消息的字节组时,unity就会立马崩溃,遇到过unity崩溃的朋友应该都知道,unity会给出两个用于查找问题的文件,一个crash.dmp和一个error.log

error.log文件会输出堆栈的二进制数据,表示看不懂,所以只能看crash.dmp这个错误报告文件了

如果电脑上装了vs,可以直接打开,打开后显示如下

提示的意思简单点说就是内存越界,然而,经过博主调试后发现导致unity崩溃的函数就是protobuf-net.dll提供的反序列化函数

----> Serializer.Serialize<IExtensible>();

然而直到这个并没有什么卵用,因为根本无法锁定到问题的核心所在

于是博主开始各种尝试:

首先,怀疑命名问题,因为协议中定义了一些看起来可能会冲突的名字:比如package

于是,博主注释掉这些看起来可疑的属性,包括appId、return_code、return_msg、err_code、err_code_des、package,结果是依然崩溃

然后继续注释掉notify_url、sign,结果没有崩溃

所以博主开始怀疑是notify_url、sign这两个属性搞的鬼,于是分开取消注释测试,发现不论取消注释哪一个,都会崩溃

好吧,凌乱了,毫无头绪,尤其是在随便更改这些属性的命名后都一样后就更加没有头绪了

所以最后不得不得出结论:并不是命名的问题

再想到文件大小的问题,博主为了省事,将所有的协议全部打包到一个cs文件中,最终这个文件有378kb,8000+行代码,这个量严格来说不算大,毕竟过万行代码的多得是

但是确实也想不到其他的可能了

按照这个思路,博主将最终生成的类文件分成多个,测试后发现还是崩溃

那么也不是文件大小的问题,这下就无奈了,错误报告太简单,解决方案也太诡异,实在无法找到错误原因,按道理unity的日志应该不会这么简单

于是,就去查unity自己的日志文件,地址如下

打开后,总算发现了一些端倪

在日志文件最底部,崩溃前的堆栈日志说明,崩溃的元凶就是proto的序列化,但是最后的utf16_to_utf8_len是什么鬼,博主表示看不懂

但是意思应该就是编码格式的转换问题了

回到协议内容一看,发现这个协议有个特点,全都是string,好吧,虽然这个可能有点扯,并且可能还不是核心,但是先试试吧

把所有的类型全部换成int,奇迹出现了,没有崩溃

再来,全部还原,然后只把appId的类型改成int,结果没有崩溃

好吧,貌似是类型全都是string的原因,但是前面只有4个属性的时候没有崩溃又是什么原因,况且也并不是没有出现过全部都是string的协议

再试试别的可能,比如修改必要性,把appId改为required等等等。。。。

经过一番测试,终于得出了如下结论(unity版本5.6.2,protobuf-net.dll版本2.3.2):

单个协议全部是optional string的情况下

修改其中一条属性类型为int或bool时,不会崩溃
修改其中一条属性为required时,不会崩溃
减少单个协议的属性数量到4个,不会崩溃,超过或等于5个,崩溃

总结:所有属性全为optional时,属性类型不能全部为string,反之则不能全为optional

上面的问题不知道大家有没有遇到过,希望大家没有遇到过,一次就能恶心半天了。

虽然问题解决了,但还是知其然不知其所以然,如果有朋友知道本质原因,希望可以分享

unity探索者之protobuf的序列化和反序列化导致unity崩溃的问题研究的更多相关文章

  1. Unity中进程间通信——使用Protobuf-net序列化与反序列化

    基于ProtoBuf协议实现网络传输(上) Protobuf 全称Protocol Buffers 是一种轻便高效的结构化数据存储格式,可以用于结构化数据串行化,很适合做数据存储或 RPC 数据交换格 ...

  2. [Go] 使用protobuf进行序列化和反序列化

    先定义消息类型 orders.proto syntax = "proto2"; package message; message Orders { required int32 o ...

  3. Unity使用protobuf-net进行二进制序列化与反序列化

    Protobuf-net提供的一种易于使用的数据序列化方案,可序列化带有[ProtoContract]特性的类实例,并可支持Unity各个发布平台,且效率高.易用性强. public static c ...

  4. Json序列化与反序列化导致多线程运行速度和单线程运行速度一致问题

    紧跟上篇文章 十个进程开启十个bash后一致写入命令执行完毕之后产生了很多很多的文件,博主需要对这些文件同意处理,也就是说对几十万个文件进行处理,想了又想,单线程处理那么多数据肯定不行,于是乎想到了使 ...

  5. 序列化和反序列化及Protobuf 基本使用

    序列化和反序列化 序列化和反序列化在平常工作中会大量使用,然而并不一定非常清楚它的概念.序列化和反序列化的选型却是系统设计或重构一个重要的环节,在分布式.大数据量系统设计里面更为显著.机器间的通信需要 ...

  6. windows环境下protobuf的java操作{编译,序列化,反序列化}

    google protocol buffer的使用和原理 概况: Protocol Buffers(也就是protobuf)是谷歌的语言中立的.平台中立的.可扩展的用于序列化结构化的数据: windo ...

  7. C# 使用 protobuf 进行对象序列化与反序列化

    protobuf 是 google的一个开源项目,可用于以下两种用途: (1)数据的存储(序列化和反序列化),类似于xml.json等: (2)制作网络通信协议. 源代码下载地址:https://gi ...

  8. ProtoBuf序列化和反序列化方法

    最近公司需要将以前的协议全都改成ProtoBuf生成的协议,再将结构体打包和解包过程终于到一些问题 ,无法使用Marshal.SizeOf计算结构体大小,最后找了一下ProtoBuf的文档,可以用它自 ...

  9. unity 序列化和反序列化

    什么是序列化和反序列化(1)序列化是指把对象转换为字节序列的过程,而反序列化是指把字节序列恢复为对象的过程:.  (2)序列化:对象序列化的最主要的用处就是在传递和保存对象的时候,保证对象的完整性和可 ...

随机推荐

  1. Ubuntu Server 19.04配置静态IP

    这个/etc/netplan下默认有个文件50-cloud-init.yaml,直接修改它就行了 sudo vim /etc/netplan/50-cloud-init.yaml 网口名字enp0s3 ...

  2. idea 导入eclipse play1.2.7项目

    1.play eclipsify #myapp 转为eclipse目录结构 2.导入eclipse,一路next. 3.新增个Application -Xms1536m-Xmx2048m-Xdebug ...

  3. React Native 控制一个component的显示隐藏

      // 首先在constructor里:   this.state = { visible: false }   // 然后在点击事件设置:   this.setState({ visible: t ...

  4. 统计M

    链接:https://vjudge.net/problem/UVA-1586 题意:给出一分子化学式,包含C,N,O,H四种元素,求M 题解:这是字符串题.分为几种情况:第一种是一个原子:第二种是多原 ...

  5. 细说JavaScript 导出 上万条Excel数据

    首先这是个鸡肋的方法 合理的做法是 后端直接生成 前端给个链接就行了 (先说原因与过程最后上代码) 1. 先说说为什么会出现这个需求吧. : 在写运维网站时 自己粗略的看了一下bootstarp-ta ...

  6. Spring中与bean有关的生命周期

    前言 记得以前的时候,每次提起Spring中的bean相关的生命周期时,内心都无比的恐惧,因为好像有很多,自己又理不清楚,然后看网上的帖子,好像都是那么一套,什么beanFactory啊,aware接 ...

  7. 关于C语言内存占用

    struct T { char a; int *d; int b; int c:16; double e; }; T *p; 在64位系统以及64位编译器下,以下描述正确的是 A. sizeof(p) ...

  8. 如何用Excel进行预测分析?

      [面试题] 一个社交APP, 它的新增用户次日留存.7日留存.30日留存分别是52%.25%.14%. 请模拟出来,每天如果日新增6万用户,那么第30天,它的日活数会达到多少?请使用Excel进行 ...

  9. API返回延迟,FPM重启后恢复之后又重现 问题解决方案

    背景 最近在提供后台API时,提供了一个简单逻辑的接口 部署在测试环境,自测没问题,提交测试 突然有一天,接口响应延迟严重,几乎每次都是3-4秒返回 这对于一个接口来说,肯定是有问题的 于是便有了以下 ...

  10. 安装 kreas 2.2.4 版本问题

    python 版本 3.6 不要使用 3.7 和 3.8 否则导致安装失败 tensorflow 使用 1.12.0 keras 使用 2.2.4 版本 pip install 包名 -i http: ...