mirror of
https://github.com/XTLS/REALITY.git
synced 2025-08-22 22:48:36 +00:00
The new implementation encodes the key schedule into the type system, which is actually nicer than what we had before. For #69536 Change-Id: Iddab62c2aae40bc2425a155443576bb9b7aafe03 Reviewed-on: https://go-review.googlesource.com/c/go/+/626836 Reviewed-by: Russ Cox <rsc@golang.org> Reviewed-by: Roland Shoemaker <roland@golang.org> Commit-Queue: Roland Shoemaker <roland@golang.org> LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com> Auto-Submit: Filippo Valsorda <filippo@golang.org> Reviewed-by: Daniel McCarney <daniel@binaryparadox.net>
56 lines
1.3 KiB
Go
56 lines
1.3 KiB
Go
// Copyright 2024 The Go Authors. All rights reserved.
|
|
// Use of this source code is governed by a BSD-style
|
|
// license that can be found in the LICENSE file.
|
|
|
|
package hkdf
|
|
|
|
import (
|
|
"github.com/xtls/reality/fips140"
|
|
"github.com/xtls/reality/hmac"
|
|
)
|
|
|
|
func Extract[H fips140.Hash](h func() H, secret, salt []byte) []byte {
|
|
if len(secret) < 112/8 {
|
|
// fips140.RecordNonApproved()
|
|
}
|
|
if salt == nil {
|
|
salt = make([]byte, h().Size())
|
|
}
|
|
extractor := hmac.New(h, salt)
|
|
hmac.MarkAsUsedInKDF(extractor)
|
|
extractor.Write(secret)
|
|
|
|
return extractor.Sum(nil)
|
|
}
|
|
|
|
func Expand[H fips140.Hash](h func() H, pseudorandomKey []byte, info string, keyLen int) []byte {
|
|
out := make([]byte, 0, keyLen)
|
|
expander := hmac.New(h, pseudorandomKey)
|
|
hmac.MarkAsUsedInKDF(expander)
|
|
var counter uint8
|
|
var buf []byte
|
|
|
|
for len(out) < keyLen {
|
|
counter++
|
|
if counter == 0 {
|
|
panic("hkdf: counter overflow")
|
|
}
|
|
if counter > 1 {
|
|
expander.Reset()
|
|
}
|
|
expander.Write(buf)
|
|
expander.Write([]byte(info))
|
|
expander.Write([]byte{counter})
|
|
buf = expander.Sum(buf[:0])
|
|
remain := keyLen - len(out)
|
|
remain = min(remain, len(buf))
|
|
out = append(out, buf[:remain]...)
|
|
}
|
|
|
|
return out
|
|
}
|
|
|
|
func Key[H fips140.Hash](h func() H, secret, salt []byte, info string, keyLen int) []byte {
|
|
prk := Extract(h, secret, salt)
|
|
return Expand(h, prk, info, keyLen)
|
|
} |