Format String Vulnerability lab实验

简介:

//csdn博客目前暂时不再更新了,有兴趣请访问我的技术博客-晓的博客:zhangxiaolong.org 


     今天做格式化字符串漏洞实验。是一个比较有难度的实验,这也是下一个shellcode实验的基础。

     首先呢,要了解一下我们将会用到的知识(以我的预习情况来给大家做知识讲解): 

(1)给出以下程序:

   main()

  {

      int num=0x41414141;

      printf("Before: num = %#x \n", num);

     printf("%.20d%hn\n", num, &num);

     printf("After: num = %#x \n", num);

  }

查看这段代码的执行结果,解释%.20d和%hn的含义。

经过运行输出为:

Before:num=0x41414141

00000000001094795585

After : num= 0x4141001a

解释:

%.20d:%m.n格式中m为输出宽度,n为精度控制。d表示以十进制形式输出带符号整数,所以解释是为输出精度为20的整形量。

%hn: h表示按短整型量输出,%n 并不告诉printf()显示什么内容,而是将已输出的字符个数放入到变元指向的变量中。在printf()调用返回后,这个变量将包含一个遇到%n是字符输出的数目。

(2)解释linux用root执行下面这条命令sysctl -w kernel.randomize_va_space=0的含义和用途。

解答:

Sysctl:sysctl is an interface that allows you to make changes to a running Linux kernel. With /etc/sysctl.conf you can configure various Linux networking and system settings such as:

1. Limit network-transmitted configuration for IPv4

2. Limit network-transmitted configuration for IPv6

3. Turn on execshield protection

4. Prevent against the common 'syn flood attack'

5. Turn on source IP address verification

6. Prevents a cracker from using a spoofing attack against the IP address of the server.

7. Logs several types of suspicious packets, such as spoofed packets, source-routed packets, and redirects.

sysctl -w kernel.randomize_va_space=0  表示关掉aslr功能,ASLR(Address space layout randomization)是一种针对缓冲区溢出的安全保护技术,通过对栈、共享库映射等线性区布局的随机化,防止攻击者定位攻击代码位置,达到阻止溢出攻击的目的。

     经过这两个小问题的学习之后,我们要了解Format String Vulnerability的实验的要求(这实验任务书是英文的,我就偷个懒,就不翻译了,不过应该很容易看懂的):

      In the following program, you will be asked to provide an input, which will be saved in a buffer calleduser input. The program then prints out the buffer using printf. The program is a Set-UID program(the owner is root), i.e., it runs with the root privilege. Unfortunately, there is a format-string vulnerabilityin the way how the printf is called on the user inputs. We want to exploit this vulnerability and see howmuch damage we can achieve.

     The program has two secret values stored in its memory, and you are interested in these secret values.However, the secret values are unknown to you, nor can you find them from reading the binary code (forthe sake of simplicity, we hardcode the secrets using constants 0x44 and 0x55). Although you do not knowthe secret values, in practice, it is not so difficult to find out the memory address (the range or the exactvalue) of them (they are in consecutive addresses), because for many operating systems, the addresses areexactly the same anytime you run the program. In this lab, we just assume that you have already known theexact addresses. To achieve this, the program “intentionally” prints out the addresses for you.

With suchknowledge, your goal is to achieve the followings (not necessarily at the same time)Crash the program .

_ Print out the secret[0] value.

_ Modify the secret[0] value.

_ Modify the secret[0] value to a pre-determined value.

Note that the binary code of the program (Set-UID) is only readable/executable by you, and there isno way you can modify the code. Namely, you need to achieve the above objectives without modifying thevulnerable code. However, you do have a copy of the source code, which can help you design your attacks.

     总体来说,需要做以下任务:

          1.  指出cret[0]中的值;

          2.  修改cret[0]中的值;

          3.  更改secret[0]的值为设计好的数值。

实验过程步骤:

(1)在linux中要关掉内存随机化分配的功能,指令如下:

       sysctl -w kernel.randomize_va_space=0                 

(2) 编写root程序vulp.c,vulp.c程序为(这个程序就是我们用printf格式化字符串攻击的程序):

/* vul_prog.c */ 
#define SECRET1 0x44
#define SECRET2 0x55
int main(int argc, char *argv[])
{
  char user_input[100];
  int *secret;
  int int_input;
  int a, b, c, d; /* other variables, not used here.*/
  /* The secret value is stored on the heap */
  secret = (int *) malloc(2*sizeof(int));
  /* getting the secret */
  secret[0] = SECRET1; secret[1] = SECRET2;
  printf("The variable secret's address is 0x%8x (on stack)\n", &secret);
  printf("The variable secret's value is 0x%8x (on heap)\n", secret);
  printf("secret[0]'s address is 0x%8x (on heap)\n", &secret[0]);
  printf("secret[1]'s address is 0x%8x (on heap)\n", &secret[1]);

  printf("Please enter a decimal integer\n");
  scanf("%d", &int_input);  /* getting an input from user */
  printf("Please enter a string\n");
  scanf("%s", user_input); /* getting a string from user */

  /* Vulnerable place */
  printf(user_input);  
  printf("\n");

  /* Verify whether your attack is successful */
  printf("The original secrets: 0x%x -- 0x%x\n", SECRET1, SECRET2);
  printf("The new secrets:      0x%x -- 0x%x\n", secret[0], secret[1]);
  return 0;
}

      编译vulp.c程序,设置为suid权限,并以用户权限执行这段程序。输入一个用于定位的数值,例如输入25,在机器中十六进制为00000019,在输入一个字符串%08x. %08x. %08x. %08x. %08x. %08x. %08x. %08x. %08x. %08x. %08x. %08x.用以输出堆栈中此时的数值,可以看到我们自己的数值0x19的位置。如下图所示。

(3)更改secret[0]中值。首先要确定这个数值的地址。可以在上图看到地址为0x804b008,换算为十进制数为134524936,故在要求输入数值时输入134524936,此数值换为十六进制为我们要写入的地址,即secret[0]。更改这个地址的内容。如图所示:

 

(4)更改secret[0]中的值为指定的数值,进行漏洞攻击。前面如(3)所示,要在secret[0]中写入0x1234替换原来的0x44,0x1234换算为十进制数为4660,计算位置数值为8×9=72,即4660=72+4588,所以要填补4588个0,才能保证secret[0]中为0x1234.如下两图所示。

 

目录
相关文章
|
6月前
|
安全
格式化字符串漏洞(Format String Attack)
格式化字符串漏洞(Format String Attack)
39 0
|
关系型数据库 MySQL
MySQL <= 5.0.45 post auth format string vulnerability
MySQL (tested: Version 5.0.45 on CentOS (Linux)) Format String Vulnerability MySQL General Available (GA) Release is vulnerable.
788 0
[转]用DateTime.ToString(string format)输出不同格式
原文:http://blog.sina.com.cn/s/blog_4f3247900100alqj.html DateTime.ToString()函数有四个重载。一般用得多的就是不带参数的那个了。
780 0
用DateTime.ToString(string format)输出不同格式的日期
DateTime.ToString()函数有四个重载。一般用得多的就是不带参数的那个了。殊不知,DateTime.ToString(string format)功能更强大,能输出不同格式的日期。
872 0
|
安全
OllyDbg Format String 0day分析和利用
文章作者:gyzy [E.S.T](www.gyzy.org)信息来源:邪恶八进制信息安全团队(www.eviloctal.com)本文已经发表在《黑客防线》2007年6月刊。
912 0
|
8天前
|
Java API 索引
Java基础—笔记—String篇
本文介绍了Java中的`String`类、包的管理和API文档的使用。包用于分类管理Java程序,同包下类无需导包,不同包需导入。使用API时,可按类名搜索、查看包、介绍、构造器和方法。方法命名能暗示其功能,注意参数和返回值。`String`创建有两种方式:双引号创建(常量池,共享)和构造器`new`(每次新建对象)。此外,列举了`String`的常用方法,如`length()`、`charAt()`、`equals()`、`substring()`等。
14 0
|
24天前
|
Java
【Java】如果一个集合中类型是String如何使用拉姆达表达式 进行Bigdecimal类型计算?
【Java】如果一个集合中类型是String如何使用拉姆达表达式 进行Bigdecimal类型计算?
25 0
|
30天前
|
Java
Java String split()方法详细教程
Java String split()方法详细教程
20 0