Last active
November 13, 2019 14:17
-
-
Save legionus/272b7d027a36c6c5912bdef945dd0da4 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/bin/bash -u | |
# Released into the Public Domain. | |
# | |
# Original implementation in C by Brad Conte (brad@bradconte.com) <https://github.com/B-Con/crypto-algorithms> | |
# Ported to Bash (lol) by Josh Junon (josh@junon.me) <https://github.com/qix-> | |
# | |
# Original gist is https://gist.github.com/Qix-/affef08b50686e54e1f2ca18f97a6ff7 | |
# Removed external utilities. | |
# | |
# Yes, it's absolutely as slow as it looks. | |
# | |
export LANG=C | |
odbash() | |
{ | |
local c x | |
while IFS= read -r -n 1 -d '' c; do | |
printf -v x "%d" "'$c" | |
printf '%4d' $(( $x & 0xff )) | |
done | |
printf '\n' | |
} | |
sha256() | |
{ | |
declare -a k data rhash bitlen state | |
declare -i datalen=0 | |
k=( \ | |
$((0x428a2f98)) $((0x71374491)) $((0xb5c0fbcf)) $((0xe9b5dba5)) $((0x3956c25b)) $((0x59f111f1)) $((0x923f82a4)) $((0xab1c5ed5)) \ | |
$((0xd807aa98)) $((0x12835b01)) $((0x243185be)) $((0x550c7dc3)) $((0x72be5d74)) $((0x80deb1fe)) $((0x9bdc06a7)) $((0xc19bf174)) \ | |
$((0xe49b69c1)) $((0xefbe4786)) $((0x0fc19dc6)) $((0x240ca1cc)) $((0x2de92c6f)) $((0x4a7484aa)) $((0x5cb0a9dc)) $((0x76f988da)) \ | |
$((0x983e5152)) $((0xa831c66d)) $((0xb00327c8)) $((0xbf597fc7)) $((0xc6e00bf3)) $((0xd5a79147)) $((0x06ca6351)) $((0x14292967)) \ | |
$((0x27b70a85)) $((0x2e1b2138)) $((0x4d2c6dfc)) $((0x53380d13)) $((0x650a7354)) $((0x766a0abb)) $((0x81c2c92e)) $((0x92722c85)) \ | |
$((0xa2bfe8a1)) $((0xa81a664b)) $((0xc24b8b70)) $((0xc76c51a3)) $((0xd192e819)) $((0xd6990624)) $((0xf40e3585)) $((0x106aa070)) \ | |
$((0x19a4c116)) $((0x1e376c08)) $((0x2748774c)) $((0x34b0bcb5)) $((0x391c0cb3)) $((0x4ed8aa4a)) $((0x5b9cca4f)) $((0x682e6ff3)) \ | |
$((0x748f82ee)) $((0x78a5636f)) $((0x84c87814)) $((0x8cc70208)) $((0x90befffa)) $((0xa4506ceb)) $((0xbef9a3f7)) $((0xc67178f2)) \ | |
) | |
state=( \ | |
$((0x6a09e667)) $((0xbb67ae85)) $((0x3c6ef372)) $((0xa54ff53a)) $((0x510e527f)) $((0x9b05688c)) $((0x1f83d9ab)) $((0x5be0cd19)) \ | |
) | |
bitlen=( 0 0 ) | |
dbl_int_add() | |
{ | |
if [ ${bitlen[0]} -gt $(( 0xffffffff - ${1} )) ]; then | |
bitlen[1]=$(( ${bitlen[1]} + 1 )) | |
fi | |
bitlen[0]=$(( ${bitlen[0]} + ${1} )) | |
} | |
rotright() | |
{ | |
eval $1=$(( (($2 >> $3) | ($2 << (32 - $3))) & 0xFFFFFFFF )) | |
} | |
ch() | |
{ | |
declare -i a=$2 b=$3 c=$4 nota | |
not32 nota $2 | |
eval $1=$(( ($a & $b) ^ ($nota & $c) )) | |
} | |
maj() | |
{ | |
declare -i a=$2 b=$3 c=$4 | |
eval $1=$(( ($a & $b) ^ ($a & $c) ^ ($b & $c) )) | |
} | |
ep0() | |
{ | |
declare -i a b c | |
rotright a $2 2 | |
rotright b $2 13 | |
rotright c $2 22 | |
eval $1=$(( $a ^ $b ^ $c )) | |
} | |
ep1() | |
{ | |
declare -i a b c | |
rotright a $2 6 | |
rotright b $2 11 | |
rotright c $2 25 | |
eval $1=$(( $a ^ $b ^ $c )) | |
} | |
sig0() | |
{ | |
declare -i a b | |
rotright a $2 7 | |
rotright b $2 18 | |
eval $1=$(( $a ^ $b ^ ($2 >> 3) )) | |
} | |
sig1() | |
{ | |
declare -i a b | |
rotright a $2 17 | |
rotright b $2 19 | |
eval $1=$(( $a ^ $b ^ ($2 >> 10) )) | |
} | |
b32() | |
{ | |
eval $1=$(( $2 & 0xFFFFFFFF )) | |
} | |
not32() | |
{ | |
declare -i a | |
b32 a $(( ~$2 )) | |
eval $1=$a | |
} | |
sha256_transform() | |
{ | |
declare -a m | |
declare -i t1 t2 x1 x2 | |
for (( i=0; i < 16; i++ )) do | |
declare -i j=$(($i * 4)) | |
b32 m[$i] $(( (${data[$j]} << 24) | (${data[$(($j + 1))]} << 16) | (${data[$(($j + 2))]} << 8) | ${data[$(($j + 3))]} )) | |
done | |
for (( i=16; i < 64; i++ )) do | |
sig1 x1 ${m[$(($i - 2))]} | |
sig0 x2 ${m[$(($i - 15))]} | |
b32 m[$i] $(( $x1 + ${m[$(($i - 7))]} + $x2 + ${m[$(($i - 16))]} )) | |
done | |
declare -i a=${state[0]} | |
declare -i b=${state[1]} | |
declare -i c=${state[2]} | |
declare -i d=${state[3]} | |
declare -i e=${state[4]} | |
declare -i f=${state[5]} | |
declare -i g=${state[6]} | |
declare -i h=${state[7]} | |
for (( i=0; i < 64; i++ )) do | |
ep1 x1 $e | |
ch x2 $e $f $g | |
b32 t1 $(( $h + $x1 + $x2 + ${k[$i]} + ${m[$i]} )) | |
ep0 x1 $a | |
maj x2 $a $b $c | |
b32 t2 $(( $x1 + $x2 )) | |
h=$g | |
g=$f | |
f=$e | |
b32 e $(( $d + $t1 )) | |
d=$c | |
c=$b | |
b=$a | |
b32 a $(( $t1 + $t2 )) | |
done | |
b32 state[0] $(( ${state[0]} + $a )) | |
b32 state[1] $(( ${state[1]} + $b )) | |
b32 state[2] $(( ${state[2]} + $c )) | |
b32 state[3] $(( ${state[3]} + $d )) | |
b32 state[4] $(( ${state[4]} + $e )) | |
b32 state[5] $(( ${state[5]} + $f )) | |
b32 state[6] $(( ${state[6]} + $g )) | |
b32 state[7] $(( ${state[7]} + $h )) | |
} | |
local line byte | |
while read -r line; do | |
for byte in $line; do | |
data[$datalen]=$byte | |
datalen=$(( $datalen + 1 )) | |
if [ $datalen -eq 64 ]; then | |
sha256_transform | |
dbl_int_add 512 | |
datalen=0 | |
fi | |
done | |
done < <(odbash) | |
declare -i i=$datalen | |
if [ $datalen -lt 56 ]; then | |
data[$i]=$(( 0x80 )) | |
i=$(( $i + 1 )) | |
while [ $i -lt 56 ]; do | |
data[$i]=0 | |
i=$(( $i + 1 )) | |
done | |
else | |
data[$i]=$(( 0x80 )) | |
i=$(( $i + 1 )) | |
while [ $i -lt 64 ]; do | |
data[$i]=0 | |
i=$(( $i + 1 )) | |
done | |
sha256_transform | |
for (( j=0; j < 56; j++ )) do | |
data[$j]=0 | |
done | |
fi | |
dbl_int_add $(( $datalen * 8 )) | |
data[63]=$(( ${bitlen[0]} & 0xFF )) | |
data[62]=$(( (${bitlen[0]} >> 8) & 0xFF )) | |
data[61]=$(( (${bitlen[0]} >> 16) & 0xFF )) | |
data[60]=$(( (${bitlen[0]} >> 24) & 0xFF )) | |
data[59]=$(( ${bitlen[1]} & 0xFF )) | |
data[58]=$(( (${bitlen[1]} >> 8) & 0xFF )) | |
data[57]=$(( (${bitlen[1]} >> 16) & 0xFF )) | |
data[56]=$(( (${bitlen[1]} >> 24) & 0xFF )) | |
sha256_transform | |
for (( j=0; j < 4; j++ )) do | |
rhash[$j]=$(( (${state[0]} >> (24 - $j * 8)) & 0xff )) | |
rhash[$(( $j + 4 ))]=$(( (${state[1]} >> (24 - $j * 8)) & 0xff )) | |
rhash[$(( $j + 8 ))]=$(( (${state[2]} >> (24 - $j * 8)) & 0xff )) | |
rhash[$(( $j + 12 ))]=$(( (${state[3]} >> (24 - $j * 8)) & 0xff )) | |
rhash[$(( $j + 16 ))]=$(( (${state[4]} >> (24 - $j * 8)) & 0xff )) | |
rhash[$(( $j + 20 ))]=$(( (${state[5]} >> (24 - $j * 8)) & 0xff )) | |
rhash[$(( $j + 24 ))]=$(( (${state[6]} >> (24 - $j * 8)) & 0xff )) | |
rhash[$(( $j + 28 ))]=$(( (${state[7]} >> (24 - $j * 8)) & 0xff )) | |
done | |
printf "%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x%02x\n" ${rhash[@]} | |
} | |
sha256 |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment