1063 lines
34 KiB
Plaintext
1063 lines
34 KiB
Plaintext
#Requires AutoHotkey v2.0
|
|||
|
|
#Warn LocalSameAsGlobal, Off
|
||
|
|
|
||
|
|
LC_Version := "0.0.24.04"
|
||
|
|
|
||
|
|
; ==============================================================================
|
||
|
|
; ASCII / Binary
|
||
|
|
; ==============================================================================
|
||
|
|
|
||
|
|
LC_ASCII2Bin(s, pretty := false) {
|
||
|
|
r := ""
|
||
|
|
for i, ch in StrSplit(s) {
|
||
|
|
byte := Ord(ch), bits := ""
|
||
|
|
Loop 8
|
||
|
|
bits := ((byte >> (A_Index - 1)) & 1) bits
|
||
|
|
r .= bits
|
||
|
|
if pretty && i < StrLen(s)
|
||
|
|
r .= " "
|
||
|
|
}
|
||
|
|
return r
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_Ascii2Bin2(Ascii) {
|
||
|
|
Out := ""
|
||
|
|
for Char in StrSplit(Ascii)
|
||
|
|
Loop 8
|
||
|
|
Out .= !!(Ord(Char) & (1 << (8 - A_Index)))
|
||
|
|
return Out
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_Bin2Ascii(Bin) {
|
||
|
|
Bin := RegExReplace(Bin, "[^10]")
|
||
|
|
Out := ""
|
||
|
|
Loop StrLen(Bin) // 8 {
|
||
|
|
val := 0
|
||
|
|
for Bit in StrSplit(SubStr(Bin, (A_Index - 1) * 8 + 1, 8))
|
||
|
|
val += val + Bit
|
||
|
|
Out .= Chr(val)
|
||
|
|
}
|
||
|
|
return Out
|
||
|
|
}
|
||
|
|
|
||
|
|
; ==============================================================================
|
||
|
|
; Binary String Encode/Decode (text <-> binary string)
|
||
|
|
; ==============================================================================
|
||
|
|
|
||
|
|
LC_BinStr_EncodeText(Text, Pretty := false, Encoding := "UTF-8") {
|
||
|
|
Len := StrPut(Text, Encoding) - 1
|
||
|
|
Buf := Buffer(Len)
|
||
|
|
StrPut(Text, Buf, Encoding)
|
||
|
|
BinStr := ""
|
||
|
|
LC_BinStr_Encode(&BinStr, &Buf, Len, Pretty)
|
||
|
|
return BinStr
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_BinStr_DecodeText(Text, Encoding := "UTF-8") {
|
||
|
|
Len := LC_BinStr_Decode(&Buf, Text)
|
||
|
|
return StrGet(Buf, Len, Encoding)
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_BinStr_Encode(&Out, &InBuf, InLen, Pretty := false) {
|
||
|
|
Out := ""
|
||
|
|
Loop InLen {
|
||
|
|
Byte := NumGet(InBuf, A_Index - 1, "UChar")
|
||
|
|
Loop 8
|
||
|
|
Out .= (Byte >> (8 - A_Index)) & 1
|
||
|
|
if Pretty
|
||
|
|
Out .= " "
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_BinStr_Decode(&Out, InTxt) {
|
||
|
|
InTxt := RegExReplace(InTxt, "[^01]")
|
||
|
|
ByteCount := StrLen(InTxt) // 8
|
||
|
|
Out := Buffer(ByteCount, 0)
|
||
|
|
BitIndex := 1
|
||
|
|
Loop ByteCount {
|
||
|
|
Byte := 0
|
||
|
|
Loop 8 {
|
||
|
|
Byte := (Byte << 1) | SubStr(InTxt, BitIndex, 1)
|
||
|
|
BitIndex += 1
|
||
|
|
}
|
||
|
|
NumPut("UChar", Byte, Out, A_Index - 1)
|
||
|
|
}
|
||
|
|
return ByteCount
|
||
|
|
}
|
||
|
|
|
||
|
|
; ==============================================================================
|
||
|
|
; ASCII85 (Original + Z85)
|
||
|
|
; ==============================================================================
|
||
|
|
|
||
|
|
LC_ASCII85_Encode(content, variant := "") {
|
||
|
|
content := StrReplace(StrReplace(content, "<~"), "~>")
|
||
|
|
bytes := []
|
||
|
|
for ch in StrSplit(content)
|
||
|
|
bytes.Push(Ord(ch))
|
||
|
|
variant := __LC_ASCII85_getVariant(variant)
|
||
|
|
n := bytes.Length, string := "", i := 1
|
||
|
|
while (i <= n) {
|
||
|
|
if (i - 1 + 4 > n)
|
||
|
|
bytes.Push(0, 0, 0)
|
||
|
|
tuple := ((bytes[i] << 24) + (bytes[i + 1] << 16) + (bytes[i + 2] << 8) + bytes[i + 3]) >> 0
|
||
|
|
if (variant["zeroTupleChar"] = "null") || (tuple > 0) {
|
||
|
|
digits := []
|
||
|
|
Loop 5 {
|
||
|
|
digits.Push(Mod(tuple, 85))
|
||
|
|
tuple := tuple // 85
|
||
|
|
}
|
||
|
|
newarr := []
|
||
|
|
for t_idx, t_val in digits
|
||
|
|
newarr.InsertAt(1, t_val)
|
||
|
|
digits := newarr
|
||
|
|
if (n < (i - 1 + 4))
|
||
|
|
digits := __LC_ASCII85_splice(digits, n - (i - 1 + 4), 4)
|
||
|
|
for t_k, t_v in digits
|
||
|
|
string .= (variant["alphabet"] = "null") ? Chr(t_v + 33) : SubStr(variant["alphabet"], t_v + 1, 1)
|
||
|
|
} else {
|
||
|
|
string .= variant["zeroTupleChar"]
|
||
|
|
}
|
||
|
|
i += 4
|
||
|
|
}
|
||
|
|
return string
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_ASCII85_Decode(content, variant := "") {
|
||
|
|
string := Trim(content)
|
||
|
|
variant := __LC_ASCII85_getVariant(variant)
|
||
|
|
n := StrLen(string)
|
||
|
|
bytes := [], i := 1
|
||
|
|
while (i <= n) {
|
||
|
|
if (SubStr(string, i, 1) = variant.zeroTupleChar) {
|
||
|
|
bytes.Push(0, 0, 0, 0)
|
||
|
|
i++
|
||
|
|
} else {
|
||
|
|
digits := []
|
||
|
|
for character in StrSplit(SubStr(string, i, 5)) {
|
||
|
|
digit := (variant["alphabet"] = "null") ? Ord(character) - 33 : InStr(variant["alphabet"], character) - 1
|
||
|
|
if (digit < 0 || digit > 84)
|
||
|
|
throw Error(Format("Invalid character '{1}' at index {2}", character, i + A_Index - 1))
|
||
|
|
digits.Push(digit)
|
||
|
|
}
|
||
|
|
tuple := 0 + digits[1] * 52200625 + digits[2] * 614125 + ((i - 1 + 2 < n) ? digits[3] : 84) * 7225 + ((i - 1 + 3 < n) ? digits[4] : 84) * 85 + ((i - 1 + 4 < n) ? digits[5] : 84)
|
||
|
|
tupleBytes := [(tuple >> 24) & 0xFF, (tuple >> 16) & 0xFF, (tuple >> 8) & 0xFF, tuple & 0xFF]
|
||
|
|
if (n < i - 1 + 5)
|
||
|
|
tupleBytes := __LC_ASCII85_splice(tupleBytes, n - (i - 1 + 5), 5)
|
||
|
|
for t_v in tupleBytes
|
||
|
|
bytes.Push(t_v)
|
||
|
|
i += 5
|
||
|
|
}
|
||
|
|
}
|
||
|
|
decoded := ""
|
||
|
|
for v in bytes
|
||
|
|
decoded .= Chr(v)
|
||
|
|
return decoded
|
||
|
|
}
|
||
|
|
|
||
|
|
__LC_ASCII85_getVariant(variant := "") {
|
||
|
|
if InStr(variant, "z")
|
||
|
|
return {name:"Z85", label:"Z85 (ZeroMQ)", alphabet:"0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ.-:+=^!/*?&<>()[]{}@%$#", zeroTupleChar:"null"}
|
||
|
|
return {name:"original", label:"Original", alphabet:"null", zeroTupleChar:"z"}
|
||
|
|
}
|
||
|
|
|
||
|
|
__LC_ASCII85_splice(arr, start, deleteCount := "") {
|
||
|
|
len := arr.Length, newarr := []
|
||
|
|
startIndex := start
|
||
|
|
if (start > len)
|
||
|
|
startIndex := len
|
||
|
|
else if (start < 0)
|
||
|
|
startIndex := len + start
|
||
|
|
if (len + start < 0)
|
||
|
|
startIndex := 0
|
||
|
|
Loop startIndex
|
||
|
|
newarr.Push(arr[A_Index])
|
||
|
|
if (deleteCount != "") {
|
||
|
|
if (deleteCount < 0)
|
||
|
|
deleteCount := 0
|
||
|
|
j := 1 + startIndex + deleteCount
|
||
|
|
while (j <= len) {
|
||
|
|
newarr.Push(arr[j])
|
||
|
|
j++
|
||
|
|
}
|
||
|
|
}
|
||
|
|
return newarr
|
||
|
|
}
|
||
|
|
|
||
|
|
; ==============================================================================
|
||
|
|
; Base64 / Hex via Windows CryptoAPI
|
||
|
|
; ==============================================================================
|
||
|
|
|
||
|
|
LC_Base64_EncodeText(Text, Encoding := "UTF-8") {
|
||
|
|
Len := StrPut(Text, Encoding) - 1
|
||
|
|
Bin := Buffer(Len)
|
||
|
|
StrPut(Text, Bin, Encoding)
|
||
|
|
Base64 := ""
|
||
|
|
LC_Base64_Encode(&Base64, &Bin, Len)
|
||
|
|
return Base64
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_Base64_DecodeText(Text, Encoding := "UTF-8") {
|
||
|
|
Len := LC_Base64_Decode(&Bin, Text)
|
||
|
|
return StrGet(Bin, Len, Encoding)
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_Base64_Encode(&OutVar, &InVar, InLen) {
|
||
|
|
return LC_Bin2Str(&OutVar, &InVar, InLen, 0x40000001)
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_Base64_Decode(&OutVar, InVar) {
|
||
|
|
return LC_Str2Bin(&OutVar, InVar, 0x1)
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_Bin2Hex(&OutVar, &InVar, InLen, Pretty := false) {
|
||
|
|
return LC_Bin2Str(&OutVar, &InVar, InLen, Pretty ? 0xb : 0x4000000c)
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_Hex2Bin(&OutVar, &InVar) {
|
||
|
|
return LC_Str2Bin(&OutVar, &InVar, 0x8)
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_Bin2Str(&OutVar, &InVar, InLen, Flags) {
|
||
|
|
OutLen := 0
|
||
|
|
DllCall("Crypt32\CryptBinaryToString", "ptr", InVar, "uint", InLen, "uint", Flags, "ptr", 0, "uint*", &OutLen)
|
||
|
|
OutVar := Buffer(OutLen * 2)
|
||
|
|
DllCall("Crypt32\CryptBinaryToString", "ptr", InVar, "uint", InLen, "uint", Flags, "ptr", OutVar, "uint*", &OutLen)
|
||
|
|
return OutLen
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_Str2Bin(&OutVar, InVar, Flags) {
|
||
|
|
OutLen := 0
|
||
|
|
DllCall("Crypt32\CryptStringToBinary", "ptr", InVar, "uint", StrLen(InVar), "uint", Flags, "ptr", 0, "uint*", &OutLen, "ptr", 0, "ptr", 0)
|
||
|
|
OutVar := Buffer(OutLen)
|
||
|
|
DllCall("Crypt32\CryptStringToBinary", "ptr", InVar, "uint", StrLen(InVar), "uint", Flags, "ptr", OutVar, "uint*", &OutLen, "ptr", 0, "ptr", 0)
|
||
|
|
return OutLen
|
||
|
|
}
|
||
|
|
|
||
|
|
; ==============================================================================
|
||
|
|
; Caesar / ROT
|
||
|
|
; ==============================================================================
|
||
|
|
|
||
|
|
LC_Caesar(string, num := 2) {
|
||
|
|
ret := ""
|
||
|
|
for ch in StrSplit(string) {
|
||
|
|
c := Ord(ch)
|
||
|
|
if (c > 64 && c < 91)
|
||
|
|
ret .= Chr(Mod(c - 65 + num, 26) + 65)
|
||
|
|
else if (c > 96 && c < 123)
|
||
|
|
ret .= Chr(Mod(c - 97 + num, 26) + 97)
|
||
|
|
else
|
||
|
|
ret .= ch
|
||
|
|
}
|
||
|
|
return ret
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_Rot5(string) {
|
||
|
|
s := ""
|
||
|
|
for ch in StrSplit(string) {
|
||
|
|
c := Ord(ch)
|
||
|
|
s .= (c >= 48 && c <= 57) ? ((c < 53) ? c + 5 : c - 5) : c
|
||
|
|
}
|
||
|
|
return s
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_Rot13(string) {
|
||
|
|
s := ""
|
||
|
|
for ch in StrSplit(string) {
|
||
|
|
c := Ord(ch)
|
||
|
|
if ((c >= 97 && c <= 109) || (c >= 65 && c <= 77))
|
||
|
|
c += 13
|
||
|
|
else if ((c >= 110 && c <= 122) || (c >= 78 && c <= 90))
|
||
|
|
c -= 13
|
||
|
|
s .= Chr(c)
|
||
|
|
}
|
||
|
|
return s
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_Rot18(string) {
|
||
|
|
return LC_Rot13(LC_Rot5(string))
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_Rot47(string) {
|
||
|
|
s := ""
|
||
|
|
for ch in StrSplit(string) {
|
||
|
|
c := Ord(ch)
|
||
|
|
c += (c >= 33 && c <= 79 ? 47 : (c >= 80 && c <= 126 ? -47 : 0))
|
||
|
|
s .= Chr(c)
|
||
|
|
}
|
||
|
|
return s
|
||
|
|
}
|
||
|
|
|
||
|
|
; ==============================================================================
|
||
|
|
; Base conversion
|
||
|
|
; ==============================================================================
|
||
|
|
|
||
|
|
LC_To_Dec(b, n) {
|
||
|
|
d := 0, n := StrUpper(n)
|
||
|
|
for i, ch in StrSplit(n) {
|
||
|
|
d *= b, k := ch
|
||
|
|
if (k < "0" || k > "9")
|
||
|
|
k := Ord(k) - 55
|
||
|
|
else
|
||
|
|
k := Integer(k)
|
||
|
|
d += k
|
||
|
|
}
|
||
|
|
return d
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_From_Dec(b, n) {
|
||
|
|
m := ""
|
||
|
|
Loop {
|
||
|
|
d := Mod(n, b), n //= b
|
||
|
|
m := (d < 10 ? d : Chr(d + 55)) m
|
||
|
|
if n < 1
|
||
|
|
Break
|
||
|
|
}
|
||
|
|
return m
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_Dec2Hex(x) {
|
||
|
|
return LC_From_Dec(16, x)
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_Hex2Dec(x) {
|
||
|
|
return LC_To_Dec(16, x)
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_Numvert(num, from, to) {
|
||
|
|
return LC_From_Dec(to, LC_To_Dec(from, num))
|
||
|
|
}
|
||
|
|
|
||
|
|
; ==============================================================================
|
||
|
|
; Div2
|
||
|
|
; ==============================================================================
|
||
|
|
|
||
|
|
LC_Div2_encode(input, WithAutoTrim := true, numproc := 1) {
|
||
|
|
if WithAutoTrim
|
||
|
|
input := StrReplace(input, A_Space, "_")
|
||
|
|
Loop numproc {
|
||
|
|
final := "", inputlen := StrLen(input)
|
||
|
|
divmax := Ceil((0.5 * inputlen) + 1)
|
||
|
|
Loop inputlen {
|
||
|
|
temp := SubStr(input, A_Index, 1)
|
||
|
|
q := inputlen + 1 - A_Index
|
||
|
|
temp2 := SubStr(input, q, 1)
|
||
|
|
if (A_Index < divmax) {
|
||
|
|
final .= temp
|
||
|
|
if (A_Index != q)
|
||
|
|
final .= temp2
|
||
|
|
} else
|
||
|
|
Break
|
||
|
|
}
|
||
|
|
input := final
|
||
|
|
}
|
||
|
|
return final
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_Div2_decode(input, WithAutoTrim := true, numproc := 1) {
|
||
|
|
if WithAutoTrim
|
||
|
|
input := StrReplace(input, A_Space, "_")
|
||
|
|
Loop numproc {
|
||
|
|
i := 1, final := "", inputlen := StrLen(input)
|
||
|
|
loopc := Ceil(inputlen * (1/2))
|
||
|
|
Loop loopc {
|
||
|
|
if (i <= inputlen)
|
||
|
|
final .= SubStr(input, i, 1)
|
||
|
|
i += 2
|
||
|
|
}
|
||
|
|
i := inputlen
|
||
|
|
Loop loopc {
|
||
|
|
if (i <= inputlen) {
|
||
|
|
if (Mod(SubStr(i, 0, 1) + 0, 2) = 1) {
|
||
|
|
if (i != 1)
|
||
|
|
final .= SubStr(input, i - 1, 1)
|
||
|
|
} else {
|
||
|
|
final .= SubStr(input, i, 1)
|
||
|
|
}
|
||
|
|
}
|
||
|
|
i -= 2
|
||
|
|
}
|
||
|
|
input := final
|
||
|
|
}
|
||
|
|
return final
|
||
|
|
}
|
||
|
|
|
||
|
|
; ==============================================================================
|
||
|
|
; URI / URL
|
||
|
|
; ==============================================================================
|
||
|
|
|
||
|
|
LC_UriEncode(Uri, RE := "[0-9A-Za-z]") {
|
||
|
|
Var := Buffer(StrPut(Uri, "UTF-8") - 1), StrPut(Uri, Var, "UTF-8"), Res := ""
|
||
|
|
Loop Var.Size {
|
||
|
|
Code := NumGet(Var, A_Index - 1, "UChar")
|
||
|
|
Res .= (Chr(Code) ~= RE) ? Chr(Code) : Format("%{:02X}", Code)
|
||
|
|
}
|
||
|
|
return Res
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_UriDecode(Uri, Encoding := "UTF-8") {
|
||
|
|
Pos := 1
|
||
|
|
while Pos := RegExMatch(Uri, "i)(%[\da-f]{2})+", &Code, Pos) {
|
||
|
|
Var := Buffer(StrLen(Code[0]) // 3, 0), CodeTxt := SubStr(Code[0], 2)
|
||
|
|
Loop Var.Size
|
||
|
|
NumPut("UChar", Integer("0x" SubStr(CodeTxt, (A_Index - 1) * 2 + 1, 2)), Var, A_Index - 1)
|
||
|
|
Decoded := StrGet(Var, Var.Size, Encoding)
|
||
|
|
Uri := SubStr(Uri, 1, Pos - 1) Decoded SubStr(Uri, Pos + StrLen(Code[0]))
|
||
|
|
Pos += StrLen(Decoded) + 1
|
||
|
|
}
|
||
|
|
return Uri
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_UrlEncode(Url) {
|
||
|
|
return LC_UriEncode(Url, "[!#$&-;=?-Z_a-z~]")
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_UrlDecode(url) {
|
||
|
|
return LC_UriDecode(url)
|
||
|
|
}
|
||
|
|
|
||
|
|
; ==============================================================================
|
||
|
|
; Vigenere
|
||
|
|
; ==============================================================================
|
||
|
|
|
||
|
|
LC_VigenereCipher(string, key, enc := 1) {
|
||
|
|
enc := ""
|
||
|
|
DllCall("user32\CharUpperW", "ptr", StrPtr(string))
|
||
|
|
string := RegExReplace(string, "[^A-Z]")
|
||
|
|
for ch in StrSplit(string) {
|
||
|
|
a := Ord(ch) - 65
|
||
|
|
b := Ord(SubStr(key, 1 + Mod(A_Index - 1, StrLen(key)), 1)) - 65
|
||
|
|
enc .= Chr(Mod(a + b, 26) + 65)
|
||
|
|
}
|
||
|
|
return enc
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_VigenereDecipher(string, key) {
|
||
|
|
dec := ""
|
||
|
|
for ch in StrSplit(key)
|
||
|
|
dec .= Chr(26 - (Ord(ch) - 65) + 65)
|
||
|
|
return LC_VigenereCipher(string, dec)
|
||
|
|
}
|
||
|
|
|
||
|
|
; ==============================================================================
|
||
|
|
; CryptoAPI Hash Core (CalcAddrHash etc.)
|
||
|
|
; ==============================================================================
|
||
|
|
|
||
|
|
LC_CalcAddrHash(addr, length, algid, &hash := 0, &hashlength := 0) {
|
||
|
|
static h := [0,1,2,3,4,5,6,7,8,9,"a","b","c","d","e","f"]
|
||
|
|
hProv := hHash := o := ""
|
||
|
|
if DllCall("advapi32\CryptAcquireContext", "ptr*", &hProv, "ptr", 0, "ptr", 0, "uint", 24, "uint", 0xF0000000) = 0 {
|
||
|
|
if DllCall("advapi32\CryptCreateHash", "ptr", hProv, "uint", algid, "uint", 0, "uint", 0, "ptr*", &hHash) = 0 {
|
||
|
|
if DllCall("advapi32\CryptHashData", "ptr", hHash, "ptr", addr, "uint", length, "uint", 0) = 0 {
|
||
|
|
if DllCall("advapi32\CryptGetHashParam", "ptr", hHash, "uint", 2, "ptr", 0, "uint*", &hashlength, "uint", 0) = 0 {
|
||
|
|
hash := Buffer(hashlength, 0)
|
||
|
|
if DllCall("advapi32\CryptGetHashParam", "ptr", hHash, "uint", 2, "ptr", hash, "uint*", &hashlength, "uint", 0) = 0 {
|
||
|
|
Loop hashlength {
|
||
|
|
v := NumGet(hash, A_Index - 1, "UChar")
|
||
|
|
o .= h[(v >> 4) + 1] h[(v & 0xF) + 1]
|
||
|
|
}
|
||
|
|
}
|
||
|
|
}
|
||
|
|
}
|
||
|
|
DllCall("advapi32\CryptDestroyHash", "ptr", hHash)
|
||
|
|
}
|
||
|
|
DllCall("advapi32\CryptReleaseContext", "ptr", hProv, "uint", 0)
|
||
|
|
}
|
||
|
|
return o
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_CalcStringHash(string, algid, encoding := "UTF-8", &hash := 0, &hashlength := 0) {
|
||
|
|
chrlength := (encoding = "CP1200" || encoding = "UTF-16") ? 2 : 1
|
||
|
|
length := (StrPut(string, encoding) - 1) * chrlength
|
||
|
|
data := Buffer(length, 0)
|
||
|
|
StrPut(string, data, length // chrlength, encoding)
|
||
|
|
return LC_CalcAddrHash(data, length, algid, &hash, &hashlength)
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_CalcHexHash(hexstring, algid) {
|
||
|
|
length := StrLen(hexstring) // 2
|
||
|
|
data := Buffer(length, 0)
|
||
|
|
Loop length
|
||
|
|
NumPut("UChar", Integer("0x" SubStr(hexstring, 2 * A_Index - 1, 2)), data, A_Index - 1)
|
||
|
|
return LC_CalcAddrHash(data, length, algid)
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_CalcFileHash(filename, algid, chunkSize := 0, &hash := 0, &hashlength := 0) {
|
||
|
|
fpos := ""
|
||
|
|
f := FileOpen(filename, "r")
|
||
|
|
if !f
|
||
|
|
return ""
|
||
|
|
f.Pos := 0
|
||
|
|
if (!chunkSize && f.Length > 0x7FFFFFFF)
|
||
|
|
return ""
|
||
|
|
if (!chunkSize) {
|
||
|
|
data := Buffer(f.Length, 0)
|
||
|
|
f.RawRead(data, f.Length)
|
||
|
|
return LC_CalcAddrHash(data, f.Length, algid, &hash, &hashlength)
|
||
|
|
}
|
||
|
|
hashlength := 0
|
||
|
|
while (f.Pos < f.Length) {
|
||
|
|
readlength := (f.Length - fpos > chunkSize) ? chunkSize : f.Length - f.Pos
|
||
|
|
data := Buffer(hashlength + readlength, 0)
|
||
|
|
DllCall("RtlMoveMemory", "ptr", data, "ptr", hash, "ptr", hashlength)
|
||
|
|
f.RawRead(data, hashlength + readlength)
|
||
|
|
h := LC_CalcAddrHash(data, hashlength + readlength, algid, &hash, &hashlength)
|
||
|
|
}
|
||
|
|
return h
|
||
|
|
}
|
||
|
|
|
||
|
|
; ==============================================================================
|
||
|
|
; MD2 / MD4 / MD5 / SHA / SHA256 / SHA384 / SHA512 wrappers
|
||
|
|
; ==============================================================================
|
||
|
|
|
||
|
|
LC_MD2(string, encoding := "UTF-8") => LC_CalcStringHash(string, 0x8001, encoding)
|
||
|
|
LC_HexMD2(hexstring) => LC_CalcHexHash(hexstring, 0x8001)
|
||
|
|
LC_FileMD2(filename) => LC_CalcFileHash(filename, 0x8001, 64*1024)
|
||
|
|
LC_AddrMD2(addr, length) => LC_CalcAddrHash(addr, length, 0x8001)
|
||
|
|
|
||
|
|
LC_MD4(string, encoding := "UTF-8") => LC_CalcStringHash(string, 0x8002, encoding)
|
||
|
|
LC_HexMD4(hexstring) => LC_CalcHexHash(hexstring, 0x8002)
|
||
|
|
LC_FileMD4(filename) => LC_CalcFileHash(filename, 0x8002, 64*1024)
|
||
|
|
LC_AddrMD4(addr, length) => LC_CalcAddrHash(addr, length, 0x8002)
|
||
|
|
|
||
|
|
LC_MD5(string, encoding := "UTF-8") => LC_CalcStringHash(string, 0x8003, encoding)
|
||
|
|
LC_HexMD5(hexstring) => LC_CalcHexHash(hexstring, 0x8003)
|
||
|
|
LC_FileMD5(filename) => LC_CalcFileHash(filename, 0x8003, 64*1024)
|
||
|
|
LC_AddrMD5(addr, length) => LC_CalcAddrHash(addr, length, 0x8003)
|
||
|
|
|
||
|
|
LC_SHA(string, encoding := "UTF-8") => LC_CalcStringHash(string, 0x8004, encoding)
|
||
|
|
LC_HexSHA(hexstring) => LC_CalcHexHash(hexstring, 0x8004)
|
||
|
|
LC_FileSHA(filename) => LC_CalcFileHash(filename, 0x8004, 64*1024)
|
||
|
|
LC_AddrSHA(addr, length) => LC_CalcAddrHash(addr, length, 0x8004)
|
||
|
|
|
||
|
|
LC_SHA256(string, encoding := "UTF-8") => LC_CalcStringHash(string, 0x800C, encoding)
|
||
|
|
LC_HexSHA256(hexstring) => LC_CalcHexHash(hexstring, 0x800C)
|
||
|
|
LC_FileSHA256(filename) => LC_CalcFileHash(filename, 0x800C, 64*1024)
|
||
|
|
LC_AddrSHA256(addr, length) => LC_CalcAddrHash(addr, length, 0x800C)
|
||
|
|
|
||
|
|
LC_SHA384(string, encoding := "UTF-8") => LC_CalcStringHash(string, 0x800D, encoding)
|
||
|
|
LC_HexSHA384(hexstring) => LC_CalcHexHash(hexstring, 0x800D)
|
||
|
|
LC_FileSHA384(filename) => LC_CalcFileHash(filename, 0x800D, 64*1024)
|
||
|
|
LC_AddrSHA384(addr, length) => LC_CalcAddrHash(addr, length, 0x800D)
|
||
|
|
|
||
|
|
LC_SHA512(string, encoding := "UTF-8") => LC_CalcStringHash(string, 0x800E, encoding)
|
||
|
|
LC_HexSHA512(hexstring) => LC_CalcHexHash(hexstring, 0x800E)
|
||
|
|
LC_FileSHA512(filename) => LC_CalcFileHash(filename, 0x800E, 64*1024)
|
||
|
|
LC_AddrSHA512(addr, length) => LC_CalcAddrHash(addr, length, 0x800E)
|
||
|
|
|
||
|
|
; ==============================================================================
|
||
|
|
; CRC32
|
||
|
|
; ==============================================================================
|
||
|
|
|
||
|
|
LC_CRC32(string, encoding := "UTF-8") {
|
||
|
|
chrlength := (encoding = "CP1200" || encoding = "UTF-16") ? 2 : 1
|
||
|
|
length := (StrPut(string, encoding) - 1) * chrlength
|
||
|
|
data := Buffer(length, 0)
|
||
|
|
StrPut(string, data, length // chrlength, encoding)
|
||
|
|
hMod := DllCall("Kernel32\LoadLibraryW", "str", "Ntdll.dll")
|
||
|
|
CRC32 := DllCall("Ntdll\RtlComputeCrc32", "uint", 0, "ptr", data, "uint", length, "uint")
|
||
|
|
CRC := Format("{:08X}", CRC32)
|
||
|
|
DllCall("User32\CharLowerW", "str", CRC)
|
||
|
|
DllCall("Kernel32\FreeLibrary", "ptr", hMod)
|
||
|
|
return CRC
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_HexCRC32(hexstring) {
|
||
|
|
length := StrLen(hexstring) // 2
|
||
|
|
data := Buffer(length, 0)
|
||
|
|
Loop length
|
||
|
|
NumPut("UChar", Integer("0x" SubStr(hexstring, 2 * A_Index - 1, 2)), data, A_Index - 1)
|
||
|
|
hMod := DllCall("Kernel32\LoadLibraryW", "str", "Ntdll.dll")
|
||
|
|
CRC32 := DllCall("Ntdll\RtlComputeCrc32", "uint", 0, "ptr", data, "uint", length, "uint")
|
||
|
|
CRC := Format("{:08X}", CRC32)
|
||
|
|
DllCall("User32\CharLowerW", "str", CRC)
|
||
|
|
DllCall("Kernel32\FreeLibrary", "ptr", hMod)
|
||
|
|
return CRC
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_FileCRC32(sFile := "", cSz := 4) {
|
||
|
|
Bytes := ""
|
||
|
|
cSz := (cSz < 0 || cSz > 8) ? 2**22 : 2**(18 + cSz)
|
||
|
|
BufferObj := Buffer(cSz, 0)
|
||
|
|
hFil := DllCall("Kernel32\CreateFileW", "str", sFile, "uint", 0x80000000, "uint", 3, "int", 0, "uint", 3, "uint", 0, "int", 0, "ptr")
|
||
|
|
if (hFil < 1)
|
||
|
|
return hFil
|
||
|
|
hMod := DllCall("Kernel32\LoadLibraryW", "str", "Ntdll.dll")
|
||
|
|
CRC32 := 0
|
||
|
|
fSz := NumGet(BufferObj, 0, "int64")
|
||
|
|
Loop (fSz // cSz + !!Mod(fSz, cSz)) {
|
||
|
|
DllCall("Kernel32\ReadFile", "ptr", hFil, "ptr", BufferObj, "uint", cSz, "uint*", &Bytes, "uint", 0)
|
||
|
|
CRC32 := DllCall("Ntdll\RtlComputeCrc32", "uint", CRC32, "ptr", BufferObj, "uint", Bytes, "uint")
|
||
|
|
}
|
||
|
|
DllCall("Kernel32\CloseHandle", "ptr", hFil)
|
||
|
|
CRC32 := Format("{:08X}", CRC32)
|
||
|
|
DllCall("User32\CharLowerW", "str", CRC32)
|
||
|
|
DllCall("Kernel32\FreeLibrary", "ptr", hMod)
|
||
|
|
return CRC32
|
||
|
|
}
|
||
|
|
|
||
|
|
; ==============================================================================
|
||
|
|
; HMAC
|
||
|
|
; ==============================================================================
|
||
|
|
|
||
|
|
LC_HMAC(Key, Message, Algo := "MD5") {
|
||
|
|
static Algorithms := {MD2:{ID:0x8001,Size:64}, MD4:{ID:0x8002,Size:64}, MD5:{ID:0x8003,Size:64}, SHA:{ID:0x8004,Size:64}, SHA256:{ID:0x800C,Size:64}, SHA384:{ID:0x800D,Size:128}, SHA512:{ID:0x800E,Size:128}}
|
||
|
|
static iconst := 0x36, oconst := 0x5C
|
||
|
|
if !Algorithms.Has(Algo)
|
||
|
|
return ""
|
||
|
|
AlgID := Algorithms[Algo].ID, BlockSize := Algorithms[Algo].Size
|
||
|
|
MsgLen := StrPut(Message, "UTF-8") - 1
|
||
|
|
KeyLen := StrPut(Key, "UTF-8") - 1
|
||
|
|
K := Buffer(KeyLen + 1, 0)
|
||
|
|
StrPut(Key, K, KeyLen, "UTF-8")
|
||
|
|
KeyHash := KeyHashLen := ""
|
||
|
|
if (KeyLen > BlockSize)
|
||
|
|
LC_CalcAddrHash(K, KeyLen, AlgID, &KeyHash, &KeyHashLen)
|
||
|
|
ipad := Buffer(BlockSize + MsgLen, iconst)
|
||
|
|
Addr := KeyLen > BlockSize ? KeyHash : K
|
||
|
|
Length := KeyLen > BlockSize ? KeyHashLen : KeyLen
|
||
|
|
i := 0
|
||
|
|
while (i < Length) {
|
||
|
|
NumPut(NumGet(Addr, i, "UChar") ^ iconst, ipad, i, "UChar")
|
||
|
|
i++
|
||
|
|
}
|
||
|
|
if (MsgLen)
|
||
|
|
StrPut(Message, Buffer(ipad.Ptr + BlockSize, MsgLen), MsgLen, "UTF-8")
|
||
|
|
InnerHash := InnerHashLen := ""
|
||
|
|
LC_CalcAddrHash(ipad, BlockSize + MsgLen, AlgID, &InnerHash, &InnerHashLen)
|
||
|
|
opad := Buffer(BlockSize + InnerHashLen, oconst)
|
||
|
|
Addr := KeyLen > BlockSize ? KeyHash : K
|
||
|
|
Length := KeyLen > BlockSize ? KeyHashLen : KeyLen
|
||
|
|
i := 0
|
||
|
|
while (i < Length) {
|
||
|
|
NumPut(NumGet(Addr, i, "UChar") ^ oconst, opad, i, "UChar")
|
||
|
|
i++
|
||
|
|
}
|
||
|
|
i := 0
|
||
|
|
while (i < InnerHashLen) {
|
||
|
|
NumPut(NumGet(InnerHash, i, "UChar"), Buffer(opad.Ptr + BlockSize + i, 1), 0, "UChar")
|
||
|
|
i++
|
||
|
|
}
|
||
|
|
return LC_CalcAddrHash(opad, BlockSize + InnerHashLen, AlgID)
|
||
|
|
}
|
||
|
|
|
||
|
|
; ==============================================================================
|
||
|
|
; L64 / L128 Hash (Laszlo)
|
||
|
|
; ==============================================================================
|
||
|
|
|
||
|
|
__LC_LHashTable := []
|
||
|
|
|
||
|
|
LC_L64Hash(x) {
|
||
|
|
global __LC_LHashTable
|
||
|
|
if __LC_LHashTable.Length = 0
|
||
|
|
__LC_LHash_LHashInit()
|
||
|
|
R := 0
|
||
|
|
for ch in StrSplit(x) {
|
||
|
|
i := (R >> 56) & 255
|
||
|
|
R := ((R << 8) + Ord(ch)) ^ __LC_LHashTable[i + 1]
|
||
|
|
}
|
||
|
|
return __LC_LHash_Hex8(R >> 32) . __LC_LHash_Hex8(R)
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_L128Hash(x) {
|
||
|
|
global __LC_LHashTable
|
||
|
|
if __LC_LHashTable.Length = 0
|
||
|
|
__LC_LHash_LHashInit()
|
||
|
|
S := 0, R := -1
|
||
|
|
for ch in StrSplit(x) {
|
||
|
|
i := (R >> 56) & 255
|
||
|
|
R := ((R << 8) + Ord(ch)) ^ __LC_LHashTable[i + 1]
|
||
|
|
i := (S >> 56) & 255
|
||
|
|
S := ((S << 8) + Ord(ch)) - __LC_LHashTable[i + 1]
|
||
|
|
}
|
||
|
|
return __LC_LHash_Hex8(R >> 32) . __LC_LHash_Hex8(R) . __LC_LHash_Hex8(S >> 32) . __LC_LHash_Hex8(S)
|
||
|
|
}
|
||
|
|
|
||
|
|
__LC_LHash_Hex8(i) {
|
||
|
|
i := 0x100000000 | (i & 0xFFFFFFFF)
|
||
|
|
return SubStr(i, -7)
|
||
|
|
}
|
||
|
|
|
||
|
|
__LC_LHash_LHashInit() {
|
||
|
|
global __LC_LHashTable
|
||
|
|
u := 0, v := 0
|
||
|
|
Loop 256 {
|
||
|
|
i := A_Index - 1
|
||
|
|
__LC_LHASH_TEA(&u, &v, 1, 22, 333, 4444, 8)
|
||
|
|
__LC_LHashTable.Push((u << 32) | v)
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
__LC_LHASH_TEA(&y, &z, k0, k1, k2, k3, n := 32) {
|
||
|
|
s := 0, d := 0x9E3779B9
|
||
|
|
Loop n {
|
||
|
|
k := [k0,k1,k2,k3][Mod(s, 4) + 1]
|
||
|
|
y := 0xFFFFFFFF & (y + (((z << 4) ^ (z >> 5)) + z ^ s + k))
|
||
|
|
s := 0xFFFFFFFF & (s + d)
|
||
|
|
k := [k0,k1,k2,k3][Mod(s >> 11, 4) + 1]
|
||
|
|
z := 0xFFFFFFFF & (z + (((y << 4) ^ (y >> 5)) + y ^ s + k))
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
; ==============================================================================
|
||
|
|
; nnnik21 encryption
|
||
|
|
; ==============================================================================
|
||
|
|
|
||
|
|
LC_nnnik21_encryptStr(str := "", pass := "") {
|
||
|
|
if !(enclen := (StrPut(str, "UTF-16") * 2))
|
||
|
|
return "Error: Nothing to Encrypt"
|
||
|
|
if !(passlen := StrPut(pass, "UTF-8") - 1)
|
||
|
|
return "Error: No Pass"
|
||
|
|
enclen := Mod(enclen, 4) ? enclen : enclen - 2
|
||
|
|
encbin := Buffer(enclen, 0)
|
||
|
|
StrPut(str, encbin, enclen // 2, "UTF-16")
|
||
|
|
passlen += Mod((4 - Mod(passlen, 4)), 4)
|
||
|
|
passbin := Buffer(passlen, 0)
|
||
|
|
StrPut(pass, passbin, StrLen(pass), "UTF-8")
|
||
|
|
LC_nnnik21_encryptbin(&encbin, encbin.Size, &passbin, passbin.Size)
|
||
|
|
Text := ""
|
||
|
|
LC_Base64_Encode(&Text, &encbin, encbin.Size)
|
||
|
|
return Text
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_nnnik21_decryptStr(str := "", pass := "") {
|
||
|
|
if !(StrPut(str, "UTF-16") * 2)
|
||
|
|
return "Error: Nothing to Decrypt"
|
||
|
|
if !(passlen := StrPut(pass, "UTF-8") - 1)
|
||
|
|
return "Error: No Pass"
|
||
|
|
passlen += Mod((4 - Mod(passlen, 4)), 4)
|
||
|
|
passbin := Buffer(passlen, 0)
|
||
|
|
StrPut(pass, passbin, StrLen(pass), "UTF-8")
|
||
|
|
encbin := Buffer(0)
|
||
|
|
enclen := LC_Base64_Decode(&encbin, str)
|
||
|
|
LC_nnnik21__decryptbin(&encbin, encbin.Size, &passbin, passbin.Size)
|
||
|
|
return StrGet(encbin, encbin.Size, "UTF-16")
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_nnnik21_encryptbin(&pBin1, sBin1, &pBin2, sBin2) {
|
||
|
|
b := 0
|
||
|
|
Loop sBin1 // 4 {
|
||
|
|
a := NumGet(pBin1, sBin1 - A_Index * 4, "UInt")
|
||
|
|
NumPut(a + b, pBin1, sBin1 - A_Index * 4, "UInt")
|
||
|
|
b := (a + b) * a
|
||
|
|
}
|
||
|
|
Loop sBin2 // 4 {
|
||
|
|
c := NumGet(pBin2, (A_Index - 1) * 4, "UInt")
|
||
|
|
b := 0
|
||
|
|
Loop sBin1 // 4 {
|
||
|
|
a := NumGet(pBin1, (A_Index - 1) * 4, "UInt")
|
||
|
|
NumPut((a + b) ^ c, pBin1, (A_Index - 1) * 4, "UInt")
|
||
|
|
b := (a + b) * a
|
||
|
|
}
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_nnnik21__decryptbin(&pBin1, sBin1, &pBin2, sBin2) {
|
||
|
|
Loop sBin2 // 4 {
|
||
|
|
c := NumGet(pBin2, sBin2 - A_Index * 4, "UInt")
|
||
|
|
b := 0
|
||
|
|
Loop sBin1 // 4 {
|
||
|
|
a := NumGet(pBin1, (A_Index - 1) * 4, "UInt")
|
||
|
|
a := (a ^ c) - b
|
||
|
|
NumPut(a, pBin1, (A_Index - 1) * 4, "UInt")
|
||
|
|
b := (a + b) * a
|
||
|
|
}
|
||
|
|
}
|
||
|
|
b := 0
|
||
|
|
Loop sBin1 // 4 {
|
||
|
|
a := NumGet(pBin1, sBin1 - A_Index * 4, "UInt")
|
||
|
|
a := a - b
|
||
|
|
NumPut(a, pBin1, sBin1 - A_Index * 4, "UInt")
|
||
|
|
b := (a + b) * a
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
; ==============================================================================
|
||
|
|
; RC4
|
||
|
|
; ==============================================================================
|
||
|
|
|
||
|
|
LC_RC4_Encrypt(Data, Pass) {
|
||
|
|
b := 0, j := 0, Key := [], sBox := [], Result := ""
|
||
|
|
Loop 256 {
|
||
|
|
a := A_Index - 1
|
||
|
|
Key[a] := Ord(SubStr(Pass, Mod(a, StrLen(Pass)) + 1, 1))
|
||
|
|
sBox[a] := a
|
||
|
|
}
|
||
|
|
Loop 256 {
|
||
|
|
a := A_Index - 1
|
||
|
|
b := (b + sBox[a] + Key[a]) & 255
|
||
|
|
t := sBox[a], sBox[a] := sBox[b], sBox[b] := t
|
||
|
|
}
|
||
|
|
for ch in StrSplit(Data) {
|
||
|
|
i := A_Index & 255
|
||
|
|
j := (sBox[i] + j) & 255
|
||
|
|
k := sBox[(sBox[i] + sBox[j]) & 255]
|
||
|
|
t := sBox[i], sBox[i] := sBox[j], sBox[j] := t
|
||
|
|
Result .= Format("{:02x}", Ord(ch) ^ sBox[k])
|
||
|
|
}
|
||
|
|
return Result
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_RC4_Decrypt(Data, Pass) {
|
||
|
|
b := 0, j := 0, Key := [], sBox := [], Result := ""
|
||
|
|
Loop 256 {
|
||
|
|
a := A_Index - 1
|
||
|
|
Key[a] := Ord(SubStr(Pass, Mod(a, StrLen(Pass)) + 1, 1))
|
||
|
|
sBox[a] := a
|
||
|
|
}
|
||
|
|
Loop 256 {
|
||
|
|
a := A_Index - 1
|
||
|
|
b := (b + sBox[a] + Key[a]) & 255
|
||
|
|
t := sBox[a], sBox[a] := sBox[b], sBox[b] := t
|
||
|
|
}
|
||
|
|
Loop StrLen(Data) // 2 {
|
||
|
|
i := A_Index & 255
|
||
|
|
j := (sBox[i] + j) & 255
|
||
|
|
k := sBox[(sBox[i] + sBox[j]) & 255]
|
||
|
|
t := sBox[i], sBox[i] := sBox[j], sBox[j] := t
|
||
|
|
Result .= Chr((Integer("0x" SubStr(Data, (2 * A_Index) - 1, 2))) ^ sBox[k])
|
||
|
|
}
|
||
|
|
return Result
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_RC4(RC4Data, RC4Pass) {
|
||
|
|
RC4PassLen := StrLen(RC4Pass), Key := [], sBox := [], b := 0, RC4Result := "", i := 0, j := 0
|
||
|
|
Loop 256 {
|
||
|
|
a := A_Index - 1
|
||
|
|
ModVal := Mod(a, RC4PassLen) + 1
|
||
|
|
c := SubStr(RC4Pass, ModVal, 1)
|
||
|
|
Key[a] := Ord(c), sBox[a] := a
|
||
|
|
}
|
||
|
|
Loop 256 {
|
||
|
|
a := A_Index - 1
|
||
|
|
b := Mod(b + sBox[a] + Key[a], 256)
|
||
|
|
T := sBox[a], sBox[a] := sBox[b], sBox[b] := T
|
||
|
|
}
|
||
|
|
for ch in StrSplit(RC4Data) {
|
||
|
|
i := Mod(i + 1, 256)
|
||
|
|
j := Mod(sBox[i] + j, 256)
|
||
|
|
k := sBox[Mod(sBox[i] + sBox[j], 256)]
|
||
|
|
c := Ord(ch) ^ k
|
||
|
|
c := (c = 0) ? k : c
|
||
|
|
RC4Result .= Chr(c)
|
||
|
|
}
|
||
|
|
return RC4Result
|
||
|
|
}
|
||
|
|
|
||
|
|
; ==============================================================================
|
||
|
|
; RSHash / SecureSalted
|
||
|
|
; ==============================================================================
|
||
|
|
|
||
|
|
LC_RSHash(str) {
|
||
|
|
a := 0xF8C9, b := 0x5C6B7, h := 0
|
||
|
|
for ch in StrSplit(str) {
|
||
|
|
h := h * a + Ord(ch)
|
||
|
|
a *= b
|
||
|
|
}
|
||
|
|
return h & 0x7FFFFFFF
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_SecureSalted(salt, message, algo := "md5") {
|
||
|
|
hash := ""
|
||
|
|
funcName := "LC_" algo
|
||
|
|
saltedHash := %funcName%(message . salt)
|
||
|
|
saltedHashR := %funcName%(salt . message)
|
||
|
|
len := StrLen(saltedHash)
|
||
|
|
Loop len // 2 {
|
||
|
|
byte1 := "0x" SubStr(saltedHash, 2 * A_Index - 1, 2)
|
||
|
|
byte2 := "0x" SubStr(saltedHashR, 2 * A_Index - 1, 2)
|
||
|
|
ns := SubStr(byte1 ^ byte2, 3)
|
||
|
|
hash .= (StrLen(ns) < 2 ? "0" ns : ns)
|
||
|
|
}
|
||
|
|
return hash
|
||
|
|
}
|
||
|
|
|
||
|
|
; ==============================================================================
|
||
|
|
; VxE 89 / 251
|
||
|
|
; ==============================================================================
|
||
|
|
|
||
|
|
LC_VxE_Encrypt89(key, &message) {
|
||
|
|
return LC_VxE_Crypt(key, &message, 1, "vxe89 len " StrLen(message))
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_VxE_Decrypt89(key, &message) {
|
||
|
|
return LC_VxE_Crypt(key, &message, 0, "vxe89 len " StrLen(message))
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_VxE_Encrypt251(key, &message, len) {
|
||
|
|
return LC_VxE_Crypt(key, &message, 1, "len " len)
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_VxE_Decrypt251(key, &message, len) {
|
||
|
|
return LC_VxE_Crypt(key, &message, 0, "len " len)
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_VxE_Crypt(key, &message, direction := 1, options := "") {
|
||
|
|
length := ""
|
||
|
|
if RegExMatch(options, "i)(?:len|l)\K(?:0x[\da-fA-F]+|\d+)", &m)
|
||
|
|
length := Integer(m[0])
|
||
|
|
if length = ""
|
||
|
|
length := StrLen(message)
|
||
|
|
UseVxE89 := InStr(options, "vxe89")
|
||
|
|
direction := 2 * (direction = 1) - 1
|
||
|
|
w := StrLen(key)
|
||
|
|
map := ""
|
||
|
|
if UseVxE89 {
|
||
|
|
Loop 126
|
||
|
|
if (A_Index >= 32 && A_Index != 34 && A_Index != 39 && A_Index != 44 && A_Index != 47 && A_Index != 92 && A_Index != 96)
|
||
|
|
map .= Chr(A_Index)
|
||
|
|
} else {
|
||
|
|
Loop 255
|
||
|
|
if (A_Index != 9 && A_Index != 10 && A_Index != 13 && A_Index != 127)
|
||
|
|
map .= Chr(A_Index)
|
||
|
|
}
|
||
|
|
k := StrLen(map)
|
||
|
|
Loop 9
|
||
|
|
if StrLen(key) < 509
|
||
|
|
key := SubStr(key Chr(48 + A_Index) key, 1, 509)
|
||
|
|
Loop 509 {
|
||
|
|
q := NumGet(StrPtr(key) + A_Index - 1, "UChar")
|
||
|
|
pos := 1 + Mod(q * A_Index * 3, k)
|
||
|
|
e := SubStr(map, pos, 1)
|
||
|
|
i := SubStr(map, 1, pos - 1)
|
||
|
|
c := SubStr(map, pos + 1)
|
||
|
|
map := i c e
|
||
|
|
w ^= q * A_Index * 1657
|
||
|
|
}
|
||
|
|
x := 0
|
||
|
|
Loop length {
|
||
|
|
c := NumGet(message, A_Index - 1, "UChar")
|
||
|
|
if !c || !(i := InStr(map, Chr(c), 1))
|
||
|
|
Continue
|
||
|
|
i--
|
||
|
|
x++
|
||
|
|
e := Mod(223390000 + i + w * direction, k)
|
||
|
|
c := Ord(SubStr(map, e + 1, 1))
|
||
|
|
NumPut(c, message, A_Index - 1, "UChar")
|
||
|
|
if (direction = 1)
|
||
|
|
c := Mod(e + x, 251)
|
||
|
|
else
|
||
|
|
c := Mod(i + x, 251)
|
||
|
|
w ^= c | c << 8 | c << 16 | c << 24
|
||
|
|
}
|
||
|
|
return length
|
||
|
|
}
|
||
|
|
|
||
|
|
; ==============================================================================
|
||
|
|
; XOR
|
||
|
|
; ==============================================================================
|
||
|
|
|
||
|
|
LC_XOR_Encrypt(str, key) {
|
||
|
|
EncLen := StrPut(str, "UTF-16") * 2
|
||
|
|
EncData := Buffer(EncLen, 0)
|
||
|
|
StrPut(str, EncData, EncLen // 2, "UTF-16")
|
||
|
|
PassLen := StrPut(key, "UTF-8") - 1
|
||
|
|
PassData := Buffer(PassLen, 0)
|
||
|
|
StrPut(key, PassData, StrLen(key), "UTF-8")
|
||
|
|
OutData := Buffer(0)
|
||
|
|
LC_XOR(&OutData, &EncData, EncLen, &PassData, PassLen)
|
||
|
|
OutBase64 := ""
|
||
|
|
LC_Base64_Encode(&OutBase64, &OutData, OutData.Size)
|
||
|
|
return OutBase64
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_XOR_Decrypt(OutBase64, key) {
|
||
|
|
OutData := Buffer(0)
|
||
|
|
EncLen := LC_Base64_Decode(&OutData, OutBase64)
|
||
|
|
PassLen := StrPut(key, "UTF-8") - 1
|
||
|
|
PassData := Buffer(PassLen, 0)
|
||
|
|
StrPut(key, PassData, StrLen(key), "UTF-8")
|
||
|
|
EncData := Buffer(0)
|
||
|
|
LC_XOR(&EncData, &OutData, EncLen, &PassData, PassLen)
|
||
|
|
return StrGet(EncData, EncData.Size, "UTF-16")
|
||
|
|
}
|
||
|
|
|
||
|
|
LC_XOR(&OutData, &EncData, EncLen, &PassData, PassLen) {
|
||
|
|
OutData := Buffer(EncLen, 0)
|
||
|
|
Loop EncLen
|
||
|
|
NumPut(NumGet(EncData, A_Index - 1, "UChar") ^ NumGet(PassData, Mod(A_Index - 1, PassLen), "UChar"), OutData, A_Index - 1, "UChar")
|
||
|
|
}
|
||
|
|
|
||
|
|
; ==============================================================================
|
||
|
|
; soupRot class
|
||
|
|
; ==============================================================================
|
||
|
|
|
||
|
|
class LC_soupRot {
|
||
|
|
enc(str, mult, junk := 0) {
|
||
|
|
str := LC_Base64_EncodeText(str)
|
||
|
|
rotBase := StrLen(str) * mult
|
||
|
|
nStr := ""
|
||
|
|
i := 0
|
||
|
|
for a in StrSplit(str) {
|
||
|
|
i++
|
||
|
|
rot := Mod(rotBase * i, 94)
|
||
|
|
nC := Ord(a) + rot
|
||
|
|
while (nC > 126 || nC < 32) {
|
||
|
|
if (nC > 126)
|
||
|
|
nC -= 94
|
||
|
|
else if (nC < 32)
|
||
|
|
nC += 94
|
||
|
|
}
|
||
|
|
nStr .= Chr(nC)
|
||
|
|
if (junk)
|
||
|
|
nStr .= this._randStr(junk, junk, 1234)
|
||
|
|
}
|
||
|
|
return nStr
|
||
|
|
}
|
||
|
|
dec(str, mult, junk := 0) {
|
||
|
|
i := 0, rotBase := StrLen(str) * mult // (junk + 1), nStr := "", skip := 0
|
||
|
|
for a in StrSplit(str) {
|
||
|
|
if (skip) {
|
||
|
|
skip--
|
||
|
|
continue
|
||
|
|
}
|
||
|
|
i++
|
||
|
|
rot := Mod(rotBase * i, 94)
|
||
|
|
nC := Ord(a) - rot
|
||
|
|
while (nC > 126 || nC < 32) {
|
||
|
|
if (nC > 126)
|
||
|
|
nC -= 94
|
||
|
|
else if (nC < 32)
|
||
|
|
nC += 94
|
||
|
|
}
|
||
|
|
nStr .= Chr(nC)
|
||
|
|
if (junk)
|
||
|
|
skip := junk
|
||
|
|
}
|
||
|
|
return RTrim(LC_Base64_DecodeText(nStr), Chr(65533))
|
||
|
|
}
|
||
|
|
_randStr(lowerBound, upperBound, mode := 1) {
|
||
|
|
if (!this._isDigit(lowerBound) || !this._isDigit(upperBound) || !this._isDigit(mode))
|
||
|
|
return -1
|
||
|
|
str := ""
|
||
|
|
Loop this._rand(lowerBound, upperBound) {
|
||
|
|
t := ""
|
||
|
|
if (StrLen(mode) = 1)
|
||
|
|
t := mode
|
||
|
|
else {
|
||
|
|
while (!this._ifContains(mode, t))
|
||
|
|
t := this._rand(1, 4)
|
||
|
|
}
|
||
|
|
if (t = 1)
|
||
|
|
str .= Chr(this._rand(97, 122))
|
||
|
|
else if (t = 2)
|
||
|
|
str .= Chr(this._rand(65, 90))
|
||
|
|
else if (t = 3)
|
||
|
|
str .= this._rand(0, 9)
|
||
|
|
else if (t = 4) {
|
||
|
|
i := this._rand(1, 4)
|
||
|
|
str .= i = 1 ? Chr(this._rand(33, 47)) : i = 2 ? Chr(this._rand(58, 64)) : i = 3 ? Chr(this._rand(91, 96)) : Chr(this._rand(123, 126))
|
||
|
|
}
|
||
|
|
}
|
||
|
|
return str
|
||
|
|
}
|
||
|
|
_rand(lowerBound, upperBound) {
|
||
|
|
return Random(lowerBound, upperBound)
|
||
|
|
}
|
||
|
|
_ifContains(haystack, needle) {
|
||
|
|
return InStr(haystack, needle) != 0
|
||
|
|
}
|
||
|
|
_isDigit(innum) {
|
||
|
|
return InStr("0123456789", innum) != 0
|
||
|
|
}
|
||
|
|
}
|