Skip to content

Instantly share code, notes, and snippets.

@joesavage
Created February 26, 2014 19:02
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save joesavage/9236127 to your computer and use it in GitHub Desktop.
Save joesavage/9236127 to your computer and use it in GitHub Desktop.
//Crazy awful hash algorithm. Created for my personal education only.
#include <stdio.h>
#include <iostream>
#include <string>
#include <sstream>
#define BYTES 8 //8 bytes = 64 bits
using std::cout;
using std::endl;
using std::cin;
using std::string;
using std::ostringstream;
typedef unsigned char byte;
void SwapBytes(byte &a, byte &b) //For swapping two bytes over
{
byte temp = a;
a = b;
b = temp;
}
void ShiftByteRight(byte &i) //Circular 8bit rotate/shift right
{
unsigned int d = i << 7;
i >>= 1;
i |= d;
}
void ShiftByteLeft(byte &i) //Circular 8bit rotate/shift left
{
unsigned int d = i >> 7;
i <<= 1;
i |= d;
}
string CreateHash(string &uinput)
{
//Init
string hash; //[BYTES*8]
byte registers[BYTES]; //'Registers' - [0] to [BYTES-1]
registers[0] = 0xA0;
registers[1] = 0x55;
registers[2] = 0x01;
registers[3] = 0xDD;
registers[4] = 0xDE;
//Compression
for(unsigned int i = 0; i < uinput.length(); i++) //For each letter (byte)
{
registers[0] = registers[0] ^ (byte)uinput[i];
registers[1] = ((registers[1] + (byte)uinput[i]) % (registers[0] | 0x01)) ^ registers[0];
registers[2] = (registers[0] ^ registers[1]) & registers[2];
registers[3] = ((registers[2] & registers[3]) + 0x35) % (byte)uinput[i];
registers[4] = (((registers[3] & (byte)uinput[i]) | registers[4]) ^ (byte)uinput[i]);
registers[5] = ((registers[4] + registers[5]) % (registers[3] | 0x01)) ^ 0xFF;
registers[6] = (registers[5] | (byte)uinput[i]) ^ ((registers[6] + (byte)uinput[i]) % 0x0A);
registers[7] = ((registers[6] & registers[3]) ^ (byte)uinput[i]) | registers[7];
if(uinput[i]%0x20 > 5)
{
registers[7] = (byte)uinput[i] ^ registers[7];
ShiftByteRight(registers[7]);
ShiftByteRight(registers[7]);
registers[5] = registers[5] >> 1;
}
if(registers[3] > 0x45)
SwapBytes(registers[3], registers[2]);
if(registers[1] > 0xA0)
SwapBytes(registers[0], registers[1]);
if(registers[7] > 0xA0 && registers[7] < 0xD0)
{
ShiftByteRight(registers[7]);
registers[7] = registers[7] << 1;
ShiftByteLeft(registers[7]);
}
if(registers[4] > 0x4A)
{
ShiftByteLeft(registers[4]);
registers[4] = registers[4] >> 1;
ShiftByteRight(registers[4]);
}
registers[0] = (registers[0] | registers[2]) ^ registers[3];
registers[2] = (registers[2] + registers[1]) % 0xCC;
registers[3] = (registers[3] % 0xA2) ^ 0x01;
if(registers[0] > 0xC0)
{
ShiftByteRight(registers[0]);
ShiftByteRight(registers[0]);
registers[0] = registers[0] << 1;
}
if(registers[5] > 0x0F)
registers[5] = ((registers[5] + (byte)uinput[i]) % (registers[4] | 0x01)) | 0x01;
}
ostringstream s; //Stringstream for storing each hex byte to add to the finished string
//Put into result 'string'
for(unsigned short i = 0; i < BYTES; i++)
{
s << std::hex << std::uppercase << (short)registers[i];
while(s.str().length() < 2) //If there is less than two hex digits
s.str("0" + s.str()); //Prepend 0s
hash += s.str();
s.str("");
s.clear();
}
return hash;
}
int main()
{
string uinput; //String that holds user input
cout << "========XHA-64========\n\n";
//Prompt
cout << "Enter a string: ";
getline(cin, uinput);
cout << BYTES << " byte hash: " << CreateHash(uinput) << "\n\n";
return 0;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment