Maybe you should think again.
Maybe it's ok to do as a personal intellectual exercise, but what's the point of compromising sha1 for everybody?
I don't get it.
For better security practices to be taken into place. IMO any hash function can be cracked and I am going to prove that by going to selected algorithms and cracking them. If you truly want a secure hash then you would need to use something like the following:
function truehash($hashzzz) {
return hash('sha1',hash('whirlpool',$hashzzz));
}
A function like that will never be cracked unless both algorithms are cracked with a third algorithm written. So pritty much the reason why I am revealing the weaknesses in SHA1 is to prove that no hash is truly secure. I heard some officials in America have already cracked sha1 but is closed source. As for my source at digital-ethers request is below. I have managed to store both the previous temp variable value and the core data of the word variable/subarray into a single variable. This variable changes on each loop round. The next step is to separate rotateleft(a,5) from word[m] which are stored in val. After that it is possible to gain access to the word array which will lead to the next set of equations.
//#include<stdio.h>
#include<string.h>
#include<malloc.h>
#include<math.h>
#include<stdlib.h>
#include<iostream>
#include <sstream>
#define rotateleft(x,n) ((x<<n) | (x>>(32-n)))
#define rotateright(x,n) ((x>>n) | (x<<(32-n)))
#define rotateleftrev(x,n) ((x<<n) | (x>>((32-n)+n)))
void SHA1(unsigned char * str1)
{
int i;
unsigned long int h0,h1,h2,h3,h4,a,b,c,d,e,f,k,temp;
h0 = 0x67452301;
h1 = 0xEFCDAB89;
h2 = 0x98BADCFE;
h3 = 0x10325476;
h4 = 0xC3D2E1F0;
unsigned char * str;
str = (unsigned char *)malloc(strlen((const char *)str1)+100);
strcpy((char *)str,(const char *)str1);
int current_length = strlen((const char *)str);
int original_length = current_length;
str[current_length] = 0x80;
str[current_length + 1] = '\0';
char ic = str[current_length];
current_length++;
int ib = current_length % 64;
if(ib<56)
ib = 56-ib;
else
ib = 120 - ib;
for(i=0;i < ib;i++)
{
str[current_length]=0x00;
current_length++;
}
str[current_length + 1]='\0';
for(i=0;i<6;i++)
{
str[current_length]=0x0;
current_length++;
}
str[current_length] = (original_length * 8) / 0x100 ;
current_length++;
str[current_length] = (original_length * 8) % 0x100;
current_length++;
str[current_length+i]='\0';
int number_of_chunks = current_length/64;
unsigned long int word[80];
for(i=0;i<number_of_chunks;i++)
{
for(int j=0;j<16;j++)
{
word[j] = str[i*64 + j*4 + 0] * 0x1000000 + str[i*64 + j*4 + 1] * 0x10000 + str[i*64 + j*4 + 2] * 0x100 + str[i*64 + j*4 + 3];
}
for(int j=16;j<80;j++)
{
word[j] = rotateleft((word[j-3] ^ word[j-8] ^ word[j-14] ^ word[j-16]),1);
}
a = h0;
b = h1;
c = h2;
d = h3;
e = h4;
for(int m=0;m<80;m++)
{
if(m<=19)
{
f = (b & c) | ((~b) & d);
k = 0x5A827999;
}
else if(m<=39)
{
f = b ^ c ^ d;
k = 0x6ED9EBA1;
}
else if(m<=59)
{
f = (b & c) | (b & d) | (c & d);
k = 0x8F1BBCDC;
}
else
{
f = b ^ c ^ d;
k = 0xCA62C1D6;
}
//std::cout << word[m] << std::endl;
temp = (rotateleft(a,5) + f + e + k + word[m]) & 0xFFFFFFFF;
if (m==79) {
std::cout << "+++ " << a << std::endl;
std::cout << "++ " << rotateleft(a,5) << std::endl;
}
e = d;
d = c;
c = rotateleft(b,30); //std::cout << "++ " << b << std::endl;
b = a;
a = temp;
}
//std::cout << "--++ " << c << std::endl;
//std::cout << b << std::endl;
//std::cout << c << std::endl;
//std::cout << h3 << "+" << d << "=" << (h3+d) << std::endl;
//printf("%x",(h3+d));
std::cout << std::endl;
//std::cout << e << std::endl;
h0 = h0 + a;
h1 = h1 + b;
h2 = h2 + c;
h3 = h3 + d;
h4 = h4 + e;
}
printf("Hash: %x %x %x %x %x",h0, h1, h2, h3, h4);
std::cout << std::endl << "Hash: " << h0 << " " << h1 << " " << h2 << " " << h3 << " " << h4 << std::endl;
}
//----------------------------------------------
// edit below
//----------------------------------------------
unsigned long int bin2dec(std::string bin)
{
unsigned long int result=0;
for(unsigned int i=0;i<bin.length();i++)
{
//if((bin[i]!='0')&&(bin[i]!='1'))
// return -1;
result=result*2+(bin[i]-'0');
//if(result<=0) return -1;
}
return result;
}
std::string *parts8(std::string originalhash) {
int arr_pos=0;
std::string chrset="";
std::string *parts;
parts = new std::string[5];
for (int i=0; i<40; i++) {
double tmp=(i+1)/8;
arr_pos=floor(tmp)-1;
tmp=((i+1.0)/8.0)-1.0;
std::string str;
str=originalhash.at(i);
chrset=chrset.append(str.c_str());
if (arr_pos==tmp) {
parts[arr_pos]=chrset;
chrset="";
}
}
return parts;
}
char xtod(char c) {
if (c>='0' && c<='9') return c-'0';
if (c>='A' && c<='F') return c-'A'+10;
if (c>='a' && c<='f') return c-'a'+10;
return c=0; // not Hex digit
}
/*long hex2int(const std::string& hexStr) {
char *offset;
if (hexStr.length( ) > 2) {
if (hexStr[0] == '0' && hexStr[1] == 'x') {
return strtol(hexStr.c_str( ), &offset, 0);
}else{
std::string str="0x";
str.append(hexStr);
return strtol(str.c_str( ), &offset, 0);
}
}
}*/
typedef __int64 int64;
int64 hexToInt64(const std::string hexStr){
std::stringstream strm;
strm << std::hex << hexStr;
int64 value = 0;
if(!(strm >> value)) throw std::exception("Conversion to int64 failed!\n");
return value;
}
unsigned long int hex2int(const std::string hexString) {
unsigned long int v;
v=hexToInt64(hexString);
return v;
}
std::string dehash_SHA1 (std::string originalhash) {
if (originalhash.length()!=40) {
return "^Error: Invalid hash";
} else {
std::string *arr;
arr=parts8(originalhash);
unsigned long int *parts;
parts = new unsigned long int[5];
parts[0]=hex2int(arr[0]);
parts[1]=hex2int(arr[1]);
parts[2]=hex2int(arr[2]);
parts[3]=hex2int(arr[3]);
//std::cout << "Num=" << parts[3] << std::endl;
parts[4]=hex2int(arr[4]);
/*std::cout << parts[0] << std::endl;
std::cout << parts[1] << std::endl;
std::cout << parts[2] << std::endl;
std::cout << parts[3] << std::endl;
std::cout << parts[4] << std::endl;*/
unsigned long int h0,h1,h2,h3,h4, a,b,c,d,e,k,f, ulong,temp,val;
unsigned int zplus;
zplus=500;
unsigned long int worddata[80][500];
unsigned long int worddata2[80][16];
h0 = 0x67452301;
h1 = 0xEFCDAB89;
h2 = 0x98BADCFE;
h3 = 0x10325476;
h4 = 0xC3D2E1F0;
ulong = 4294967295;
ulong = 18446744073709551615;
//std::cout << std::endl << parts[3] << "-" << h3 << "=" << (parts[3]-h3) << std::endl;
// --- loop beginning --- //
a=parts[0]-h0; parts[0]=a;
b=parts[1]-h1; parts[1]=b;
c=parts[2]-h2; parts[2]=c;
d=parts[3]-h3; parts[3]=d;
e=parts[4]-h4; parts[4]=e;
for (int m=79; m>=0; m--) {
if(m<=19)
{
f = (b & c) | ((~b) & d);
k = 0x5A827999;
}
else if(m<=39)
{
f = b ^ c ^ d;
k = 0x6ED9EBA1;
}
else if(m<=59)
{
f = (b & c) | (b & d) | (c & d);
k = 0x8F1BBCDC;
}
else
{
f = b ^ c ^ d;
k = 0xCA62C1D6;
}
//c = rotateright();
//std::cout << "++" << b << std::endl;
//std::cout << "++" << b << std::endl;
//std::cout << "++" << c << std::endl;
//temp is smaller than var a;
/*temp = (rotateleft(a,5) + f + e + k + word[m]) & 0xFFFFFFFF;
e = d;
d = c;
c = rotateleft(b,30); //// std::cout << "++ " << b << std::endl;
b = a;
a = temp;*/
temp = a;
val=0;
while (true) {
if ((( f + e + k + val) & 0xFFFFFFFF)==temp) {
break;
} else {
val++;
if ((( f + e + k + val + 1000000) & 0xFFFFFFFF)<temp) {
val+=1000000;
}
}
}
unsigned int zz=1;
for (unsigned int z=0;z<zplus;z++) {
if (rotateleft(zz,5)<val) {
if (rotateleft(zz,5)>0) {
worddata[m][z]=rotateleft(zz,5);
std::cout << worddata[m][z] << std::endl;
}
}
zz++;
}
std::cout << std::endl;
/*
val = rotateleft(a,5) + word[m] The current value of val
worddata[x] contains the possible numbers of word[m].
worddata2 needs to be populated by going through the array worddata
and changing the last for binary digits to 1010, 1101, 1011 etc.
Get number smaller than the val variable and it's binary value ends in 00000
That is ends in 5 zeros for it's binary value.
*/
a = b;
if (m==78) {
std::cout << a << std::endl;
}
b = rotateright(c,30);
c = d;
d = e;
}
//std::cout << d << std::endl;
//std::cout << std::endl << parts[0] << std::endl;
//std::cout << parts[1] << std::endl;
//std::cout << parts[2] << std::endl;
//std::cout << parts[3] << "--" << 0x10325476 << std::endl;
//std::cout << parts[4] << std::endl;
return "";
}
}
void main()
{
std::string tmp;
coda:
system("CLS");
SHA1((unsigned char *)"The quick brown fox jumps over the lazy dog");
//above and below are same hash
tmp=dehash_SHA1("2fd4e1c67a2d28fced849ee1bb76e7391b93eb12");
std::cout << tmp.c_str() << std::endl;
std::cout << std::endl;
std::cout << bin2dec("1101") << std::endl;
system("PAUSE");
goto coda;
}