- 控制传入的index参数(Reloc表项偏移)到可控内存
- 控制Reloc表项r_info字段,进而控制dynsym表项到可控内存
- 控制dynsym表项name字段,指向想要执行的函数(system)
符号表结构
typedef struct
{
Elf32_Word st_name;//符号名,在字符串表中的下标
Elf32_Addr st_value;
//目标文件中, 如st_shndx不为SHN_COMMON,表示符号段内偏移
//否则表示对齐属性
//可执行文件 or动态链接库, 表示虚拟地址
Elf32_Word st_size; //符号大小(字节)
unsigned char st_info;//类型和绑定信息
//低四位:Type
//STT_NOTYPE 未知类型
//STT_OBJECT 数据对象
//STT_FUNC 函数或代码
//STT_SECTION 段 对应STB_LOCAL
//STT_FILE 文件名 对应STB_LOCAL,st_shndx为SHN_ABS
//
//高四位:绑定信息
//STB_LOCAL
//STB_GLOBAL
//STB_WEAK
unsigned char st_other; //0
Elf32_Half st_shndx; //符号所在段
//SHN_ABS 0xff1 绝对值
//SHN_COMMON 0xff2 "COMMON块" 未初始化全局符号
//SHN_UNDEF 0 未定义,定义在其它模块
}
重定位表结构
typedef struct
{
Elf32_Addr r_offset;//重定位入口
//可重定位文件: 段内偏移
//EXE or Shared Lib: 虚拟地址
Elf32_Word r_info;
//重定位入口类型和符号
//低8位: 类型 高24位,对应符号表中的下标
}
64位如何分析 ?
符号表结构
typedef struct elf64_sym {
Elf64_Word st_name; /* Symbol name, index in string tbl */
unsigned char st_info; /* Type and binding attributes */
unsigned char st_other; /* No defined meaning, 0 */
Elf64_Half st_shndx; /* Associated section index */
Elf64_Addr st_value; /* Value of the symbol */
Elf64_Xword st_size; /* Associated symbol size */
} Elf64_Sym;
重定位表结构
typedef __u16 Elf64_Half;
typedef __u32 Elf64_Word;
typedef __u64 Elf64_Addr;
typedef __u64 Elf64_Xword;
typedef __s64 Elf64_Sxword;
typedef struct elf64_rela {
Elf64_Addr r_offset; /* Location at which to apply the action */
Elf64_Xword r_info; /* index and type of relocation */
Elf64_Sxword r_addend; /* Constant addend used to compute value */
} Elf64_Rela;
#define ELF64_R_SYM(i) ((i) >> 32) #define ELF64_R_TYPE(i) ((i) & 0xffffffff)
_dl_runtime_resolver的第二个参数由offset 变为index, 依然通过栈传递参数
Roputils使用
rop.fill(len)填充至return address
rop.call(func_addr_or_name, args[])执行函数调用
rop.dl_resolve_call(stack_addr_of_plt_0,args[])调用plt_0
rop.string(str)填充字符串rop.fill()填充至stack_addr_of_plt_0
rop.dl_resolve_data(stack_addr_of_plt_0,fake_func_name)填充fake reloc&sym
...