]> Cypherpunks repositories - gostls13.git/commitdiff
crypto/rand: use the getentropy syscall on OpenBSD
authorMichael McConville <momcconville@gmail.com>
Sun, 3 Jan 2016 01:50:57 +0000 (20:50 -0500)
committerBrad Fitzpatrick <bradfitz@golang.org>
Fri, 26 Feb 2016 19:58:09 +0000 (19:58 +0000)
Go already supports Linux's getrandom, which is a slightly modified
version of getentropy.

getentropy was added in OpenBSD 5.6. All supported versions of OpenBSD
include it so, unlike with Linux and getrandom, we don't need to test
for its presence.

Fixes #13785.

Change-Id: Ib536b96675f257cd8c5de1e3a36165e15c9abac9
Reviewed-on: https://go-review.googlesource.com/18219
Run-TryBot: Brad Fitzpatrick <bradfitz@golang.org>
TryBot-Result: Gobot Gobot <gobot@golang.org>
Reviewed-by: Brad Fitzpatrick <bradfitz@golang.org>
src/crypto/rand/rand.go
src/crypto/rand/rand_openbsd.go [new file with mode: 0644]
src/internal/syscall/unix/getentropy_openbsd.go [new file with mode: 0644]

index ee32fa0bd67e52cffea909e36d7ba0eeeb1d2056..5e48fc9cd9ba2699ab4944f4dcc09e741af0bcbe 100644 (file)
@@ -11,8 +11,9 @@ import "io"
 // Reader is a global, shared instance of a cryptographically
 // strong pseudo-random generator.
 //
-// On Unix-like systems, Reader reads from /dev/urandom.
 // On Linux, Reader uses getrandom(2) if available, /dev/urandom otherwise.
+// On OpenBSD, Reader uses getentropy(2).
+// On other Unix-like systems, Reader reads from /dev/urandom.
 // On Windows systems, Reader uses the CryptGenRandom API.
 var Reader io.Reader
 
diff --git a/src/crypto/rand/rand_openbsd.go b/src/crypto/rand/rand_openbsd.go
new file mode 100644 (file)
index 0000000..405c091
--- /dev/null
@@ -0,0 +1,28 @@
+// Copyright 2016 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 rand
+
+import (
+       "internal/syscall/unix"
+)
+
+func init() {
+       altGetRandom = getRandomOpenBSD
+}
+
+func getRandomOpenBSD(p []byte) (ok bool) {
+       // getentropy(2) returns a maximum of 256 bytes per call
+       for i := 0; i < len(p); i += 256 {
+               end := i + 256
+               if len(p) < end {
+                       end = len(p)
+               }
+               err := unix.GetEntropy(p[i:end])
+               if err != nil {
+                       return false
+               }
+       }
+       return true
+}
diff --git a/src/internal/syscall/unix/getentropy_openbsd.go b/src/internal/syscall/unix/getentropy_openbsd.go
new file mode 100644 (file)
index 0000000..fd3dabc
--- /dev/null
@@ -0,0 +1,25 @@
+// Copyright 2016 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 unix
+
+import (
+       "syscall"
+       "unsafe"
+)
+
+// getentropy(2)'s syscall number, from /usr/src/sys/kern/syscalls.master
+const entropyTrap uintptr = 7
+
+// GetEntropy calls the OpenBSD getentropy system call.
+func GetEntropy(p []byte) error {
+       _, _, errno := syscall.Syscall(entropyTrap,
+               uintptr(unsafe.Pointer(&p[0])),
+               uintptr(len(p)),
+               0)
+       if errno != 0 {
+               return errno
+       }
+       return nil
+}