十年匠心定制 · 商业建站与技术教学双线并行 咨询热线:400-886-1026 service@lmnt.cn
ARTICLE DETAIL

资讯详情

深耕网站建设与运营推广的一线实战洞察。

Marshalling 实战:C# 字符串到 C 指针的安全穿越指南

Marshalling 实战:C# 字符串到 C 指针的安全穿越指南 开场:凌晨两点,游戏服务器的崩溃日志疯狂刷屏。你刚接入的某个 C 库通过 P/Invoke 传回了一串乱码,Profiler 指着托管堆里某个string的地址,而那个对象已经被 GC 悄悄搬走了。这种跨语言调用的噩梦,几乎每个 Unity 开发者都遇到过。当你把 C# 字符串塞进DllImport的那一刻,CLR 就要把它翻译成 C 端能懂的char*。这个翻译过程就是 Marshalling(封送)。它不是一行[MarshalAs]注解那么简单,而是数据格式、内存布局、GC 生命周期三方规则的精密博弈——任何一方理解不到位,换来的就是乱码、泄漏或玄学崩溃。本文沿着一个字符串从托管堆到非托管内存的完整旅程,把每一步"内部怎么走、为何这么设计"讲透,最后给出 Unity 工程的落地清单。一、两个世界的字符串:为什么必须"翻译"要理解封送,先看双方的数据结构差异有多大:C#string:托管堆上的对象,UTF-16 编码,带对象头与长度字段,不可变(immutable),地址随时可能被 GC 压缩堆时移动。Cchar*:指向一段连续字节的裸指针,编码可能是 ANSI/UTF-8/UTF-16,以\0结尾(长度不靠字段,靠扫描终止符),地址固定但生命周期全
返回列表