// Copyright 2023 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 randimport ()// A ChaCha8 is a ChaCha8-based cryptographically strong// random number generator.typeChaCha8struct { state chacha8rand.State// The last readLen bytes of readBuf are still to be consumed by Read. readBuf [8]byte readLen int// 0 <= readLen <= 8}// NewChaCha8 returns a new ChaCha8 seeded with the given seed.func ( [32]byte) *ChaCha8 { := new(ChaCha8) .state.Init()return}// Seed resets the ChaCha8 to behave the same way as NewChaCha8(seed).func ( *ChaCha8) ( [32]byte) { .state.Init() .readLen = 0 .readBuf = [8]byte{}}// Uint64 returns a uniformly distributed random uint64 value.func ( *ChaCha8) () uint64 {for { , := .state.Next()if {return } .state.Refill() }}// Read reads exactly len(p) bytes into p.// It always returns len(p) and a nil error.//// If calls to Read and Uint64 are interleaved, the order in which bits are// returned by the two is undefined, and Read may return bits generated before// the last call to Uint64.func ( *ChaCha8) ( []byte) ( int, error) {if .readLen > 0 { = copy(, .readBuf[len(.readBuf)-.readLen:]) .readLen -= = [:] }forlen() >= 8 {byteorder.LEPutUint64(, .Uint64()) = [8:] += 8 }iflen() > 0 {byteorder.LEPutUint64(.readBuf[:], .Uint64()) += copy(, .readBuf[:]) .readLen = 8 - len() }return}// UnmarshalBinary implements the [encoding.BinaryUnmarshaler] interface.func ( *ChaCha8) ( []byte) error { , := cutPrefix(, []byte("readbuf:"))if {var []byte , , = readUint8LengthPrefixed()if ! {returnerrors.New("invalid ChaCha8 Read buffer encoding") } .readLen = copy(.readBuf[len(.readBuf)-len():], ) }returnchacha8rand.Unmarshal(&.state, )}func cutPrefix(, []byte) ( []byte, bool) {iflen() < len() || string([:len()]) != string() {return , false }return [len():], true}func readUint8LengthPrefixed( []byte) (, []byte, bool) {iflen() == 0 || len() < int(1+[0]) {returnnil, nil, false }return [1 : 1+[0]], [1+[0]:], true}// AppendBinary implements the [encoding.BinaryAppender] interface.func ( *ChaCha8) ( []byte) ([]byte, error) {if .readLen > 0 { = append(, "readbuf:"...) = append(, uint8(.readLen)) = append(, .readBuf[len(.readBuf)-.readLen:]...) }returnappend(, chacha8rand.Marshal(&.state)...), nil}// MarshalBinary implements the [encoding.BinaryMarshaler] interface.func ( *ChaCha8) () ([]byte, error) {// the maximum length of (chacha8rand.Marshal + c.readBuf + "readbuf:") is 64return .AppendBinary(make([]byte, 0, 64))}
The pages are generated with Goldsv0.7.3. (GOOS=linux GOARCH=amd64)
Golds is a Go 101 project developed by Tapir Liu.
PR and bug reports are welcome and can be submitted to the issue list.
Please follow @zigo_101 (reachable from the left QR code) to get the latest news of Golds.