2.6内核里劫持系统调用

Linux2.6系统调用劫持介绍 这几天做操作系统课程的作业,其中一个要求是设计内核模块,在查阅资料的过程中发现内核模块可以在不重新编译内核的情况下增加内核的功能,当然也可以对内核进行修改,实现对系统调用劫持。这篇文章就是对linux下劫持系统调用的介绍和资料的整理。 一、介绍         先介绍一下内核模块。内核模块是在操作系统需要的时候动态载入的目标文件对象,链接成内核的一部分,从而可以在不重新编译整个内核 阅读详情
     2005-07

几乎所有的空用户间操作在系统内核里都是通过系统里的系统调用来实现的,前面也写了一篇有关系统调用的文章,这里再简单的介绍一下大至过程,当用户执行某 一操作时,比如果打开文件的操作,打开文件的程序会调用到glib库中的open函数,而open函数最终在内核的实现就是open系统调用,当用户执行 到open函数时,会由用户空间切换到内核内间,通过int 80进行切换,进入内核空间后会找到一个sys_call_table的符号,sys_call_table是一个指向系统调用号列表的指针,再在 sys_call_table里找到想应的系统调用号,再通过系统调用号找到内核的系统调用,再执行系统调用。
劫持系统调用就是我们自己构造一个系统调用,想办法使sys_call_table相应的系统调用号指向我们自己构造的函数。在原来的2.2内核里,可以 将sys_call_table直接导出,这样我们就很容易拿到sys_call_table的控制权来实现系统调用的劫持,但是从2.4的版本以后,考 虑到安全问题不允许将sys_call_table再导出,这样就加大了取得sys_call_table控制权的难度,后面有人从/dev/kmem里 读取sys_call_table的地址,再通过sys_call_table地址来实现系统调用的劫持,后来找到了一种更好的办法,可以不通过 /dev/kmem来直接找到sys_call_table的地址。这里重点讨论一下这种方法。
这种方法的原理比较简单,但思路很好,实现过程是自已构建一个内核模块,在这个模块中导出一个sys_call_table,因为内核的 sys_call_table不允许导出,所以我们在自已编写的内核模块里实现sys_call_table的导出。我们在模块里找到int 80对sys_call_table的引用,找出sys_call_table的地址,再将我们将要导出的sys_call_table指向这个地址,这 样就是使到导出的sys_call_table和真实的sys_call_table没区别。
实现代码如下:
getsyscall.c文件
代码::

#ifndef __SYSCALL_INCLUDE__
# define __SYSCALL_INCLUDE__
#endif
#ifdef MODVERSIONS
#include <linux/modversions.h>
#endif
#include <linux/module.h>
#include <linux/kernel.h>
MODULE_LICENSE("GPL");
MODULE_AUTHOR("xinhe <xinhe007@163.com>");
MODULE_DESCRIPTION("export the sys_call_table");
#if !defined(symname)
#error symname not defined
#endif
#define CALLOFF 100
unsigned symname; /* #define */
struct {
unsigned short limit;
unsigned int base;
} __attribute__ ((packed)) idtr;

struct {
unsigned short off1;
unsigned short sel;
unsigned char none,
flags;
unsigned short off2;
} __attribute__ ((packed)) * idt;

void set_symbol_addr(unsigned old_value, unsigned new_value)
{
  struct module *mod;
  struct kernel_symbol *s;
  int i;
  for (mod = THIS_MODULE, s = mod->syms, i = 0; i < mod->num_syms; ++i, ++s)
  if (s->value == old_value)
  {
    s->value = new_value;
    return;
  }
  /*遍历本模块的符号表,把本模块的一个也叫sys_call_table的符号的地址
     设置为系统真正的sys_call_table的实际地址。 */
}

char * findoffset(char *start)
{
  char *p;
  for (p = start; p < start + CALLOFF; p++)
  if (*(p + 0) == '/xff' && *(p + 1) == '/x14' && *(p + 2) == '/x85')
   return p;
  /*查找ini 80处理函数对sys_call_table的引用*/
  return NULL;
}

