码迷,mamicode.com
首页 > 其他好文 > 详细

Buffer Overflow

时间:2015-10-26 15:23:27      阅读:311      评论:0      收藏:0      [点我收藏+]

标签:

  本实验是关于缓冲区溢出的原理以及如何利用缓冲区溢出漏洞进行攻击,分为以下十个练习:

  Part A:buffer overflow principal

  • Exercise1:output 3 addresses
  • Exercise2:use gdb
  • Exercise3:turn off ASLR and output addresses again
  • Exercise4:print value of %eip when program crashes
  • Exercise5:about function badman
  • Exercise6:attack stack2.c with shellcode offered

  Part B:buffer overflows in the touchstone web server

  • Exercise7:find vulnerability in server‘s code
  • Exercise8:crash the web server
  • Exercise9:delete file in the server‘s directory with shellcode

  Part C:fixing buffer overflow

  • Exercise10:fix the buffer overflow vulnerabilities

  在计算机中,通常使用如下图所示的栈数据结构来控制函数的调用(call)和返回(ret),可以看到我们有一个12字节大小的缓冲区buf,在内存中,缓冲区再往上面依次存放了old-ebp,return address等,对于C语言里众多不执行边界检查的函数,如strcpy,strcat等,使用中很容易造成缓冲区溢出,即old-ebp,retrun address被其它数据覆盖,从而改变程序执行过程。

  技术分享

  Exercise 1:

  根据如下代码,打印出buffer数组的地址,其中注释部分便是加入的代码,编译并运行程序三次,结果如下图所示,可以看到三次分配给func函数里buffer数组的地址各不相同。

#include <stdlib.h>
#include <stdio.h>
#include <string.h>

void badman()
{
    printf("I am the bad man\n");
    return;
}

int func(char *str)
{
  int variable_a;
  char buffer[12];
  //printf("%p->%p\n",buffer,buffer+11);
  strcpy(buffer, str);
  
  return 1;
}

int main(int argc, char **argv)
{
  char *buf = "hello\n";
  
  if(argc > 1){
    buf = argv[1];
  }

  func(buf);
  printf("Returned Properly\n");
  return 1;
}

技术分享

  Exercise2:

  学习基本的gdb调试指令:

  1. b用于设置断点,这里在func入口处设置断点,然后r开始运行,可以看到程序会在func入口处停止运行;
  2. info r用于显示各寄存器的值,对应的可以用i  r register显示某个特定寄存器的值,如i r $ebp显示寄存器ebp的值,即当前函数值的栈底指针;
  3. x/…  addr指令用于取addr所存的值,可以指定输出形式,如x/4wx是以x(hex)形式从指定地址往后打印4个w(4字节一组),还有诸如x/bx,x/10i,x/2s等格式;
  4. disass func显示func函数对应的汇编指令以及指令在内存中的地址;
  5. 可以用p打印变量信息,如p badman打印badman函数的入口地址;
  6. set命令可以设置变量,地址等的值。

技术分享

  Exercise3:

  关闭ASLR,即地址空间随机化机制:

  在终端运行sudo sysctl -w kernel.randomize_va_space=0,将其设为0即可,然后我们再运行三次stack1.c,如下图所示,可以看到buffer的地址是相同的。

技术分享

  Exercise4:

  运行stack1.c时输入一串字符串作为其参数,增加字符串长度,使程序缓冲区溢出,用gdb查看溢出时eip寄存器的值。

  为了查看缓冲区溢出时eip的值,我们需要关闭栈保护机制,否则缓冲区溢出会被检测到,系统会调用保护函数,此时我们不能看到预期中的eip的值,关闭方法是加-fno-stack-protector参数编译stack1.c

  gcc -g -fno-stack-protector -o stack1 stack1.c

  用gdb调试stack1,用set args aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa给程序设置参数,然后运行,程序将会出错,此时用i r $eip查看eip寄存器的值,结果如下图所示,程序崩溃是eip的值是0x61616161,即我们的参数覆盖了返回地址。

技术分享

  Exercise5:

  

Buffer Overflow

标签:

原文地址:http://www.cnblogs.com/louwqtc/p/4910949.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!