package passwd import ( "fmt" "github.com/openwall/yescrypt-go" ) type SCrypt struct { Passwd } // Make an MD5Crypt password instance. func NewSCryptPasswd() PasswdInterface { m := new(SCrypt) m.Magic = S_CRYPT_MAGIC m.SetSCryptParams(14, 32, 1) m.SaltLength = 22 // Set the interface to allow parents to call overriden functions. m.i = m return m } // Sets the SCrypt params using integers. func (a *SCrypt) SetSCryptParams(N, r, p int) (err error) { var b64 []byte b64 = append(b64, iota64Encoding[N]) b64 = append(b64, Base64Uint32Encode(uint32(r), 30)...) b64 = append(b64, Base64Uint32Encode(uint32(p), 30)...) a.Params = string(b64) return } // Decode SCrypt params. func (a *SCrypt) DecodeSCriptParams() (N, r, p int) { b64 := []byte(a.Params) if len(b64) != 11 { return } N = AToI64(b64[0]) r = int(Base64Uint32Decode(b64[1:6], 30)) p = int(Base64Uint32Decode(b64[6:11], 30)) return } // Hash a password with salt using scrypt standard. func (a *SCrypt) Hash(password []byte, salt []byte) (hash []byte, err error) { N, r, p := a.DecodeSCriptParams() scryptHash, err := yescrypt.ScryptKey(password, salt, 1<