static int __init init(void)
{
  unsigned sys_call_off;
  unsigned sct;
  char *p;
  asm("sidt %0":"=m"(idtr));
  idt = (void *) (idtr.base + 8 * 0x80);
  sys_call_off = (idt->off2 << 16) | idt->off1;
  /*查找int 80的入口地址*/
  if ((p = findoffset((char *) sys_call_off)))
  {
   sct = *(unsigned *) (p + 3);
   set_symbol_addr((unsigned) &symname, sct);
  }
  EXPORT_SYMBOL(sys_call_table);
  return 0;
}

static void __exit fini(void)
{
}
module_init(init);
module_exit(fini);

getsyscall的makefile
代码::

obj-m   :=getsyscall.o
EXTRA_CFLAGS := -Dsymname=sys_call_table
KDIR   := /lib/modules/$(shell uname -r)/build
PWD   := $(shell pwd)
default:
   $(MAKE) -C $(KDIR) SUBDIRS=$(PWD) modules
clean:
   $(RM) -rf .*.cmd *.mod.c *.o *.ko .tmp*


为了证明sys_call_table确实导出来,我们再来写一个系统调用劫持的模块来证明一下
getmkdir.c文件
代码::

#ifndef __GETMKDIR_INCLUDE__
# define __GETMKDIR_INCLUDE__
#endif
#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/types.h>
#include <linux/dirent.h>
#include <linux/string.h>
#include <asm/unistd.h>
MODULE_LICENSE("GPL");
MODULE_AUTHOR("xinhe <xinhe007@163.com>");
MODULE_DESCRIPTION("export the sys_call_table");
extern void *sys_call_table[];
int (*orig_mkdir)(const char *path);/*指向系统的mkdir*/
/*构造自己的mkdir*/
int hacked_mkdir(const char *path)
{
  printk("<1>this is a test");
  return 0;
}
static int __init init(void)
{
  orig_mkdir=sys_call_table[__NR_mkdir];
  sys_call_table[__NR_mkdir]=hacked_mkdir;
  /*将sys_call_table的mkdir指向我们自己构造的hacked_mkdir*/
}
static void __exit fini(void)
{
  sys_call_table[__NR_mkdir]=orig_mkdir;
  /*做恢复工作*/
}
module_init(init);
module_exit(fini);

对应的makefile文件
代码::

obj-m   :=getmkdir.o
KDIR   := /lib/modules/$(shell uname -r)/build
PWD   := $(shell pwd)
default:
   $(MAKE) -C $(KDIR) SUBDIRS=$(PWD) modules
clean:
   $(RM) -rf .*.cmd *.mod.c *.o *.ko .tmp*

加载这个两模块后,再用mkdir创建目录,发现已经不能创建目录了

注:以上代码全在2.6.9中测试通过

存在的问题:
在测试的过程中也发现了一些问题.
当我在2.6.11.4中编译没问题,加载getsyscall没问题,当加载getmkdir时就出错了,而且内核出现异常,很多gnome的程序都出现问题,当执mkdir命令时也出来段错误,希望有高手来说明一下

===========================
2005-08
2.6的最新版据说要把sys_call_table里的东西挪到.rodata section中,这种方法似乎就不奏效了吧 :(
等开学了回去看看
内核态Rootkit攻防解析:从系统调用劫持到DKOM隐藏技术 系统调用是用户程序与操作系统内核交互的核心接口,它定义了进程请求内核服务的标准方式。其原理是通过软中断或专用指令触发,将CPU从用户态切换到特权更高的内核态,执行对应的内核函数后再返回结果。理解系统调用机制对于掌握操作系统安全至关重要,因为它是许多高级攻击技术的切入点。在安全领域,内核态Rootkit代表了最高级别的威胁,它通过劫持系统调用表、挂钩内核函数或直接操作内核对象等技术,实现对系统信息的完全隐藏和操控,从而具备极强的隐蔽性和破坏力。这类技术常被用于高级持续性威胁中,以维持对目标系统的长期控制。本文 阅读详情

相关推荐

Labview项目01:标准可配置序列测试框架

摘要:本文介绍了一个基于LabVIEW2020开发的通用测试框架系统。该系统采用模块化设计,包含主界面、调试界面、设置界面和登录界面。主功能包括:1)可配置测试序列,支持延时、预定值输出、随机值输出等操作;2)单步测试功能自主添加;3)界面支持测试序列编辑和权限管理。系统采用队列机制处理事件和测试流程,通过CSV文件存储测试序列,支持参数化配置。用户可自定义测试VI(A_.vi和N_.vi格式),并通过调试界面验证测试序列。最终测试结果在主界面显示,提供整体判断功能。该系统既可作为学习参考,也可用于实际测试

weixin_38637405的博客 1497

内核线程注入x64

Win764位下通过驱动Attach到目标进程下再调用NtCreateThreadEx函数创建线程执行ShellCode来注入Dll。

台球 PCOL:极致物理还原的网页斯诺克引擎(附源码深度解析)

