1
0
mirror of https://github.com/Luzifer/cloudkeys-go.git synced 2024-09-20 08:02:57 +00:00
cloudkeys-go/vendor/golang.org/x/crypto/chacha20poly1305/chacha20poly1305_amd64.go
Knut Ahlers a1df72edc5
Squashed commit of the following:
commit f0db1ff1f8
Author: Knut Ahlers <knut@ahlers.me>
Date:   Sun Dec 24 12:19:56 2017 +0100

    Mark option as deprecated

    Signed-off-by: Knut Ahlers <knut@ahlers.me>

commit 9891df2a16
Author: Knut Ahlers <knut@ahlers.me>
Date:   Sun Dec 24 12:11:56 2017 +0100

    Fix: Typo

    Signed-off-by: Knut Ahlers <knut@ahlers.me>

commit 836006de64
Author: Knut Ahlers <knut@ahlers.me>
Date:   Sun Dec 24 12:04:20 2017 +0100

    Add new dependencies

    Signed-off-by: Knut Ahlers <knut@ahlers.me>

commit d64fee60c8
Author: Knut Ahlers <knut@ahlers.me>
Date:   Sun Dec 24 11:55:52 2017 +0100

    Replace insecure password hashing

    Prior this commit passwords were hashed with a static salt and using the
    SHA1 hashing function. This could lead to passwords being attackable in
    case someone gets access to the raw data stored inside the database.
    This commit introduces password hashing using bcrypt hashing function
    which addresses this issue.

    Old passwords are not automatically re-hashed as they are unknown.
    Replacing the old password scheme is not that easy and needs #10 to be
    solved. Therefore the old hashing scheme is kept for compatibility
    reason.

    Signed-off-by: Knut Ahlers <knut@ahlers.me>

Signed-off-by: Knut Ahlers <knut@ahlers.me>

closes #14
closes #15
2017-12-24 19:44:24 +01:00

128 lines
3.3 KiB
Go

// 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.
// +build go1.7,amd64,!gccgo,!appengine
package chacha20poly1305
import "encoding/binary"
//go:noescape
func chacha20Poly1305Open(dst []byte, key []uint32, src, ad []byte) bool
//go:noescape
func chacha20Poly1305Seal(dst []byte, key []uint32, src, ad []byte)
// cpuid is implemented in chacha20poly1305_amd64.s.
func cpuid(eaxArg, ecxArg uint32) (eax, ebx, ecx, edx uint32)
// xgetbv with ecx = 0 is implemented in chacha20poly1305_amd64.s.
func xgetbv() (eax, edx uint32)
var (
useASM bool
useAVX2 bool
)
func init() {
detectCPUFeatures()
}
// detectCPUFeatures is used to detect if cpu instructions
// used by the functions implemented in assembler in
// chacha20poly1305_amd64.s are supported.
func detectCPUFeatures() {
maxID, _, _, _ := cpuid(0, 0)
if maxID < 1 {
return
}
_, _, ecx1, _ := cpuid(1, 0)
haveSSSE3 := isSet(9, ecx1)
useASM = haveSSSE3
haveOSXSAVE := isSet(27, ecx1)
osSupportsAVX := false
// For XGETBV, OSXSAVE bit is required and sufficient.
if haveOSXSAVE {
eax, _ := xgetbv()
// Check if XMM and YMM registers have OS support.
osSupportsAVX = isSet(1, eax) && isSet(2, eax)
}
haveAVX := isSet(28, ecx1) && osSupportsAVX
if maxID < 7 {
return
}
_, ebx7, _, _ := cpuid(7, 0)
haveAVX2 := isSet(5, ebx7) && haveAVX
haveBMI2 := isSet(8, ebx7)
useAVX2 = haveAVX2 && haveBMI2
}
// isSet checks if bit at bitpos is set in value.
func isSet(bitpos uint, value uint32) bool {
return value&(1<<bitpos) != 0
}
// setupState writes a ChaCha20 input matrix to state. See
// https://tools.ietf.org/html/rfc7539#section-2.3.
func setupState(state *[16]uint32, key *[32]byte, nonce []byte) {
state[0] = 0x61707865
state[1] = 0x3320646e
state[2] = 0x79622d32
state[3] = 0x6b206574
state[4] = binary.LittleEndian.Uint32(key[:4])
state[5] = binary.LittleEndian.Uint32(key[4:8])
state[6] = binary.LittleEndian.Uint32(key[8:12])
state[7] = binary.LittleEndian.Uint32(key[12:16])
state[8] = binary.LittleEndian.Uint32(key[16:20])
state[9] = binary.LittleEndian.Uint32(key[20:24])
state[10] = binary.LittleEndian.Uint32(key[24:28])
state[11] = binary.LittleEndian.Uint32(key[28:32])
state[12] = 0
state[13] = binary.LittleEndian.Uint32(nonce[:4])
state[14] = binary.LittleEndian.Uint32(nonce[4:8])
state[15] = binary.LittleEndian.Uint32(nonce[8:12])
}
func (c *chacha20poly1305) seal(dst, nonce, plaintext, additionalData []byte) []byte {
if !useASM {
return c.sealGeneric(dst, nonce, plaintext, additionalData)
}
var state [16]uint32
setupState(&state, &c.key, nonce)
ret, out := sliceForAppend(dst, len(plaintext)+16)
chacha20Poly1305Seal(out[:], state[:], plaintext, additionalData)
return ret
}
func (c *chacha20poly1305) open(dst, nonce, ciphertext, additionalData []byte) ([]byte, error) {
if !useASM {
return c.openGeneric(dst, nonce, ciphertext, additionalData)
}
var state [16]uint32
setupState(&state, &c.key, nonce)
ciphertext = ciphertext[:len(ciphertext)-16]
ret, out := sliceForAppend(dst, len(ciphertext))
if !chacha20Poly1305Open(out, state[:], ciphertext, additionalData) {
for i := range out {
out[i] = 0
}
return nil, errOpen
}
return ret, nil
}