From b7bcfaaa1b7a349acb2d055a2a35a345154f7751 Mon Sep 17 00:00:00 2001 From: Abhishek Chadha Date: Thu, 9 May 2019 22:44:37 -0700 Subject: [PATCH] scaffold --- core/vm/contracts.go | 19 +++++++++++ crypto/ed25519/ed25519.go | 62 +++++++++++++++++++++++++++++++++++ crypto/ed25519/ed2551_test.go | 7 ++++ params/protocol_params.go | 1 + 4 files changed, 89 insertions(+) create mode 100644 crypto/ed25519/ed25519.go create mode 100644 crypto/ed25519/ed2551_test.go diff --git a/core/vm/contracts.go b/core/vm/contracts.go index 20b741f8f1..0396a1d5ba 100644 --- a/core/vm/contracts.go +++ b/core/vm/contracts.go @@ -44,6 +44,7 @@ var PrecompiledContractsHomestead = map[common.Address]PrecompiledContract{ common.BytesToAddress([]byte{2}): &sha256hash{}, common.BytesToAddress([]byte{3}): &ripemd160hash{}, common.BytesToAddress([]byte{4}): &dataCopy{}, + common.BytesToAddress([]byte{5}): &ecrecovered25519{}, } // PrecompiledContractsByzantium contains the default set of pre-compiled Ethereum @@ -101,6 +102,24 @@ func (c *ecrecover) Run(input []byte) ([]byte, error) { return common.LeftPadBytes(crypto.Keccak256(pubKey[1:])[12:], 32), nil } +// ECRECOVER_EDDSA implemented as a native contract for Web Authentication support +type ecrecovered25519 struct{} + +func (c *ecrecovered25519) RequiredGas(input []byte) uint64 { + return params.EcrecoverEd25519Gas +} + +func (c *ecrecovered25519) Run(input []byte) ([]byte, error) { + /** + TODO: Read these real good and write this code proper + https://godoc.org/golang.org/x/crypto/ed25519 + https://ed25519.cr.yp.to/ + + **/ + var pubKey []byte + return pubKey, nil +} + // SHA256 implemented as a native contract. type sha256hash struct{} diff --git a/crypto/ed25519/ed25519.go b/crypto/ed25519/ed25519.go new file mode 100644 index 0000000000..f27870de45 --- /dev/null +++ b/crypto/ed25519/ed25519.go @@ -0,0 +1,62 @@ +package ed25519 + +import ( + "errors" + "math/big" +) + +func init() { +} + +var ( + ErrInvalidMsgLen = errors.New("invalid message length, need 32 bytes") + ErrInvalidSignatureLen = errors.New("invalid signature length") + ErrInvalidRecoveryID = errors.New("invalid signature recovery id") + ErrInvalidKey = errors.New("invalid private key") + ErrInvalidPubkey = errors.New("invalid public key") + ErrSignFailed = errors.New("signing failed") + ErrRecoverFailed = errors.New("recovery failed") +) + +// Sign creates a recoverable ed25519 signature. +// The produced signature is in the 65-byte [R || S || V] format where V is 0 or 1. +// +// The caller is responsible for ensuring that msg cannot be chosen +// directly by an attacker. It is usually preferable to use a cryptographic +// hash function on any input before handing it to this function. +func Sign(msg []byte, seckey []byte) ([]byte, error) { + // Lets just use golang.org/x/crypto/ed25519 ?? + var sig []byte + return sig, nil +} + +// RecoverPubkey returns the public key of the signer. +// msg must be the 32-byte hash of the message to be signed. +// sig must be a 65-byte compact ECDSA signature containing the +// recovery id as the last element. +func RecoverPubkey(msg []byte, sig []byte) ([]byte, error) { + var pubkey []byte + return pubkey, nil +} + +// VerifySignature checks that the given pubkey created signature over message. +// The signature should be in [R || S] format. +func VerifySignature(pubkey, msg, signature []byte) bool { + return false +} + +func checkSignature(sig []byte) error { + return nil +} + +// DecompressPubkey parses a public key in the 33-byte compressed format. +// It returns non-nil coordinates if the public key is valid. +func DecompressPubkey(pubkey []byte) (x, y *big.Int) { + return nil, nil +} + +// CompressPubkey encodes a public key to 33-byte compressed format. +func CompressPubkey(x, y *big.Int) []byte { + var compressedKey []byte + return compressedKey +} diff --git a/crypto/ed25519/ed2551_test.go b/crypto/ed25519/ed2551_test.go new file mode 100644 index 0000000000..8ab020ce3b --- /dev/null +++ b/crypto/ed25519/ed2551_test.go @@ -0,0 +1,7 @@ +package ed25519 + +import "testing" + +func TestSignatureValidity(t *testing.T) { + t.Error("Unimplemented") +} diff --git a/params/protocol_params.go b/params/protocol_params.go index 14750f6a1a..a0552224c3 100644 --- a/params/protocol_params.go +++ b/params/protocol_params.go @@ -74,6 +74,7 @@ const ( // Precompiled contract gas prices EcrecoverGas uint64 = 3000 // Elliptic curve sender recovery gas price + EcrecoverEd25519Gas uint64 = 3000 // Ed25519Gas Elliptic curve (not sender) recovery gas price - TODO: decide this value Sha256BaseGas uint64 = 60 // Base price for a SHA256 operation Sha256PerWordGas uint64 = 12 // Per-word price for a SHA256 operation Ripemd160BaseGas uint64 = 600 // Base price for a RIPEMD160 operation