54 lines
1.5 KiB
TypeScript
54 lines
1.5 KiB
TypeScript
import { randomBytes, createHash } from 'crypto'
|
|
import bigInt from 'big-integer'
|
|
|
|
export const hex2bin = (s: String) => {
|
|
const ret = []
|
|
for (let i = 0, l = s.length; i < l; i += 2) {
|
|
const c = parseInt(s.substr(i, 1), 16)
|
|
const k = parseInt(s.substr(i + 1, 1), 16)
|
|
if (isNaN(c) || isNaN(k)) return false
|
|
ret.push((c << 4) | k)
|
|
}
|
|
return String.fromCharCode.apply(String, ret)
|
|
}
|
|
|
|
export const bin2hex = (s: String) => {
|
|
let result = ''
|
|
for (let i = 0, l = s.length; i < l; i++) {
|
|
const n = s.charCodeAt(i).toString(16)
|
|
result += n.length < 2 ? '0' + n : n
|
|
}
|
|
return result
|
|
}
|
|
|
|
export const reverseHex = (string: String) => {
|
|
const bytes = []
|
|
for (let i = 0, length = string.length; i < length; i += 2) {
|
|
bytes.push(string.substr(i, 2))
|
|
}
|
|
return bytes.reverse().join('')
|
|
}
|
|
|
|
export const register = (
|
|
username: String,
|
|
password: String,
|
|
gHex = '07',
|
|
NHex = '894B645E89E1535BBDAD5B8B290650530801B18EBFBF5E8FAB3C82872A3E9BB7'
|
|
) => {
|
|
const g = bigInt(gHex, 16)
|
|
const N = bigInt(NHex, 16)
|
|
const saltDB = bin2hex(randomBytes(32).toString('binary'))
|
|
const salt = hex2bin(reverseHex(saltDB))
|
|
const identity = createHash('sha1')
|
|
.update((username + ':' + password).toUpperCase())
|
|
.digest('latin1')
|
|
const sha = reverseHex(
|
|
createHash('sha1')
|
|
.update(salt + identity, 'latin1')
|
|
.digest('hex')
|
|
)
|
|
const privateKey = bigInt(sha, 16)
|
|
const verifier = g.modPow(privateKey, N).toString(16)
|
|
return { salt: saltDB, verifier }
|
|
}
|