温馨提示×

温馨提示×

您好,登录后才能下订单哦!

密码登录×
登录注册×
其他方式登录
点击 登录注册 即表示同意《亿速云用户服务条款》

用php读取elf结构的方法

发布时间:2020-12-22 09:58:48 阅读:202 作者:小新 栏目:编程语言
PHP开发者专用服务器限时活动,0元免费领,库存有限,领完即止! 点击查看>>

这篇文章给大家分享的是有关用php读取elf结构的方法的内容。小编觉得挺实用的,因此分享给大家做个参考。一起跟随小编过来看看吧。

前提知识
  1. UNIX系统的可执行文件都采用ELF格式,类型分为目标文件、可执行文件和共享库

  2. ELF格式探析之三:sections

  3. 本例基于64位的小端序linux机器

以读取目标文件hello.o为例
#include <stdio.h>
void say_hello(char *who) {
    printf("hello, %s!\n", who);
}
char *my_name = "wb";
int man() {
    say_hello(my_name);
    return 0;
}
// 执行gcc -c hello.c生成hello.o
目标文件elf结构主要有:
  1. ELF header,位于文件的0~64字节,存储文件的描述信息,Section header table的起始位置

  2. N个Section

  3. Section header table,每个条目64字节,对应一个Section的信息

  4. Program header table,可执行文件需要,本例的hello.o没有

进一步分析elf结构
  1. 首先用readelf命令读取elf信息:readelf -h hello.o。总结如下:

  2. ELF header占用64字节

  3. N个Section占用6488-64-1472=4952字节

  4. Section header table占用23*64=1472字节

readelf -h hello.o
ELF Header:
Class:                             ELF64
Data:                              2's complement, little endian
OS/ABI:                            UNIX - System V
Type:                              REL (Relocatable file)
Machine:                           Advanced Micro Devices X86-64
Start of program headers:          0 (bytes into file)
Start of section headers:          5016 (bytes into file) //Section header table的起始位置
Size of this header:               64 (bytes) //ELF header的占用大小
Size of program headers:           0 (bytes)  //hello.o没有program header table
Number of program headers:         0          //hello.o没有program header table
Size of section headers:           64 (bytes) //Section header table每个条目占用大小
Number of section headers:         23         //Section header table条目个数
Section header string table index: 22         //.shstrtab Section位于Section header table第22个条目
用php读取.shstrtab Section内容
  1. .shstrtab Section其实是存储的所有Section的名字

<?php
$fp fopen("hello.o""rb");

fseek($fp40, SEEK_SET);
$sh_off fread($fp8);
$sh_off unpack("P"$sh_off);
var_dump("section header offset in file: "$sh_off[1]);

fseek($fp10, SEEK_CUR);
$sh_ent_size fread($fp2);
$sh_ent_size unpack("v"$sh_ent_size);
var_dump("section header entry size: "$sh_ent_size[1]);

$sh_num fread($fp2);
$sh_num unpack("v"$sh_num);
var_dump("section header number: "$sh_num[1]);

$sh_strtab_index fread($fp2);
$sh_strtab_index unpack("v"$sh_strtab_index);
var_dump("section header string table index: "$sh_strtab_index[1]);

fseek($fp$sh_off[1] + $sh_strtab_index[1] * $sh_ent_size[1], SEEK_SET);
fseek($fp24, SEEK_CUR); //sh_name(4) + sh_type(4) + sh_flags(8) + sh_addr(8) = 24
$str_table_off fread($fp8);
$str_table_off unpack("P"$str_table_off);
var_dump("section name string table offset: "$str_table_off[1]);

$str_table_size fread($fp8);
$str_table_size unpack("P"$str_table_size);
var_dump("section name string table size: "$str_table_size[1]);

fseek($fp$str_table_off[1], SEEK_SET);
$str fread($fp$str_table_size[1]);
print_r(explode("\x00"trim($str"\x00")));

// 读取所有Section条目信息
for ($i =0;$i $sh_num[1]; $i ++) {
    fseek($fp$sh_off[1] + $i $sh_ent_size[1], SEEK_SET);
    $sh_name fread($fp4);
    $sh_name unpack("V"$sh_name);
    fseek($fp20, SEEK_CUR); //sh_type(4) + sh_flags(8) + sh_addr(8) = 20
    $sh_offset fread($fp8);
    $sh_offset unpack("P"$sh_offset);

    $sh_size fread($fp8);
    $sh_size unpack("P"$sh_size);

    printf("section: %2s name: %-24s offset: %12s size: %12s\n"$iget_section_name($sh_name[1]), $sh_offset[1], $sh_size[1]);
}

function get_section_name($start{
    global $str;
    $name substr($str$start);
    return strstr($name"\x00"true);
}

感谢各位的阅读!关于用php读取elf结构的方法就分享到这里了,希望以上内容可以对大家有一定的帮助,让大家可以学到更多知识。如果觉得文章不错,可以把它分享出去让更多的人看到吧!

亿速云「云服务器」,即开即用、新一代英特尔至强铂金CPU、三副本存储NVMe SSD云盘,价格低至29元/月。点击查看>>

向AI问一下细节

免责声明:本站发布的内容(图片、视频和文字)以原创、转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系站长邮箱:is@yisu.com进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。

AI

开发者交流群×