*完整源码地址**:[https://github.com/billiards/pcol-core](https://github.com/billiards/pcol-core)(包含详细文档与示例)通过这个项目,我们不仅创建了一个游戏,更构建了一个**可扩展的物理引擎框架**,为网页端复杂物理模拟开辟了新的可能性。**在线体验**:[https://pcol.billiards](https://pcol.billiards)(支持移动端触控操作)clone.velocity.x *= -0.92;

Loving_enjoy的博客 2713

内核劫持线程注入DLL并隐藏

在驱动程序中,您可以通过调用PsSetCreateThreadNotifyRoutine或PsSetLoadImageNotifyRoutine等API来获取进程线程的通知。这时,您可以暂停线程并修改其上下文,以便在恢复时执行您的代码。为了实现这些功能,您需要学习Windows内核编程和驱动开发。在此过程中,您可能需要使用Windows Driver Kit(WDK)和Visual Studio。编写好驱动程序后,您需要在目标系统上加载和卸载它。在劫持线程后,您需要将目标DLL加载到目标进程的内存中。

人生苦短,我用python 2083

驱动开发:内核RIP劫持实现DLL注入

本章将探索内核级DLL模块注入实现原理,DLL模块注入在应用层中通常会使用`CreateRemoteThread`直接开启远程线程执行即可,驱动级别的注入有多种实现原理,而其中最简单的一种实现方式则是通过劫持EIP的方式实现,其实现原理可总结为,挂起目标进程,停止目标进程EIP的变换,在目标进程开启空间,并把相关的指令机器码和数据拷贝到面去,然后直接修改目标进程EIP使其强行跳转到我们拷贝进去的相关机器码位置,执行相关代码后,然后再次跳转回来执行原始指令集。

微软技术分享 9571

线程劫持技术

windows 线程劫持

weixin_43799752的博客 1481

2.6内核劫持系统调用(转)

2.6内核劫持系统调用(转)  几乎所有的空用户间操作在系统内核都是通过系统系统调用来实现的,前面也写了一篇有关系统调用的文章,这再简单的介绍一下大至过程,当用户执行某一操作时,比如果打开文件的操作,打开文件的程序会调...

cizn2013的博客 450

Linux2.4.18内核下基于LKM的系统调用劫持

Linux现在使用是越来越多了,因此Linux的安全问题现在也慢慢为更多人所关注。Rootkit是攻击者用来隐藏踪迹和保留root访问权限的工具集,在这些工具当中,基于LKM的rootkit尤其受到关注。这些rootkit可以实现隐藏文件、隐藏进程、重定向可执行文件,给linux的安全带来很大的威胁,它们所用到的技术主要是系统调用劫持。用LKM技术截获系统调用的通常步骤如下:找到需要的系统调用

xpiloveyou的专栏 1235

Linux 系统调用(二)——使用内核模块添加系统调用(无需编译内核

本文将介绍Linux使用内核模块添加系统调用的方法(无需编译内核),思路就是修改映射在内存中的系统调用表,把一个空闲的系统调用表项指向自己写的模块中的函数,如果是已使用的表项,甚至可以实现系统调用劫持。 1、查看预留系统调用号 不同内核版本,文件位置有所不同,我们可以直接查找unistd_64.h文件,命令如下: sudo find / -name unistd_64.h sudo cat /...

金荣的个人技术博客 7816

2.6内核系统调用劫持段错误segment fault等问题的解决方法

在网上搜了很多关于2.6内核系统调用劫持的文章,流传的最多的可能就是那个以mkdir系统调用为例子的文章,自己按照源码敲进去,写好Makefile后也编译通过了,但是加载时却出现了Segment fault的错误,后来调试了一下,发现sys_call_table找得不对,后面却用了返回的一个非法地址,结果出现访问错误。看来这个segment fault是由于非法访问内存引起的,添加了返回值判断后,

579

内核调试和系统调用劫持

如何在不重新编译内核,不rmmod内核模块的情况下修改系统调用 为了解决这个问题,最终实现了两种解决方式: 1.Linux系统调用劫持 2.Kprobes内核调试技术(并非真正的修改) 下面分别说下: Linux系统调用劫持: 其实就是修改内核符号表,来达到一个劫持的作用。因为系统调用实际上是触发了一个0x80的软中断,然后转到了系统调用处理程序的入口system_call()。system_call()会检查系统调用号来得出到底是调用哪种服务,然后会根据内核符号表跳转到所需要调用的..

caotuo_csdn的博客 501

linux系统下的各种hook方式\Linux内核hook系统调用

文章目录一、linux系统下的各种hook方式1. 函数指针hook2. 动态库劫持3. Linux系统调用劫持 hook4. 堆栈式文件系统5. LSM二、Linux内核hook系统调用 一、linux系统下的各种hook方式 在计算机中,基本所有的软件程序都可以通过hook方式进行行为拦截,hook方式就是改变原始的执行流, Linux平台上常见的拦截: 修改函数指针。 用户态动态库拦截。 内核系统调用拦截。 堆栈式文件系统拦截。 LSM(Linux Security Modules) 1. 函数

西京刀客 1万+

Linux 2.6 劫持系统调用 隐藏进程

Linux 2.6 劫持系统调用 隐藏进程

6989

系统调用劫持

一,系统调用劫持 一、介绍         先介绍一下内核模块。内核模块是在操作系统需要的时候动态载入的目标文件对象,链接成内核的一部分,从而可以在不重新编译整个内核的情况加扩展内核的功能。例如一些内核模块是设备驱动程序模块,它们用来让操作系统正确的识别和使用硬件设备,如果没有内核模块,每次增加新驱动程序就得重新编译内核和重启了。         复习一下系统调用的流程。Linux中实现系统

freemind 4259

5.4.1 IPIPE劫持系统调用的流程与场景

本文总结:ipipe_handle_syscall劫持系统调用后,需要处理6中场景,分为3个代码路径进行处理:快速、慢速和正常路径!

三问Linux社区 2039

linux内核劫持

/* ============================================================================ Name : hellomod.c Author : Hava Version : 0.0.0.0 Copyright : Copyright by 2011 Description : Hello World in C, Ansi-style ===========================.

囚牢-峰子的博客 619

信呼协同办公OA系统 v1.8.6

信呼协同办公OA系统是开源的一款办公系统,跨平台的系统,支持APP,pc网页版,pc客户端等。 简介: 1、让每个企业单位都有自己的工作系统。 2、移动,开源工作系统,数据全部

上一篇: 2.6版本Linux上替换系统调用函数实现隐藏文件学习
下一篇: LKM完全指南 (收集得比较全了)
ldong2007
博客等级 码龄19年 17粉丝 10原创
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值