37 lines
915 B
Go
37 lines
915 B
Go
|
package entropy
|
||
|
|
||
|
import (
|
||
|
"fmt"
|
||
|
"github.com/hashicorp/errwrap"
|
||
|
)
|
||
|
|
||
|
type Sourcer interface {
|
||
|
GetRandom(bytes int) ([]byte, error)
|
||
|
}
|
||
|
|
||
|
type Reader struct {
|
||
|
source Sourcer
|
||
|
}
|
||
|
|
||
|
func NewReader(source Sourcer) *Reader{
|
||
|
return &Reader{source}
|
||
|
}
|
||
|
|
||
|
// Read reads exactly len(p) bytes from r into p.
|
||
|
// If r returns an error having read at least len(p) bytes, the error is dropped.
|
||
|
// It returns the number of bytes copied and an error if fewer bytes were read.
|
||
|
// On return, n == len(p) if and only if err == nil.
|
||
|
func (r *Reader) Read(p []byte) (n int, err error){
|
||
|
requested := len(p)
|
||
|
randBytes, err := r.source.GetRandom(requested)
|
||
|
delivered := copy(p, randBytes)
|
||
|
if delivered != requested {
|
||
|
if err != nil {
|
||
|
return delivered, errwrap.Wrapf("unable to fill provided buffer with entropy: {{err}}", err)
|
||
|
}
|
||
|
return delivered, fmt.Errorf("unable to fill provided buffer with entropy")
|
||
|
}
|
||
|
|
||
|
return delivered, nil
|
||
|
}
|