Skip to content

Commit

Permalink
Support to crypto curves (#35)
Browse files Browse the repository at this point in the history
* feat: add support to many curves on go funcs

* feat: add dependabot for gomods

* fix: dependabot config

* fix: remove dependabot changes

* fix: app_test file
  • Loading branch information
emmanuelm41 authored Sep 3, 2024
1 parent 0f19f52 commit bc26c51
Show file tree
Hide file tree
Showing 4 changed files with 65 additions and 44 deletions.
48 changes: 25 additions & 23 deletions app.go
Original file line number Diff line number Diff line change
Expand Up @@ -145,14 +145,13 @@ func (ledger *LedgerFilecoin) GetVersion() (*VersionInfo, error) {

// Deprecated: Use Sign method instead.
func (ledger *LedgerFilecoin) SignSECP256K1(bip44Path []uint32, transaction []byte) (*SignatureAnswer, error) {
return ledger.Sign(bip44Path, transaction)
return ledger.Sign(bip44Path, transaction, SECP256K1)
}


// SignSECP256K1 signs a transaction using Filecoin user app
// Sign signs a transaction using Filecoin user app
// this command requires user confirmation in the device
func (ledger *LedgerFilecoin) Sign(bip44Path []uint32, transaction []byte) (*SignatureAnswer, error) {
signatureBytes, err := ledger.sign(bip44Path, transaction)
func (ledger *LedgerFilecoin) Sign(bip44Path []uint32, transaction []byte, curve CryptoCurve) (*SignatureAnswer, error) {
signatureBytes, err := ledger.sign(bip44Path, transaction, curve)
if err != nil {
return nil, err
}
Expand All @@ -171,43 +170,39 @@ func (ledger *LedgerFilecoin) Sign(bip44Path []uint32, transaction []byte) (*Sig
return &signatureAnswer, nil
}



// Deprecated: Use GetPublicKey instead.
func (ledger *LedgerFilecoin) GetPublicKeySECP256K1(bip44Path []uint32) ([]byte, error) {
pubkey, err := ledger.GetPublicKey(bip44Path)
pubkey, err := ledger.GetPublicKey(bip44Path, SECP256K1)
return pubkey, err
}


// GetPublicKeySECP256K1 retrieves the public key for the corresponding bip44 derivation path
// GetPublicKey retrieves the public key for the corresponding bip44 derivation path
// this command DOES NOT require user confirmation in the device
func (ledger *LedgerFilecoin) GetPublicKey(bip44Path []uint32) ([]byte, error) {
pubkey, _, _, err := ledger.retrieveAddressPubKey(bip44Path, false)
func (ledger *LedgerFilecoin) GetPublicKey(bip44Path []uint32, curve CryptoCurve) ([]byte, error) {
pubkey, _, _, err := ledger.retrieveAddressPubKey(bip44Path, curve, false)
return pubkey, err
}

// Deprecated: Use GetAddressPubKey instead.
func (ledger *LedgerFilecoin) GetAddressPubKeySECP256K1(bip44Path []uint32) (pubkey []byte, addrByte []byte, addrString string, err error) {
return ledger.GetAddressPubKey(bip44Path)
return ledger.GetAddressPubKey(bip44Path, SECP256K1)
}

// GetAddressPubKeySECP256K1 returns the pubkey and addresses
// GetAddressPubKey returns the pubkey and addresses
// this command does not require user confirmation
func (ledger *LedgerFilecoin) GetAddressPubKey(bip44Path []uint32) (pubkey []byte, addrByte []byte, addrString string, err error) {
return ledger.retrieveAddressPubKey(bip44Path, false)
func (ledger *LedgerFilecoin) GetAddressPubKey(bip44Path []uint32, curve CryptoCurve) (pubkey []byte, addrByte []byte, addrString string, err error) {
return ledger.retrieveAddressPubKey(bip44Path, curve, false)
}


// Deprecated: Use ShowAddressPubKey instead.
func (ledger *LedgerFilecoin) ShowAddressPubKeySECP256K1(bip44Path []uint32) (pubkey []byte, addrByte []byte, addrString string, err error) {
return ledger.ShowAddressPubKey(bip44Path)
return ledger.ShowAddressPubKey(bip44Path, SECP256K1)
}

// ShowAddressPubKeySECP256K1 returns the pubkey (compressed) and addresses
// ShowAddressPubKey returns the pubkey (compressed) and addresses
// this command requires user confirmation in the device
func (ledger *LedgerFilecoin) ShowAddressPubKey(bip44Path []uint32) (pubkey []byte, addrByte []byte, addrString string, err error) {
return ledger.retrieveAddressPubKey(bip44Path, true)
func (ledger *LedgerFilecoin) ShowAddressPubKey(bip44Path []uint32, curve CryptoCurve) (pubkey []byte, addrByte []byte, addrString string, err error) {
return ledger.retrieveAddressPubKey(bip44Path, curve, true)
}

func (ledger *LedgerFilecoin) GetBip44bytes(bip44Path []uint32, hardenCount int) ([]byte, error) {
Expand All @@ -219,7 +214,10 @@ func (ledger *LedgerFilecoin) GetBip44bytes(bip44Path []uint32, hardenCount int)
return pathBytes, nil
}

func (ledger *LedgerFilecoin) sign(bip44Path []uint32, transaction []byte) ([]byte, error) {
func (ledger *LedgerFilecoin) sign(bip44Path []uint32, transaction []byte, curve CryptoCurve) ([]byte, error) {
if err := isCryptoCurveSupported(curve); err != nil {
return nil, err
}

pathBytes, err := ledger.GetBip44bytes(bip44Path, HardenCount)
if err != nil {
Expand Down Expand Up @@ -277,7 +275,11 @@ func (ledger *LedgerFilecoin) sign(bip44Path []uint32, transaction []byte) ([]by
}

// retrieveAddressPubKey returns the pubkey and address
func (ledger *LedgerFilecoin) retrieveAddressPubKey(bip44Path []uint32, requireConfirmation bool) (pubkey []byte, addrByte []byte, addrString string, err error) {
func (ledger *LedgerFilecoin) retrieveAddressPubKey(bip44Path []uint32, curve CryptoCurve, requireConfirmation bool) (pubkey []byte, addrByte []byte, addrString string, err error) {
if err := isCryptoCurveSupported(curve); err != nil {
return nil, nil, "", err
}

pathBytes, err := ledger.GetBip44bytes(bip44Path, HardenCount)
if err != nil {
return nil, nil, "", err
Expand Down
26 changes: 13 additions & 13 deletions app_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -66,7 +66,7 @@ func Test_UserGetPublicKey(t *testing.T) {

path := []uint32{44, 461, 5, 0, 21}

pubKey, err := app.GetPublicKey(path)
pubKey, err := app.GetPublicKey(path, SECP256K1)
if err != nil {
t.Fatalf("Detected error, err: %s\n", err.Error())
}
Expand All @@ -90,7 +90,7 @@ func Test_GetAddressPubKeySECP256K1_Zero(t *testing.T) {

path := []uint32{44, 461, 0, 0, 0}

pubKey, addrByte, addrString, err := app.GetAddressPubKey(path)
pubKey, addrByte, addrString, err := app.GetAddressPubKey(path, SECP256K1)
if err != nil {
t.Fatalf("Detected error, err: %s\n", err.Error())
}
Expand All @@ -116,7 +116,7 @@ func Test_GetAddressPubKeySECP256K1(t *testing.T) {

path := []uint32{44, 461, 5, 0, 21}

pubKey, addrByte, addrString, err := app.GetAddressPubKey(path)
pubKey, addrByte, addrString, err := app.GetAddressPubKey(path, SECP256K1)
if err != nil {
t.Fatalf("Detected error, err: %s\n", err.Error())
}
Expand All @@ -142,7 +142,7 @@ func Test_ShowAddressPubKeySECP256K1(t *testing.T) {

path := []uint32{44, 461, 5, 0, 21}

pubKey, addrByte, addrString, err := app.ShowAddressPubKey(path)
pubKey, addrByte, addrString, err := app.ShowAddressPubKey(path, SECP256K1)
if err != nil {
t.Fatalf("Detected error, err: %s\n", err.Error())
}
Expand Down Expand Up @@ -185,7 +185,7 @@ func Test_UserPK_HDPaths(t *testing.T) {
for i := uint32(0); i < 10; i++ {
path[4] = i

pubKey, err := app.GetPublicKey(path)
pubKey, err := app.GetPublicKey(path, SECP256K1)
if err != nil {
t.Fatalf("Detected error, err: %s\n", err.Error())
}
Expand Down Expand Up @@ -214,13 +214,13 @@ func Test_Sign(t *testing.T) {

message, _ := hex.DecodeString("8a0058310396a1a3e4ea7a14d49985e661b22401d44fed402d1d0925b243c923589c0fbc7e32cd04e29ed78d15d37d3aaa3fe6da3358310386b454258c589475f7d16f5aac018a79f6c1169d20fc33921dd8b5ce1cac6c348f90a3603624f6aeb91b64518c2e80950144000186a01961a8430009c44200000040")

signature, err := app.Sign(path, message)
signature, err := app.Sign(path, message, SECP256K1)
if err != nil {
t.Fatalf("[Sign] Error: %s\n", err.Error())
}

// Verify Signature
pubKey, err := app.GetPublicKey(path)
pubKey, err := app.GetPublicKey(path, SECP256K1)
if err != nil {
t.Fatalf("Detected error, err: %s\n", err.Error())
}
Expand Down Expand Up @@ -261,13 +261,13 @@ func Test_Sign2(t *testing.T) {

message, _ := hex.DecodeString("8a0055019f4c34943e4b92f4542bed08af54be955629fc6f5501ef8fd1e48a1e0f1a49310ec675bc677a3954147400430003e81903e84200014200010040")

signature, err := app.Sign(path, message)
signature, err := app.Sign(path, message, SECP256K1)
if err != nil {
t.Fatalf("[Sign] Error: %s\n", err.Error())
}

// Verify Signature
pubKey, err := app.GetPublicKey(path)
pubKey, err := app.GetPublicKey(path, SECP256K1)
if err != nil {
t.Fatalf("Detected error, err: %s\n", err.Error())
}
Expand Down Expand Up @@ -310,13 +310,13 @@ func Test_Sign3(t *testing.T) {

message, _ := hex.DecodeString("8a0055019f4c34943e4b92f4542bed08af54be955629fc6f5501ef8fd1e48a1e0f1a49310ec675bc677a3954147400430003e81903e84200014200010040")

signature, err := app.Sign(path, message)
signature, err := app.Sign(path, message, SECP256K1)
if err != nil {
t.Fatalf("[Sign] Error: %s\n", err.Error())
}

// Verify Signature
pubKey, err := app.GetPublicKey(path)
pubKey, err := app.GetPublicKey(path, SECP256K1)
if err != nil {
t.Fatalf("Detected error, err: %s\n", err.Error())
}
Expand Down Expand Up @@ -377,7 +377,7 @@ func Test_Sign_Fails(t *testing.T) {
garbage := []byte{65}
message = append(garbage, message...)

_, err = app.Sign(path, message)
_, err = app.Sign(path, message, SECP256K1)
assert.Error(t, err)
errMessage := err.Error()
assert.Equal(t, errMessage, "Unexpected data type")
Expand All @@ -386,7 +386,7 @@ func Test_Sign_Fails(t *testing.T) {
garbage = []byte{65}
message = append(message, garbage...)

_, err = app.Sign(path, message)
_, err = app.Sign(path, message, SECP256K1)
assert.Error(t, err)
errMessage = err.Error()
assert.Equal(t, errMessage, "Unexpected CBOR EOF")
Expand Down
22 changes: 14 additions & 8 deletions types.go
Original file line number Diff line number Diff line change
Expand Up @@ -22,14 +22,14 @@ import (
)

const (
CLA = 0x06
CLA = 0x06

INSGetVersion = 0
INSGetAddr = 1
INSSign = 2
INSSignDataCap = 5
INSSignClientDeal = 6
INSSignRawBytes = 7
INSGetVersion = 0
INSGetAddr = 1
INSSign = 2
INSSignDataCap = 5
INSSignClientDeal = 6
INSSignRawBytes = 7
)

const (
Expand All @@ -40,6 +40,13 @@ const (

const HardenCount int = 2

type CryptoCurve uint64

const (
SECP256K1 CryptoCurve = iota
BLS
)

// LedgerFilecoin represents a connection to the Ledger app
type LedgerFilecoin struct {
api ledger_go.LedgerDevice
Expand All @@ -61,7 +68,6 @@ type VersionInfo struct {
Patch uint8
}


// VersionRequiredError the command is not supported by this app
type VersionRequiredError struct {
Found VersionInfo
Expand Down
13 changes: 13 additions & 0 deletions utils.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
package ledger_filecoin_go

import "fmt"

func isCryptoCurveSupported(curve CryptoCurve) error {
switch curve {
case SECP256K1:
return nil
default:
return fmt.Errorf("curve not supported yet")

}
}

0 comments on commit bc26c51

Please sign in to comment.