Search code examples
javamultithreadingpasswordsprocessor

How to multi-thread a brute force java password program


I created a program for for my 11th grade computer science project where I made a java password cracker that brute-forces the password. However, I would like to get some advice on how to multi-thread my java program (code provided below) to speed up the brute-force process. If it helps at all I am running a i7-3770 processor by Intel and it is quad-core but has 2 threads per core so 8 possible threads at once.

Here is the code:

import java.util.*;
import java.io.*;
class pwcracker
{
public static void main (String[] args)
{
Scanner scan = new Scanner( System.in );
Random rand = new Random();

Runtime.getRuntime().availableProcessors();

 String pw, choices, guess;
long tries;
int j, length;

System.out.println("Enter a password that is up to 5 chars and contains no numbers: ");
pw = "" + scan.nextLine();
length = pw.length();

choices = "abcdefghijklmnopqrstuvwxyz";
tries = 0;
guess = "";

System.out.println("Your pw is: " + pw);
System.out.println("The length of your pw is: " + length);

System.out.println("for TEST- Guess: " + guess + "pw :"+pw);


 if (guess !=  pw){

 while  (guess !=  pw) 
 { 
    j = 0;
    guess = "";

    while ( j < length )
    {
        guess = guess + choices.charAt( rand.nextInt ( choices.length() ) );
        j = j + 1;

    if (guess == pw)
 {
   System.out.println("Match found, ending loop..");
   break;
 }

    }
            System.out.println("2 Guess: " + guess + " pw :"+pw); 

    tries = tries + 1;                      
}
}
System.out.println("Here is your password: " + guess);
System.out.println("It took " + tries + " tries to guess it.");
 }
 }

Solution

  • This is not a parallel processing solution but a much more optimised brute force approach. You can consider changing the Iterator to a Spliterator. If time permits I will possibly give a Spliterator approach in a following post.

    package pwcracker;
    
    import java.util.Iterator;
    import java.util.Scanner;
    
    public class pwcracker {
    
        public static void main(String[] args) {
            Scanner scan = new Scanner(System.in);
            String pw;
            int length;
    
            System.out.println("Enter a password that is up to 5 chars and contains no numbers: ");
            pw = "" + scan.nextLine();
            length = pw.length();
    
            SequentialPatternGenerator generator = new SequentialPatternGenerator(length);
    
            generator.forEachRemaining(test -> {if(pw.equals(test)) {
                System.out.println("Your password: " + test );
            }});
    
        }
    }
    
    class SequentialPatternGenerator implements Iterator<String> {
    
        private static final char[] CHOICES = new char[]{'a', 'b', 'c', 'd', 'e', 'f',
            'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z'};
    
        private static final int MAX_INDEX = CHOICES.length - 1;
        private boolean keepProducing = true;
        private final int[] indexes;
    
        public SequentialPatternGenerator(final int length) {
            indexes = new int[length];
            initIndexes();
        }
    
        private void initIndexes() {
            for (int i = 0; i < indexes.length; i++) {
                indexes[i] = 0;
            }
        }
    
        @Override
        public boolean hasNext() {
            if (!keepProducing) {
                return false;
            }
    
            for (int i = 0; i < indexes.length; i++) {
                if (indexes[i] < MAX_INDEX) {
                    return true;
                }
            }
    
            return false;
        }
    
        @Override
        public String next() {
            if (!keepProducing || !hasNext()) {
                return null;
            }
    
            String next = produceString();
            adjustIndexes();
    
            return next;
        }
    
        public void stop() {
            keepProducing = false;
        }
    
        private String produceString() {
            StringBuilder sb = new StringBuilder();
            for (int i = 0; i < indexes.length; i++) {
                sb.append(CHOICES[indexes[i]]);
            }
    
            return sb.toString();
        }
    
        private void adjustIndexes() {
            int i;
            for(i = 0 ; i < indexes.length ; i++) {
                if(indexes[i] < MAX_INDEX) {
                    indexes[i] = indexes[i] + 1;
                    break;
                }
            }
    
            for(int j=0; j < i; j++) {
                indexes[j] = 0;
            }
        }
    }