当前位置: 首页 > news >正文

网站网页设计制作公司汕头公众号建设网站

网站网页设计制作公司,汕头公众号建设网站,wordpress付费下载功能,dreamware做网站转载自#xff1a;http://blog.csdn.net/jasonblog/article/details/49909209 1. 相关API和数据结构 由于我们在上面回溯线程调用栈拿到的是一组地址#xff0c;所以这里进行符号化的输入输出应该分别是地址和符号#xff0c;接口设计类似如下#xff1a; - (NSString *)s… 转载自http://blog.csdn.net/jasonblog/article/details/49909209 1. 相关API和数据结构 由于我们在上面回溯线程调用栈拿到的是一组地址所以这里进行符号化的输入输出应该分别是地址和符号接口设计类似如下 - (NSString *)symbolicateAddress:(uintptr_t)addr; 不过在实际操作中我们需要依赖于dyld相关方法和数据结构 /** Structure filled in by dladdr().*/ typedef struct dl_info {const char *dli_fname; /* Pathname of shared object */void *dli_fbase; /* Base address of shared object */const char *dli_sname; /* Name of nearest symbol */void *dli_saddr; /* Address of nearest symbol */ } Dl_info;_dyld_image_count() returns the current number of images mapped in by dyld. Note that using this count to iterate all images is not thread safe, because another thread may be adding or removing images dur-ing duringing the iteration.   _dyld_get_image_header() returns a pointer to the mach header of the image indexed by image_index. If image_index is out of range, NULL is returned.   _dyld_get_image_vmaddr_slide() returns the virtural memory address slide amount of the image indexed by image_index. If image_index is out of range zero is returned.   _dyld_get_image_name() returns the name of the image indexed by image_index. The C-string continues to be owned by dyld and should not deleted. If image_index is out of range NULL is returned.12345678910111213141516171819202122232425261234567891011121314151617181920212223242526 又为了要判断此次解析是否成功所以接口设计演变为 bool jdy_symbolicateAddress(const uintptr_t addr, Dl_info *info) Dl_info用来填充解析的结果。 2. 算法思路 对一个地址进行符号化解析说起来也是比较直接的就是找到地址所属的内存镜像然后定位该镜像中的符号表最后从符号表中匹配目标地址的符号。 图片来源于苹果官方文档 以下思路是描述一个大致的方向并没有涵盖具体的细节比如基于ASLR的偏移量 // 基于ASLR的偏移量https://en.wikipedia.org/wiki/Address_space_layout_randomization /*** When the dynamic linker loads an image, * the image must be mapped into the virtual address space of the process at an unoccupied address.* The dynamic linker accomplishes this by adding a value the virtual memory slide amount to the base address of the image. */12345678910111234567891011 2.1 寻找包含地址的目标镜像 通过遍历每个段判断目标地址是否落在该段包含的范围内 /** The segment load command indicates that a part of this file is to be* mapped into the tasks address space. The size of this segment in memory,* vmsize, maybe equal to or larger than the amount to map from this file,* filesize. The file is mapped starting at fileoff to the beginning of* the segment in memory, vmaddr. The rest of the memory of the segment,* if any, is allocated zero fill on demand. The segments maximum virtual* memory protection and initial virtual memory protection are specified* by the maxprot and initprot fields. If the segment has sections then the* section structures directly follow the segment command and their size is* reflected in cmdsize.*/ struct segment_command { /* for 32-bit architectures */uint32_t cmd; /* LC_SEGMENT */uint32_t cmdsize; /* includes sizeof section structs */char segname[16]; /* segment name */uint32_t vmaddr; /* memory address of this segment */uint32_t vmsize; /* memory size of this segment */uint32_t fileoff; /* file offset of this segment */uint32_t filesize; /* amount to map from the file */vm_prot_t maxprot; /* maximum VM protection */vm_prot_t initprot; /* initial VM protection */uint32_t nsects; /* number of sections in segment */uint32_t flags; /* flags */ };/*** brief 判断某个segment_command是否包含addr这个地址基于segment的虚拟地址和段大小来判断*/ bool jdy_segmentContainsAddress(const struct load_command *cmdPtr, const uintptr_t addr) {if (cmdPtr-cmd LC_SEGMENT) {struct segment_command *segPtr (struct segment_command *)cmdPtr;if (addr segPtr-vmaddr addr (segPtr-vmaddr segPtr-vmsize)) {return true;} }}123456789101112131415161718192021222324252627282930313233343536123456789101112131415161718192021222324252627282930313233343536 这样一来我们就可以找到包含目标地址的镜像文件了。 2.2 定位目标镜像的符号表 由于符号的收集和符号表的创建贯穿着编译和链接阶段这里就不展开了而是只要确定除了代码段_TEXT和数据段DATA外还有个_LINKEDIT段包含符号表 The __LINKEDIT segment contains raw data used by the dynamic linker, such as symbol, string, and relocation table entries. 所以现在我们需要先定位到__LINKEDIT段同样摘自苹果官方文档 Segments and sections are normally accessed by name. Segments, by convention, are named using all uppercase letters preceded by two underscores (for example, _TEXT); sections should be named using all lowercase letters preceded by two underscores (for example, _text). This naming convention is standard, although not required for the tools to operate correctly. 我们通过遍历每个段比较段名称是否和__LINKEDIT相同 usr/include/mach-o/loader.h #define SEG_LINKEDIT __LINKEDIT123123 接着来找符号表 /*** 摘自《The Mac Hackers Handbook》* The LC_SYMTAB load command describes where to find the string and symbol tables within the __LINKEDIT segment.  * The offsets given are file offsets, so you subtract the file offset of the __LINKEDIT segment to obtain the virtual memory offset of the string and symbol tables.  * Adding the virtual memory offset to the virtual-memory address where the __LINKEDIT segment is loaded will give you the in-memory location of the string and sym- bol tables.*/12345671234567 也就是说我们需要结合__LINKEDIT segment_command见上面结构描述和LC_SYMTAB load_command见下面结构描述来定位符号表 /** The symtab_command contains the offsets and sizes of the link-edit 4.3BSD* stab style symbol table information as described in the header files* nlist.h and stab.h.*/ struct symtab_command {uint32_t cmd; /* LC_SYMTAB */uint32_t cmdsize; /* sizeof(struct symtab_command) */uint32_t symoff; /* symbol table offset */uint32_t nsyms; /* number of symbol table entries */uint32_t stroff; /* string table offset */uint32_t strsize; /* string table size in bytes */ };1234567891011121312345678910111213 如上述引用描述LC_SYMTAB和_LINKEDIT中的偏移量都是文件偏移量所以要获得内存中符号表和字符串表的地址我们先将LC_SYMTAB的symoff和stroff分别减去LINKEDIT的fileoff得到虚拟地址偏移量然后再加上_LINKEDIT的vmoffset得到虚拟地址。当然要得到最终的实际内存地址还需要加上基于ASLR的偏移量。 2.3 在符号表中寻找和目标地址最匹配的符号 终于找到符号表了写到这里有点小累直接贴下代码 /*** brief 在指定的符号表中为地址匹配最合适的符号这里的地址需要减去vmaddr_slide*/ const JDY_SymbolTableEntry *jdy_findBestMatchSymbolForAddress(uintptr_t addr,JDY_SymbolTableEntry *symbolTable,uint32_t nsyms) {// 1. addr symbol.value; 因为addr是某个函数中的一条指令地址它应该大于等于这个函数的入口地址也就是对应符号的值// 2. symbol.value is nearest to addr; 离指令地址addr更近的函数入口地址才是更准确的匹配项const JDY_SymbolTableEntry *nearestSymbol NULL;uintptr_t currentDistance UINT32_MAX;for (uint32_t symIndex 0; symIndex nsyms; symIndex) {uintptr_t symbolValue symbolTable[symIndex].n_value;if (symbolValue 0) {uintptr_t symbolDistance addr - symbolValue;if (symbolValue addr symbolDistance currentDistance) {currentDistance symbolDistance;nearestSymbol symbolTable symIndex;}}}return nearestSymbol; }/** This is the symbol table entry structure for 64-bit architectures.*/ struct nlist_64 {union {uint32_t n_strx; /* index into the string table */} n_un;uint8_t n_type; /* type flag, see below */uint8_t n_sect; /* section number or NO_SECT */uint16_t n_desc; /* see mach-o/stab.h */uint64_t n_value; /* value of this symbol (or stab offset) */ };1234567891011121314151617181920212223242526272829303132333435363738394012345678910111213141516171819202122232425262728293031323334353637383940 找到匹配的nlist结构后我们可以通过.n_un.n_strx来定位字符串表中相应的符号名。
http://www.zqtcl.cn/news/136493/

