import java.io.*;
import java.security.MessageDigest;

public class pwlib
{
	
	int minLength;
	int maxLength;
	int startAscii;
	int stopAscii;
	boolean config = false;
	
	int dictMin;
	int dictMax;
	
	BufferedReader file;
	
	int currentString[];
	int currentLength;
	
	
	public pwlib()
	{		
	}
	
	public void configBruteForce(int min, int max)
	{
		this.configBruteForce(min, max, 65, 122);
	}
	
	public void configBruteForce(int min, int max, int start)
	{
		this.configBruteForce(min, max, start, 122);
	}
	
	public void configBruteForce(int min, int max, int start, int stop)
	{
		this.config = true;
		this.currentLength = this.minLength = min;
		this.maxLength = max;
		this.startAscii = start;
		this.stopAscii = stop;
		
		this.currentString = new int[max];
		for(int a=min; a<max; a++)
			this.currentString[a] = 0;
		this.generateNextBruteForce();
	}
	
	public void configDictionary(String filename)
	{
		this.configDictionary(filename, -1, 1024);
	}
	
	public void configDictionary(String filename, int min)
	{
		this.configDictionary(filename, min, 1024);
	}
	
	public void configDictionary(String filename, int min, int max)
	{
		try
		{
			this.file = new BufferedReader(new FileReader(filename));
		}catch(Exception x)
		{
			System.out.println("An error occured opening the file: " + filename);	
		}
		this.dictMin = min;
		this.dictMax = max;
	}
	
	public String plainDictionary()
	{
		String tmp = "";
		try
		{
			int size;
			do
			{
				tmp = file.readLine();
				size = tmp.length();
			}while( size > this.dictMax || size < this.dictMin);
		}catch(Exception x){return "";}
		return tmp;
	}
	
	public String hashDictionary()
	{
		return this.hashDictionary("md5");
	}
	
	public String hashDictionary(String type)
	{
		String pw = this.plainDictionary();
		if(pw == null || pw == "")
			return "";
			
		String out = "";
		if(type != "md5" && type != "sha1")
			type = "md5";
		try
		{	
			MessageDigest md = MessageDigest.getInstance(type);
			
			md.update(pw.getBytes());
			byte mdbytes[] = md.digest();
			StringBuffer hexString = new StringBuffer();
			for (int i=0;i<mdbytes.length;i++) {
				hexString.append(Integer.toHexString(0xFF & mdbytes[i]));
			}
			out = hexString.toString();
		}catch(Exception x){}
		return out;
	}
	
	public String plainBruteForce()
	{
		try{
		if(!this.config)
			throw new Exception("Brute Forcing not configured. Please use configBruteForce()");
		}catch(Exception x)
		{
			System.out.println("Error throwing exception");
		}	
		String tmp = this.toString();
		this.generateNextBruteForce();
		return tmp;	
	}
	
	public String hashBruteForce()
	{
		return this.hashBruteForce("md5");
	}
	
	public String hashBruteForce(String type)
	{
		String pw = this.plainBruteForce();
		if(pw == null || pw == "")
			return "";
			
		String out = "";
		if(type != "md5" && type != "sha1")
			type = "md5";
		try
		{	
			MessageDigest md = MessageDigest.getInstance(type);
			
			md.update(pw.getBytes());
			byte mdbytes[] = md.digest();
			StringBuffer hexString = new StringBuffer();
			for (int i=0;i<mdbytes.length;i++) {
				hexString.append(Integer.toHexString(0xFF & mdbytes[i]));
			}
			out = hexString.toString();
		}catch(Exception x){}
		return out;	
	}
	
	public void generateNextBruteForce()
	{
		
		int pos = 0;
		do
		{
			if(this.currentString[pos]==0)
				this.currentString[pos] = this.startAscii;
			else
				this.currentString[pos]++;
			int posn = pos - 1;
			if(posn >= 0 && this.currentString[posn] > this.stopAscii)
				this.currentString[posn] = this.startAscii;
			pos++;
		}while(this.currentString[pos-1] > this.stopAscii && pos < this.currentString.length);
		
	}
	
	public String toString()
	{
		
		String tmp = "";
		if(this.currentString.length >= this.maxLength && this.currentString[this.maxLength-1] >= this.stopAscii)
		{}
		else
		{
			for(int a=0; a < this.currentString.length; a++)
				if(this.currentString[a] != 0)
					tmp += (char)(this.currentString[a]);
		}
		return tmp;	
	}
	
	public static void main(String args[])
	{
		pwlib hash = new pwlib();
		hash.configDictionary("test.txt", 1, 3);
		hash.configBruteForce(1,3);
		String test = hash.plainBruteForce();
		while(test != "")
		{
			System.out.println(test);
			test = hash.hashBruteForce();	
		}
	}
	
}
