奋斗中拥有

网上搜索了一下, 发现此代码主要原理是通过搜索 int 0x80的中断服务程序中的sys_call_table来实现.

在linux中所有的syscall都是调用int 0x80, int 0x80的中断服务程序为system_call(arch/x86/kernel/traps_32.c:set_system_gate(SYSCALL_VECTOR,&system_call). system_call (arch/x86/entry_32.S)最终call *sys_call_table(,%eax,4)来完成一个syscall调用.

即int 0x80 -> system_call -> sys_call_table, 这样我们只要首先获取int 0x80的中断服务地址system_call地址, 然后在system_call代码中直接搜索call指令即可找到sys_call_table地址了!

另一种方法就是直接修改

通过cat /boot/System.map-`uname -r` |grep sys_call_table 查看当前sys_call_table地址,并与通过以上方法取得的地址做比较!

内核版本: ubuntu 2.6.24-19-server

/** Standard in kernel modules*/#include <linux/kernel.h> /* We’re doing kernel work */#include <linux/module.h> /* Specifically, a module, */#include <linux/moduleparam.h> /* which will have params */#include <linux/unistd.h> /* The list of system calls */

/** For the current (process) structure, we need* this to know who the current user is.*/#include <linux/sched.h>#include <asm/uaccess.h>

unsigned long *sys_call_table = 0;//EXPORT_SYMBOL ( sys_call_table );struct { unsigned short limit; unsigned int base;} __attribute__ ( ( packed ) ) idtr;struct { unsigned short offset_low; unsigned short segment_select; unsigned char reserved, flags; unsigned short offset_high;} __attribute__ ( ( packed ) ) * idt;

unsigned long* find_sys_call_table(void){ unsigned long system_call = 0; // x80中断处理程序system_call 地址 char *call_hex = “/xff/x14/x85”; // call 指令 char *code_ptr = NULL; char *p = NULL; unsigned long sct = 0x0; int i = 0;

// 获取中断描述符表寄存器的地址 __asm__ ( “sidt %0”: “=m” ( idtr ) ); // 获取0x80中断处理程序的地址 idt = ( void * ) ( idtr.base + 8 * 0x80 ); system_call = ( idt->offset_high << 16 ) | idt->offset_low;

// 搜索system_call代码 code_ptr = (char *)system_call; for(i = 0;i < ( 100 – 2 ); i++) { //// 查找call指令 if(code_ptr[i] == call_hex[0] && code_ptr[i+1] == call_hex[1] && code_ptr[i+2] == call_hex[2] ) { // p = &code_ptr[i] + 3; break; } } if ( p ){ sct = *(unsigned long*)p; } return (unsigned long*)sct;}

int init_module ( void ) {

if ( ( sys_call_table = find_sys_call_table() ) ) { printk( “sys_call_table = %p/n”, sys_call_table ); } return 0;}

void cleanup_module ( void ) {}

Makefile文件:

obj-m = get_sct.oKVERSION = $(shell uname -r)all: make -C /lib/modules/$(KVERSION)/build M=$(PWD) modulesclean: make -C /lib/modules/$(KVERSION)/build M=$(PWD) clean

,失败是什么?没有什么.只是更走近成功一步,

奋斗中拥有

相关文章:

你感兴趣的文章:

标签云: