Xamarin.Forms集成Android动态库与OpenCV遇DllNotFoundException问题
问题描述
在Xamarin.Forms(仅Android)项目中,原本正常工作的C动态共享库libMathFuncs.so及对应的C#包装器,在配置引入Android版OpenCV原生库后(未在代码中实际调用OpenCV),编译可成功通过,但运行时调用C函数会抛出异常:
System.DllNotFoundException: 'libMathFuncs.so assembly: type: member:(null)'
已尝试的配置修改
针对C++动态库项目的Visual Studio配置,已做如下调整:
- STL设置:试过LLVM libc++静态库(
c++_static)和共享库两种选项 - C++编译配置:
- 附加包含库/VC++外部包含目录添加了OpenCV的
include路径 - 启用C++异常(
-fexceptions) - 启用运行时类型信息(
-frtti) - 禁用预编译头
- 附加包含库/VC++外部包含目录添加了OpenCV的
- 链接器配置:尝试两种方式
- 输入->附加依赖项直接添加
libopencv_java4.so的完整路径 - 常规->附加库目录添加OpenCV的
arm64-v8a库路径,输入->库依赖项添加opencv_java4
- 输入->附加依赖项直接添加
环境信息
- Visual Studio 2022
- Xamarin.Forms(仅Android)
- 目标API级别:Android 9.0(Pie,android-28)
- Android NDK:R23C
- 测试设备:Nokia 8.1(Android 11)
排查与解决方案建议
- 检查.so文件部署情况
- 确认Xamarin Android项目中,
libMathFuncs.so已正确放置在lib/arm64-v8a目录下,且生成操作设置为AndroidNativeLibrary;同时必须将OpenCV的libopencv_java4.so也部署到同一目录,因为动态库已链接OpenCV,运行时依赖该库。
- 确认Xamarin Android项目中,
- 验证动态库依赖关系
- 使用NDK自带的
readelf工具(路径示例:NDK_ROOT/toolchains/llvm/prebuilt/windows-x86_64/bin/aarch64-linux-android-readelf)执行命令,查看库的依赖项:
若输出包含readelf -d libMathFuncs.so | grep NEEDEDlibopencv_java4.so,则必须确保该库存在于设备可加载路径中。
- 使用NDK自带的
- 调整OpenCV链接方式
- 若使用动态链接,必须打包OpenCV的.so文件;若想静态链接,需改用OpenCV SDK中
staticlibs目录下的静态库文件,同时保持STL版本一致(静态链接OpenCV时,STL需用静态版本,避免冲突)。
- 若使用动态链接,必须打包OpenCV的.so文件;若想静态链接,需改用OpenCV SDK中
- 确认架构完全匹配
- 确保C++动态库和OpenCV库均为
arm64-v8a架构,禁止混用x86或armeabi-v7a版本的库。
- 确保C++动态库和OpenCV库均为
- 检查DllImport声明正确性
- 确认C#包装器中的
[DllImport]声明格式正确,示例:
注意库名只需写[DllImport("MathFuncs", EntryPoint = "你的函数名", CallingConvention = CallingConvention.Cdecl)] public static extern 返回类型 函数名(参数类型 参数);MathFuncs,Android会自动补全lib前缀和.so后缀。
- 确认C#包装器中的
- 清理重建项目
- 删除C++动态库项目和Xamarin Android项目的
bin、obj目录,清理缓存后重新编译部署,避免旧文件干扰。
- 删除C++动态库项目和Xamarin Android项目的
内容的提问来源于stack exchange,提问作者Reza
相关产品推荐
相关产品推荐