相关文章:

  • 一个学校怎么制作网站阿里云服务器登录
  • 网站建设哪家合适对网站建设服务公司的看法
  • 网站留住访客柳州正规网站建设加盟
  • 网站照片要求现在百度怎么优化排名
  • 国外经典平面设计网站60平米一居室装修价格
  • 网站建设选择题个人游戏网站备案
  • 深圳企业网站制作公司wordpress 自定义插件开发
  • 网站代付系统怎么做iis不能新建网站
  • 廉政网站建设做环保的网站有哪些
  • 做彩票网站违法网站邮箱后台子域名
  • 响应式中文网站模板wordpress 模特模板
  • 专业做影楼招聘网站有哪些中铁建设集团登陆
  • 室内设计工作室网站怎么做前端开发面试会被问到的一些问题
  • 六安网站建设网络服务30分钟seo网站
  • 网站开发难点谁会制作网站
  • 北京通州网站制作公司设计网站中企动力优
  • 网站地图生成器横琴人寿保险公司官网
  • 免费建站网站一级大录像不卡专业团队建设方案
  • 创建网站的目的是什么想自己建个网站
  • 网站开发公司有什么福利龙岩几个县
  • 网站镜像做排名成都网站开发
  • 江西建设推广网站苏州 网站的公司
  • 中山民众网站建设有一个网站专门做民宿
  • 快速建站完整版兰州兼职做网站
  • 西安网站群搭建php网站开发设计
  • 网站首页没收录php做的网站源代码
  • 网站搭建技术要求企业网站推广的一般策略
  • 网站建设流程行业现状安阳历史
  • 制作软件的网站装饰工程设计东莞网站建设
  • 如何不花钱开发网站搜索引擎营销原理是什么