最近开发一个android app的时候碰到个问题,这个app在native层加载了几个动态so库,其中有一个A库内部又动态加载了B库,且A库与B库有相同的全局变量,但因为两个库是分开动态加载的,导致实际上在两个库内部这个全局变量是各自独立的,说白了就是有2份全局变量互不影响。但实际使用上全局变量是要能共享使用的,因此就想到是否可以使用共享内存的方式来实现共享。
首先研究了一下android的共享内存机制,发现android提供了匿名共享内存机制,但匿名共享内存有个问题是通过文件句柄fd的传递来达到进程间共享的目的,而且这个fd的传递是通过Java层Binder传递的,对于我这个同一进程内的native层传递来说不太好用,于是转而研究具名共享内存的使用,即通过mmap映射文件的方式创建共享内存。
实际开发时发现android是没有提供shm_open函数的,不过这也无所谓,反正shm_open内部也是通过open打开一个文件而已,所以直接就使用open来打开文件获取fd,然后通过mmap映射文件获取共享内存地址。这里有个小插曲,原来想着反正是进程内的共享,也是临时性的共享,没必要回写磁盘,于是mmap时使用了MAP_PRIVATE模式,想着可以提升点效率,但实际测试发现我还是想当然了,虽然是同一进程内各自进行的2次mmap,但mmap出来的内存实际是不共享的。没办法还是改回MAP_SHARED模式,此时就可以共享内存了,也算解决了这个比较奇葩的使用场景,写个小作文记录一下。