update the algorithm again
This commit is contained in:
parent
8c461dd178
commit
2bd897a6f6
1 changed files with 55 additions and 79 deletions
130
IGA.ts
130
IGA.ts
|
@ -1,6 +1,7 @@
|
|||
type padding = {
|
||||
padding: number[]
|
||||
seed: number
|
||||
generator: randomGenerator
|
||||
}
|
||||
|
||||
type verifyOut = {
|
||||
|
@ -51,7 +52,8 @@ function generatePadding(len: number, seed?: number): padding {
|
|||
}
|
||||
return {
|
||||
padding: out,
|
||||
seed: seed
|
||||
seed: seed,
|
||||
generator: generator
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -98,17 +100,6 @@ function hex2bin(hex: string): string {
|
|||
}
|
||||
return bin
|
||||
}
|
||||
function xor(a: string, b: string): string {
|
||||
let out = ""
|
||||
for (let i = 0; i < a.length; i++) {
|
||||
if (a[i] == b[i]) {
|
||||
out += "0"
|
||||
} else {
|
||||
out += "1"
|
||||
}
|
||||
}
|
||||
return out
|
||||
}
|
||||
|
||||
function checksum(input: string) {
|
||||
let state: string[] = []
|
||||
|
@ -135,34 +126,45 @@ function checksum(input: string) {
|
|||
return state.join("")
|
||||
}
|
||||
|
||||
function hashBlock(block: number[][], salt: number, iterations: number): number[][] {
|
||||
for (let it = 0; it < iterations; it++) {
|
||||
let state: number[][] = copy(block, true)
|
||||
//Add columns
|
||||
for (let i = 0; i < block.length; i++) {
|
||||
for (let ii = 0; ii < block[i].length; ii++) {
|
||||
let temp = state[i][ii]+(state[i][ii+1] ? state[i][ii+1] : (state[i+1] ? state[i+1][0] : state[0][0]))
|
||||
while (temp > 65536) {
|
||||
let subtemp = it==0 ? 2411 : state[i][ii-1] ? state[i][ii-1] : (state[i-1] ? state[i-1][state[i-1].length-1] : state[state.length-1][state[state.length-1].length-1])
|
||||
temp -= subtemp == 0 ? 2411 : subtemp
|
||||
function hashInternal(toHash: number[], len: number, salt: number): number[] {
|
||||
let complete: number[] = []
|
||||
|
||||
while (toHash.length > 0) {
|
||||
let inp = copy(toHash, true)
|
||||
for (let i = 0; i < complete.length; i++) {
|
||||
inp.push(complete[i])
|
||||
}
|
||||
block[i][ii] = temp
|
||||
let selected: number[] = []
|
||||
for (let i = 0; i < len; i++) {
|
||||
selected.push(inp[i])
|
||||
}
|
||||
inp = inp.slice(len, inp.length)
|
||||
toHash = toHash.slice(len, toHash.length)
|
||||
let curr = 0
|
||||
for (let i = 0; i < inp.length; i++) {
|
||||
selected[curr] = (selected[curr] + inp[i] + salt) % 65536
|
||||
curr++
|
||||
if (curr >= len) {
|
||||
curr = 0
|
||||
}
|
||||
}
|
||||
state = copy(block, true)
|
||||
//Add rows
|
||||
for (let i = 0; i < block.length; i++) {
|
||||
for (let ii = 0; ii < block[i].length; ii++) {
|
||||
let temp = state[i][ii]+(state[i+1] ? state[i+1][ii] : (state[0][ii+1] ? state[0][ii+1] : state[0][0]))
|
||||
while (temp > 65536) {
|
||||
let subtemp = it==0 ? 2411 : state[i-1] ? state[i-1][ii] : (state[state.length-1][ii-1] ? state[state.length-1][ii-1] : state[state.length-1][state[state.length-1].length-1])
|
||||
temp -= subtemp == 0 ? 2411 : subtemp
|
||||
}
|
||||
block[i][ii] = temp
|
||||
for (let i = 0; i < selected.length; i++) {
|
||||
complete.push(selected[i])
|
||||
}
|
||||
}
|
||||
|
||||
return complete
|
||||
}
|
||||
function hashInternal2(toHash: number[], salt: number): number[] {
|
||||
let state = copy(toHash, true)
|
||||
for (let i = 0; i < toHash.length; i++) {
|
||||
let temp = state[i] + (state[i+1] ? state[i+1] : state[0]) + salt
|
||||
while (temp >= 65536) {
|
||||
temp -= state[i-1] ? state[i-1] : state[state.length-1]
|
||||
}
|
||||
return block
|
||||
toHash[i] = temp
|
||||
}
|
||||
return toHash
|
||||
}
|
||||
|
||||
function hash(input: string, salt: number = 0, len: number = 32, seed?: number): string {
|
||||
|
@ -173,7 +175,7 @@ function hash(input: string, salt: number = 0, len: number = 32, seed?: number):
|
|||
throw new Error("Length must be at least 16")
|
||||
}
|
||||
if (len > 512) {
|
||||
throw new Error("Length must be at most 512")
|
||||
throw new Error("Length can't be more than 512")
|
||||
}
|
||||
if (seed != undefined) {
|
||||
if (seed < 0 || seed > 65535) {
|
||||
|
@ -182,58 +184,32 @@ function hash(input: string, salt: number = 0, len: number = 32, seed?: number):
|
|||
}
|
||||
const iterations = len*2
|
||||
const padding = generatePadding(len, seed);
|
||||
let blocks: number[][][] = [[[]]] // len x 16
|
||||
for (let ip = 0; ip < padding.padding.length; ip++) {
|
||||
if (blocks[blocks.length-1][blocks[blocks.length-1].length-1].length == len) {
|
||||
blocks[blocks.length-1].push([])
|
||||
}
|
||||
blocks[blocks.length-1][blocks[blocks.length-1].length-1].push(padding.padding[ip])
|
||||
let toHash: number[] = []
|
||||
for (let i = 0; i < padding.padding.length; i++) {
|
||||
toHash.push(padding.padding[i])
|
||||
}
|
||||
for (let i = 0; i < input.length; i++) {
|
||||
if (input.charCodeAt(i) < 0 || input.charCodeAt(i) > 65535) {
|
||||
throw new Error("Character at index " + i + " is not a valid character")
|
||||
}
|
||||
if (blocks[blocks.length-1].length == 16 && blocks[blocks.length-1][blocks[blocks.length-1].length-1].length == len) {
|
||||
blocks.push([[]])
|
||||
for (let ip = 0; ip < padding.padding.length; ip++) {
|
||||
if (blocks[blocks.length-1][blocks[blocks.length-1].length-1].length == len) {
|
||||
blocks[blocks.length-1].push([])
|
||||
if (i % len == 0) {
|
||||
toHash.push(padding.generator.next())
|
||||
}
|
||||
blocks[blocks.length-1][blocks[blocks.length-1].length-1].push(padding.padding[ip])
|
||||
toHash.push(input.charCodeAt(i))
|
||||
}
|
||||
while ((toHash.length % len != 0) || (toHash.length < iterations)) {
|
||||
toHash.push(padding.generator.next())
|
||||
}
|
||||
if (blocks[blocks.length-1][blocks[blocks.length-1].length-1].length == len) {
|
||||
blocks[blocks.length-1].push([])
|
||||
}
|
||||
blocks[blocks.length-1][blocks[blocks.length-1].length-1].push(input.charCodeAt(i))
|
||||
}
|
||||
let pPos = 0
|
||||
while (blocks[blocks.length-1].length != 16 || blocks[blocks.length-1][blocks[blocks.length-1].length-1].length != len) {
|
||||
if (blocks[blocks.length-1][blocks[blocks.length-1].length-1].length == len) {
|
||||
blocks[blocks.length-1].push([])
|
||||
}
|
||||
blocks[blocks.length-1][blocks[blocks.length-1].length-1].push(padding.padding[pPos])
|
||||
pPos++
|
||||
if (pPos >= padding.padding.length) {
|
||||
pPos = 0
|
||||
}
|
||||
}
|
||||
for (let i = 0; i < blocks.length; i++) {
|
||||
blocks[i] = hashBlock(blocks[i], salt, iterations)
|
||||
for (let it = 0; it < iterations; it++) {
|
||||
toHash = hashInternal(toHash, len, salt)
|
||||
toHash = hashInternal2(toHash, salt)
|
||||
}
|
||||
const pBin = fixbin(dec2bin(padding.seed), 16)
|
||||
let dataBins: string[] = []
|
||||
for (let i = 0; i < blocks.length; i++) {
|
||||
dataBins[i] = ""
|
||||
for (let ii = 0; dataBins[i].length < len*4-32; ii++) {
|
||||
dataBins[i] += fixbin(dec2bin(blocks[i][0][ii]), 16)
|
||||
let dataBin = ""
|
||||
for (let i = 0; dataBin.length < len*4-32; i++) {
|
||||
dataBin += fixbin(dec2bin(toHash[i]), 16)
|
||||
}
|
||||
}
|
||||
while (dataBins.length > 1) {
|
||||
dataBins[0] = xor(dataBins[0], dataBins[1])
|
||||
dataBins.splice(1, 1)
|
||||
}
|
||||
let hash = bin2hex(pBin + dataBins[0])
|
||||
let hash = bin2hex(pBin + dataBin)
|
||||
const crc = checksum(hash)
|
||||
hash += bin2hex(crc)
|
||||
return hash
|
||||
|
@ -247,7 +223,7 @@ function verifyHash(input: string, inHash: string, salt: number = 0, len: number
|
|||
throw new Error("Length must be at least 16")
|
||||
}
|
||||
if (len > 512) {
|
||||
throw new Error("Length must be at most 512")
|
||||
throw new Error("Length can't be more than 512")
|
||||
}
|
||||
if (inHash.length != len) {
|
||||
throw new Error("The hash is not " + len + " long")
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue