!WIP! - Router Info
This commit is contained in:
@@ -38,7 +38,8 @@ type Destination struct {
|
||||
func (destination Destination) Base32Address() (str string) {
|
||||
log.Debug("Generating Base32 address for Destination")
|
||||
|
||||
dest := destination.KeysAndCert.KeyCertificate.Bytes()
|
||||
cert := destination.KeysAndCert.Certificate()
|
||||
dest := cert.Bytes()
|
||||
hash := crypto.SHA256(dest)
|
||||
str = strings.Trim(base32.EncodeToString(hash[:]), "=")
|
||||
str = str + ".b32.i2p"
|
||||
@@ -54,7 +55,8 @@ func (destination Destination) Base32Address() (str string) {
|
||||
func (destination Destination) Base64() string {
|
||||
log.Debug("Generating Base64 address for Destination")
|
||||
|
||||
dest := destination.KeysAndCert.KeyCertificate.Bytes()
|
||||
cert := destination.KeysAndCert.Certificate()
|
||||
dest := cert.Bytes()
|
||||
base64Address := base64.EncodeToString(dest)
|
||||
|
||||
log.WithFields(logrus.Fields{
|
||||
|
@@ -5,7 +5,7 @@ import common "github.com/go-i2p/go-i2p/lib/common/router_identity"
|
||||
func Fuzz(data []byte) int {
|
||||
router_identity, _, _ := common.ReadRouterIdentity(data)
|
||||
router_identity.Certificate()
|
||||
router_identity.PublicKey()
|
||||
router_identity.SigningPublicKey()
|
||||
router_identity.publicKey()
|
||||
router_identity.signingPublicKey()
|
||||
return 0
|
||||
}
|
||||
|
@@ -29,7 +29,6 @@ payload :: data
|
||||
|
||||
import (
|
||||
"errors"
|
||||
|
||||
"github.com/go-i2p/go-i2p/lib/util/logger"
|
||||
"github.com/sirupsen/logrus"
|
||||
|
||||
@@ -66,7 +65,7 @@ const (
|
||||
KEYCERT_MIN_SIZE = 7
|
||||
)
|
||||
|
||||
// SigningPublicKey sizes for Signing Key Types
|
||||
// signingPublicKey sizes for Signing Key Types
|
||||
const (
|
||||
KEYCERT_SIGN_DSA_SHA1_SIZE = 128
|
||||
KEYCERT_SIGN_P256_SIZE = 64
|
||||
@@ -79,7 +78,7 @@ const (
|
||||
KEYCERT_SIGN_ED25519PH_SIZE = 32
|
||||
)
|
||||
|
||||
// PublicKey sizes for Public Key Types
|
||||
// publicKey sizes for Public Key Types
|
||||
const (
|
||||
KEYCERT_CRYPTO_ELG_SIZE = 256
|
||||
KEYCERT_CRYPTO_P256_SIZE = 64
|
||||
@@ -106,34 +105,34 @@ func (key_certificate KeyCertificate) Data() ([]byte, error) {
|
||||
data := key_certificate.Certificate.RawBytes()
|
||||
log.WithFields(logrus.Fields{
|
||||
"data_length": len(data),
|
||||
}).Debug("Retrieved raw data from KeyCertificate")
|
||||
}).Debug("Retrieved raw data from keyCertificate")
|
||||
return key_certificate.Certificate.RawBytes(), nil
|
||||
}
|
||||
|
||||
// SigningPublicKeyType returns the SigningPublicKey type as a Go integer.
|
||||
// SigningPublicKeyType returns the signingPublicKey type as a Go integer.
|
||||
func (key_certificate KeyCertificate) SigningPublicKeyType() (signing_pubkey_type int) {
|
||||
signing_pubkey_type = key_certificate.spkType.Int()
|
||||
log.WithFields(logrus.Fields{
|
||||
"signing_pubkey_type": signing_pubkey_type,
|
||||
}).Debug("Retrieved SigningPublicKey type")
|
||||
}).Debug("Retrieved signingPublicKey type")
|
||||
return key_certificate.spkType.Int()
|
||||
}
|
||||
|
||||
// PublicKeyType returns the PublicKey type as a Go integer.
|
||||
// PublicKeyType returns the publicKey type as a Go integer.
|
||||
func (key_certificate KeyCertificate) PublicKeyType() (pubkey_type int) {
|
||||
pubkey_type = key_certificate.cpkType.Int()
|
||||
log.WithFields(logrus.Fields{
|
||||
"pubkey_type": pubkey_type,
|
||||
}).Debug("Retrieved PublicKey type")
|
||||
}).Debug("Retrieved publicKey type")
|
||||
return key_certificate.cpkType.Int()
|
||||
}
|
||||
|
||||
// ConstructPublicKey returns a PublicKey constructed using any excess data that may be stored in the KeyCertififcate.
|
||||
// ConstructPublicKey returns a publicKey constructed using any excess data that may be stored in the KeyCertififcate.
|
||||
// Returns enr errors encountered while parsing.
|
||||
func (key_certificate KeyCertificate) ConstructPublicKey(data []byte) (public_key crypto.PublicKey, err error) {
|
||||
log.WithFields(logrus.Fields{
|
||||
"input_length": len(data),
|
||||
}).Debug("Constructing PublicKey from KeyCertificate")
|
||||
}).Debug("Constructing publicKey from keyCertificate")
|
||||
key_type := key_certificate.PublicKeyType()
|
||||
if err != nil {
|
||||
return
|
||||
@@ -141,7 +140,7 @@ func (key_certificate KeyCertificate) ConstructPublicKey(data []byte) (public_ke
|
||||
data_len := len(data)
|
||||
if data_len < key_certificate.CryptoSize() {
|
||||
log.WithFields(logrus.Fields{
|
||||
"at": "(KeyCertificate) ConstructPublicKey",
|
||||
"at": "(keyCertificate) ConstructPublicKey",
|
||||
"data_len": data_len,
|
||||
"required_len": KEYCERT_PUBKEY_SIZE,
|
||||
"reason": "not enough data",
|
||||
@@ -174,7 +173,7 @@ func (key_certificate KeyCertificate) ConstructPublicKey(data []byte) (public_ke
|
||||
func (key_certificate KeyCertificate) ConstructSigningPublicKey(data []byte) (signing_public_key crypto.SigningPublicKey, err error) {
|
||||
log.WithFields(logrus.Fields{
|
||||
"input_length": len(data),
|
||||
}).Debug("Constructing SigningPublicKey from KeyCertificate")
|
||||
}).Debug("Constructing signingPublicKey from keyCertificate")
|
||||
signing_key_type := key_certificate.PublicKeyType()
|
||||
if err != nil {
|
||||
return
|
||||
@@ -182,7 +181,7 @@ func (key_certificate KeyCertificate) ConstructSigningPublicKey(data []byte) (si
|
||||
data_len := len(data)
|
||||
if data_len < key_certificate.SignatureSize() {
|
||||
log.WithFields(logrus.Fields{
|
||||
"at": "(KeyCertificate) ConstructSigningPublicKey",
|
||||
"at": "(keyCertificate) ConstructSigningPublicKey",
|
||||
"data_len": data_len,
|
||||
"required_len": KEYCERT_SPK_SIZE,
|
||||
"reason": "not enough data",
|
||||
@@ -247,7 +246,7 @@ func (key_certificate KeyCertificate) ConstructSigningPublicKey(data []byte) (si
|
||||
return
|
||||
}
|
||||
|
||||
// SignatureSize return the size of a Signature corresponding to the Key Certificate's SigningPublicKey type.
|
||||
// SignatureSize return the size of a Signature corresponding to the Key Certificate's signingPublicKey type.
|
||||
func (key_certificate KeyCertificate) SignatureSize() (size int) {
|
||||
sizes := map[int]int{
|
||||
KEYCERT_SIGN_DSA_SHA1: KEYCERT_SIGN_DSA_SHA1_SIZE,
|
||||
@@ -269,7 +268,7 @@ func (key_certificate KeyCertificate) SignatureSize() (size int) {
|
||||
return sizes[int(key_type)]
|
||||
}
|
||||
|
||||
// CryptoSize return the size of a Public Key corresponding to the Key Certificate's PublicKey type.
|
||||
// CryptoSize return the size of a Public Key corresponding to the Key Certificate's publicKey type.
|
||||
func (key_certificate KeyCertificate) CryptoSize() (size int) {
|
||||
sizes := map[int]int{
|
||||
KEYCERT_CRYPTO_ELG: KEYCERT_CRYPTO_ELG_SIZE,
|
||||
@@ -293,7 +292,7 @@ func (key_certificate KeyCertificate) CryptoSize() (size int) {
|
||||
func NewKeyCertificate(bytes []byte) (key_certificate *KeyCertificate, remainder []byte, err error) {
|
||||
log.WithFields(logrus.Fields{
|
||||
"input_length": len(bytes),
|
||||
}).Debug("Creating new KeyCertificate")
|
||||
}).Debug("Creating new keyCertificate")
|
||||
|
||||
var certificate Certificate
|
||||
certificate, remainder, err = ReadCertificate(bytes)
|
||||
@@ -302,9 +301,9 @@ func NewKeyCertificate(bytes []byte) (key_certificate *KeyCertificate, remainder
|
||||
return
|
||||
}
|
||||
if len(bytes) < KEYCERT_MIN_SIZE {
|
||||
log.WithError(err).Error("keyCertificate data too short")
|
||||
err = errors.New("error parsing key certificate: not enough data")
|
||||
remainder = bytes[KEYCERT_MIN_SIZE:]
|
||||
log.WithError(err).Error("KeyCertificate data too short")
|
||||
}
|
||||
key_certificate = &KeyCertificate{
|
||||
Certificate: certificate,
|
||||
@@ -320,20 +319,20 @@ func NewKeyCertificate(bytes []byte) (key_certificate *KeyCertificate, remainder
|
||||
"spk_type": key_certificate.spkType.Int(),
|
||||
"cpk_type": key_certificate.cpkType.Int(),
|
||||
"remainder_length": len(remainder),
|
||||
}).Debug("Successfully created new KeyCertificate")
|
||||
}).Debug("Successfully created new keyCertificate")
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
// KeyCertificateFromCertificate returns a *KeyCertificate from a *Certificate.
|
||||
func KeyCertificateFromCertificate(certificate Certificate) *KeyCertificate {
|
||||
log.Debug("Creating KeyCertificate from Certificate")
|
||||
log.Debug("Creating keyCertificate from Certificate")
|
||||
// k, _, _ := NewKeyCertificate(certificate.RawBytes())
|
||||
k, _, err := NewKeyCertificate(certificate.RawBytes())
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to create KeyCertificate from Certificate")
|
||||
log.WithError(err).Error("Failed to create keyCertificate from Certificate")
|
||||
} else {
|
||||
log.Debug("Successfully created KeyCertificate from Certificate")
|
||||
log.Debug("Successfully created keyCertificate from Certificate")
|
||||
}
|
||||
return k
|
||||
}
|
||||
|
@@ -35,7 +35,7 @@ func TestPublicKeyTypeReturnsCorrectInteger(t *testing.T) {
|
||||
key_cert, _, err := NewKeyCertificate([]byte{0x05, 0x00, 0x04, 0x00, 0x00, 0x00, 0x03})
|
||||
pk_type := key_cert.PublicKeyType()
|
||||
|
||||
assert.Nil(err, "PublicKey() returned error with valid data")
|
||||
assert.Nil(err, "publicKey() returned error with valid data")
|
||||
assert.Equal(pk_type, KEYCERT_SIGN_P521, "PublicKeyType() did not return correct typec")
|
||||
}
|
||||
|
||||
@@ -94,7 +94,7 @@ func TestConstructSigningPublicKeyWithDSASHA1(t *testing.T) {
|
||||
spk, err := key_cert.ConstructSigningPublicKey(data)
|
||||
|
||||
assert.Nil(err, "ConstructSigningPublicKey() with DSA SHA1 returned error with valid data")
|
||||
assert.Equal(spk.Len(), KEYCERT_SIGN_DSA_SHA1_SIZE, "ConstructSigningPublicKey() with DSA SHA1 returned incorrect SigningPublicKey length")
|
||||
assert.Equal(spk.Len(), KEYCERT_SIGN_DSA_SHA1_SIZE, "ConstructSigningPublicKey() with DSA SHA1 returned incorrect signingPublicKey length")
|
||||
}
|
||||
|
||||
func TestConstructSigningPublicKeyWithP256(t *testing.T) {
|
||||
@@ -105,7 +105,7 @@ func TestConstructSigningPublicKeyWithP256(t *testing.T) {
|
||||
spk, err := key_cert.ConstructSigningPublicKey(data)
|
||||
|
||||
assert.Nil(err, "ConstructSigningPublicKey() with P256 returned err on valid data")
|
||||
assert.Equal(spk.Len(), KEYCERT_SIGN_P256_SIZE, "ConstructSigningPublicKey() with P256 returned incorrect SigningPublicKey length")
|
||||
assert.Equal(spk.Len(), KEYCERT_SIGN_P256_SIZE, "ConstructSigningPublicKey() with P256 returned incorrect signingPublicKey length")
|
||||
}
|
||||
|
||||
func TestConstructSigningPublicKeyWithP384(t *testing.T) {
|
||||
@@ -116,7 +116,7 @@ func TestConstructSigningPublicKeyWithP384(t *testing.T) {
|
||||
spk, err := key_cert.ConstructSigningPublicKey(data)
|
||||
|
||||
assert.Nil(err, "ConstructSigningPublicKey() with P384 returned err on valid data")
|
||||
assert.Equal(spk.Len(), KEYCERT_SIGN_P384_SIZE, "ConstructSigningPublicKey() with P384 returned incorrect SigningPublicKey length")
|
||||
assert.Equal(spk.Len(), KEYCERT_SIGN_P384_SIZE, "ConstructSigningPublicKey() with P384 returned incorrect signingPublicKey length")
|
||||
}
|
||||
|
||||
func TestConstructSigningPublicKeyWithP521(t *testing.T) {
|
||||
@@ -127,5 +127,5 @@ func TestConstructSigningPublicKeyWithP521(t *testing.T) {
|
||||
spk, err := key_cert.ConstructSigningPublicKey(data)
|
||||
|
||||
assert.Nil(err, "ConstructSigningPublicKey() with P521 returned err on valid data")
|
||||
assert.Equal(spk.Len(), KEYCERT_SIGN_P521_SIZE, "ConstructSigningPublicKey() with P521 returned incorrect SigningPublicKey length")
|
||||
assert.Equal(spk.Len(), KEYCERT_SIGN_P521_SIZE, "ConstructSigningPublicKey() with P521 returned incorrect signingPublicKey length")
|
||||
}
|
||||
|
@@ -30,7 +30,7 @@ Description
|
||||
An encryption public key, a signing public key, and a certificate, used as either a RouterIdentity or a Destination.
|
||||
|
||||
Contents
|
||||
A PublicKey followed by a SigningPublicKey and then a Certificate.
|
||||
A publicKey followed by a signingPublicKey and then a Certificate.
|
||||
|
||||
+----+----+----+----+----+----+----+----+
|
||||
| public_key |
|
||||
@@ -55,14 +55,14 @@ A PublicKey followed by a SigningPublicKey and then a Certificate.
|
||||
| certificate |
|
||||
+----+----+----+-//
|
||||
|
||||
public_key :: PublicKey (partial or full)
|
||||
public_key :: publicKey (partial or full)
|
||||
length -> 256 bytes or as specified in key certificate
|
||||
|
||||
padding :: random data
|
||||
length -> 0 bytes or as specified in key certificate
|
||||
padding length + signing_key length == 128 bytes
|
||||
|
||||
signing__key :: SigningPublicKey (partial or full)
|
||||
signing__key :: signingPublicKey (partial or full)
|
||||
length -> 128 bytes or as specified in key certificate
|
||||
padding length + signing_key length == 128 bytes
|
||||
|
||||
@@ -76,34 +76,34 @@ total length: 387+ bytes
|
||||
//
|
||||
// https://geti2p.net/spec/common-structures#keysandcert
|
||||
type KeysAndCert struct {
|
||||
KeyCertificate *KeyCertificate
|
||||
keyCertificate *KeyCertificate
|
||||
publicKey crypto.PublicKey
|
||||
padding []byte
|
||||
Padding []byte
|
||||
signingPublicKey crypto.SigningPublicKey
|
||||
}
|
||||
|
||||
// Bytes returns the entire KeyCertificate in []byte form, trims payload to specified length.
|
||||
// Bytes returns the entire keyCertificate in []byte form, trims payload to specified length.
|
||||
func (keys_and_cert KeysAndCert) Bytes() []byte {
|
||||
bytes := keys_and_cert.KeyCertificate.Bytes()
|
||||
bytes := keys_and_cert.keyCertificate.Bytes()
|
||||
log.WithFields(logrus.Fields{
|
||||
"bytes_length": len(bytes),
|
||||
}).Debug("Retrieved bytes from KeysAndCert")
|
||||
return bytes
|
||||
}
|
||||
|
||||
// PublicKey returns the public key as a crypto.PublicKey.
|
||||
// publicKey returns the public key as a crypto.publicKey.
|
||||
func (keys_and_cert *KeysAndCert) PublicKey() (key crypto.PublicKey) {
|
||||
return keys_and_cert.publicKey
|
||||
}
|
||||
|
||||
// SigningPublicKey returns the signing public key.
|
||||
// signingPublicKey returns the signing public key.
|
||||
func (keys_and_cert *KeysAndCert) SigningPublicKey() (signing_public_key crypto.SigningPublicKey) {
|
||||
return keys_and_cert.signingPublicKey
|
||||
}
|
||||
|
||||
// Certfificate returns the certificate.
|
||||
func (keys_and_cert *KeysAndCert) Certificate() (cert Certificate) {
|
||||
return keys_and_cert.KeyCertificate.Certificate
|
||||
return keys_and_cert.keyCertificate.Certificate
|
||||
}
|
||||
|
||||
// ReadKeysAndCert creates a new *KeysAndCert from []byte using ReadKeysAndCert.
|
||||
@@ -123,7 +123,7 @@ func ReadKeysAndCert(data []byte) (keys_and_cert KeysAndCert, remainder []byte,
|
||||
"reason": "not enough data",
|
||||
}).Error("error parsing keys and cert")
|
||||
err = errors.New("error parsing KeysAndCert: data is smaller than minimum valid size")
|
||||
keys_and_cert.KeyCertificate, remainder, _ = NewKeyCertificate(data[KEYS_AND_CERT_DATA_SIZE:])
|
||||
keys_and_cert.keyCertificate, remainder, _ = NewKeyCertificate(data[KEYS_AND_CERT_DATA_SIZE:])
|
||||
return
|
||||
} else if data_len < KEYS_AND_CERT_DATA_SIZE {
|
||||
log.WithFields(logrus.Fields{
|
||||
@@ -135,30 +135,30 @@ func ReadKeysAndCert(data []byte) (keys_and_cert KeysAndCert, remainder []byte,
|
||||
err = errors.New("error parsing KeysAndCert: data is smaller than minimum valid size")
|
||||
return
|
||||
}
|
||||
keys_and_cert.KeyCertificate, remainder, err = NewKeyCertificate(data[KEYS_AND_CERT_DATA_SIZE:])
|
||||
keys_and_cert.keyCertificate, remainder, err = NewKeyCertificate(data[KEYS_AND_CERT_DATA_SIZE:])
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to create KeyCertificate")
|
||||
log.WithError(err).Error("Failed to create keyCertificate")
|
||||
return
|
||||
}
|
||||
// TODO: this only supports one key type right now and it's the old key type, but the layout is the same.
|
||||
// a case-switch which sets the size of the SPK and the PK should be used to replace the referenced KEYS_AND_CERT_PUBKEY_SIZE
|
||||
// and KEYS_AND_CERT_SPK_SIZE constants in the future.
|
||||
keys_and_cert.publicKey, err = keys_and_cert.KeyCertificate.ConstructPublicKey(data[:keys_and_cert.KeyCertificate.CryptoSize()])
|
||||
keys_and_cert.publicKey, err = keys_and_cert.keyCertificate.ConstructPublicKey(data[:keys_and_cert.keyCertificate.CryptoSize()])
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to construct PublicKey")
|
||||
log.WithError(err).Error("Failed to construct publicKey")
|
||||
return
|
||||
}
|
||||
keys_and_cert.signingPublicKey, err = keys_and_cert.KeyCertificate.ConstructSigningPublicKey(data[KEYS_AND_CERT_DATA_SIZE-keys_and_cert.KeyCertificate.SignatureSize() : KEYS_AND_CERT_DATA_SIZE])
|
||||
keys_and_cert.signingPublicKey, err = keys_and_cert.keyCertificate.ConstructSigningPublicKey(data[KEYS_AND_CERT_DATA_SIZE-keys_and_cert.keyCertificate.SignatureSize() : KEYS_AND_CERT_DATA_SIZE])
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to construct SigningPublicKey")
|
||||
log.WithError(err).Error("Failed to construct signingPublicKey")
|
||||
return
|
||||
}
|
||||
padding := data[KEYS_AND_CERT_PUBKEY_SIZE : KEYS_AND_CERT_DATA_SIZE-KEYS_AND_CERT_SPK_SIZE]
|
||||
keys_and_cert.padding = padding
|
||||
keys_and_cert.Padding = padding
|
||||
|
||||
log.WithFields(logrus.Fields{
|
||||
"public_key_type": keys_and_cert.KeyCertificate.PublicKeyType(),
|
||||
"signing_public_key_type": keys_and_cert.KeyCertificate.SigningPublicKeyType(),
|
||||
"public_key_type": keys_and_cert.keyCertificate.PublicKeyType(),
|
||||
"signing_public_key_type": keys_and_cert.keyCertificate.SigningPublicKeyType(),
|
||||
"padding_length": len(padding),
|
||||
"remainder_length": len(remainder),
|
||||
}).Debug("Successfully read KeysAndCert")
|
||||
@@ -166,3 +166,66 @@ func ReadKeysAndCert(data []byte) (keys_and_cert KeysAndCert, remainder []byte,
|
||||
return
|
||||
}
|
||||
|
||||
// NewKeysAndCert creates a new KeysAndCert instance with the provided parameters.
|
||||
// It validates the sizes of the provided keys and padding before assembling the struct.
|
||||
func NewKeysAndCert(
|
||||
keyCertificate *KeyCertificate,
|
||||
publicKey crypto.PublicKey,
|
||||
padding []byte,
|
||||
signingPublicKey crypto.SigningPublicKey,
|
||||
) (*KeysAndCert, error) {
|
||||
log.Debug("Creating new KeysAndCert with provided parameters")
|
||||
|
||||
// 1. Validate keyCertificate
|
||||
if keyCertificate == nil {
|
||||
log.Error("KeyCertificate is nil")
|
||||
return nil, errors.New("KeyCertificate cannot be nil")
|
||||
}
|
||||
|
||||
// 2. Validate publicKey size
|
||||
if publicKey.Len() != KEYS_AND_CERT_PUBKEY_SIZE {
|
||||
log.WithFields(logrus.Fields{
|
||||
"expected_size": KEYS_AND_CERT_PUBKEY_SIZE,
|
||||
"actual_size": publicKey.Len(),
|
||||
}).Error("Invalid publicKey size")
|
||||
return nil, errors.New("publicKey has an invalid size")
|
||||
}
|
||||
|
||||
/*
|
||||
// 3. Validate signingPublicKey size
|
||||
if signingPublicKey.Len() != KEYS_AND_CERT_SPK_SIZE {
|
||||
log.WithFields(logrus.Fields{
|
||||
"expected_size": KEYS_AND_CERT_SPK_SIZE,
|
||||
"actual_size": signingPublicKey.Len(),
|
||||
}).Error("Invalid signingPublicKey size")
|
||||
return nil, errors.New("signingPublicKey has an invalid size")
|
||||
}
|
||||
|
||||
*/
|
||||
|
||||
// 4. Validate padding size
|
||||
expectedPaddingSize := KEYS_AND_CERT_DATA_SIZE - KEYS_AND_CERT_PUBKEY_SIZE - KEYS_AND_CERT_SPK_SIZE
|
||||
if len(padding) != expectedPaddingSize {
|
||||
log.WithFields(logrus.Fields{
|
||||
"expected_size": expectedPaddingSize,
|
||||
"actual_size": len(padding),
|
||||
}).Error("Invalid padding size")
|
||||
return nil, errors.New("padding has an invalid size")
|
||||
}
|
||||
|
||||
// 5. Assemble KeysAndCert
|
||||
keysAndCert := &KeysAndCert{
|
||||
keyCertificate: keyCertificate,
|
||||
publicKey: publicKey,
|
||||
Padding: padding,
|
||||
signingPublicKey: signingPublicKey,
|
||||
}
|
||||
|
||||
log.WithFields(logrus.Fields{
|
||||
"public_key_length": publicKey.Len(),
|
||||
"signing_public_key_length": signingPublicKey.Len(),
|
||||
"padding_length": len(padding),
|
||||
}).Debug("Successfully created KeysAndCert")
|
||||
|
||||
return keysAndCert, nil
|
||||
}
|
||||
|
@@ -32,13 +32,13 @@ Accurate for version 0.9.49
|
||||
|
||||
Description
|
||||
Contains all of the currently authorized Leases for a particular Destination, the
|
||||
PublicKey to which garlic messages can be encrypted, and then the SigningPublicKey
|
||||
publicKey to which garlic messages can be encrypted, and then the signingPublicKey
|
||||
that can be used to revoke this particular version of the structure. The LeaseSet is one
|
||||
of the two structures stored in the network database (the other being RouterInfo), and
|
||||
is kered under the SHA256 of the contained Destination.
|
||||
|
||||
Contents
|
||||
Destination, followed by a PublicKey for encryption, then a SigningPublicKey which
|
||||
Destination, followed by a publicKey for encryption, then a signingPublicKey which
|
||||
can be used to revoke this version of the LeaseSet, then a 1 byte Integer specifying how
|
||||
many Lease structures are in the set, followed by the actual Lease structures and
|
||||
finally a Signature of the previous bytes signed by the Destination's SigningPrivateKey.
|
||||
@@ -100,10 +100,10 @@ finally a Signature of the previous bytes signed by the Destination's SigningPri
|
||||
destination :: Destination
|
||||
length -> >= 387 bytes
|
||||
|
||||
encryption_key :: PublicKey
|
||||
encryption_key :: publicKey
|
||||
length -> 256 bytes
|
||||
|
||||
signing_key :: SigningPublicKey
|
||||
signing_key :: signingPublicKey
|
||||
length -> 128 bytes or as specified in destination's key certificate
|
||||
|
||||
num :: Integer
|
||||
@@ -157,7 +157,7 @@ func (lease_set LeaseSet) PublicKey() (public_key crypto.ElgPublicKey, err error
|
||||
remainder_len := len(remainder)
|
||||
if remainder_len < LEASE_SET_PUBKEY_SIZE {
|
||||
log.WithFields(logrus.Fields{
|
||||
"at": "(LeaseSet) PublicKey",
|
||||
"at": "(LeaseSet) publicKey",
|
||||
"data_len": remainder_len,
|
||||
"required_len": LEASE_SET_PUBKEY_SIZE,
|
||||
"reason": "not enough data",
|
||||
@@ -167,7 +167,7 @@ func (lease_set LeaseSet) PublicKey() (public_key crypto.ElgPublicKey, err error
|
||||
return
|
||||
}
|
||||
copy(public_key[:], remainder[:LEASE_SET_PUBKEY_SIZE])
|
||||
log.Debug("Successfully retrieved PublicKey from LeaseSet")
|
||||
log.Debug("Successfully retrieved publicKey from LeaseSet")
|
||||
return
|
||||
}
|
||||
|
||||
@@ -200,11 +200,11 @@ func (lease_set LeaseSet) SigningKey() (signing_public_key crypto.SigningPublicK
|
||||
}
|
||||
if cert_len == 0 {
|
||||
// No Certificate is present, return the LEASE_SET_SPK_SIZE byte
|
||||
// SigningPublicKey space as legacy DSA SHA1 SigningPublicKey.
|
||||
// signingPublicKey space as legacy DSA SHA1 signingPublicKey.
|
||||
var dsa_pk crypto.DSAPublicKey
|
||||
copy(dsa_pk[:], lease_set[offset:offset+LEASE_SET_SPK_SIZE])
|
||||
signing_public_key = dsa_pk
|
||||
log.Debug("Retrieved legacy DSA SHA1 SigningPublicKey")
|
||||
log.Debug("Retrieved legacy DSA SHA1 signingPublicKey")
|
||||
} else {
|
||||
// A Certificate is present in this LeaseSet's Destination
|
||||
cert_type := cert.Type()
|
||||
@@ -216,17 +216,17 @@ func (lease_set LeaseSet) SigningKey() (signing_public_key crypto.SigningPublicK
|
||||
lease_set[offset : offset+LEASE_SET_SPK_SIZE],
|
||||
)
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to construct SigningPublicKey from KeyCertificate")
|
||||
log.WithError(err).Error("Failed to construct signingPublicKey from keyCertificate")
|
||||
} else {
|
||||
log.Debug("Retrieved SigningPublicKey from KeyCertificate")
|
||||
log.Debug("Retrieved signingPublicKey from keyCertificate")
|
||||
}
|
||||
} else {
|
||||
// No Certificate is present, return the LEASE_SET_SPK_SIZE byte
|
||||
// SigningPublicKey space as legacy DSA SHA1 SigningPublicKey.
|
||||
// signingPublicKey space as legacy DSA SHA1 signingPublicKey.
|
||||
var dsa_pk crypto.DSAPublicKey
|
||||
copy(dsa_pk[:], lease_set[offset:offset+LEASE_SET_SPK_SIZE])
|
||||
signing_public_key = dsa_pk
|
||||
log.Debug("Retrieved legacy DSA SHA1 SigningPublicKey (Certificate present but not Key Certificate)")
|
||||
log.Debug("Retrieved legacy DSA SHA1 signingPublicKey (Certificate present but not Key Certificate)")
|
||||
}
|
||||
}
|
||||
return
|
||||
@@ -358,7 +358,7 @@ func (lease_set LeaseSet) Verify() error {
|
||||
//data := lease_set[:data_end]
|
||||
//spk, _ := lease_set.
|
||||
// Destination().
|
||||
// SigningPublicKey()
|
||||
// signingPublicKey()
|
||||
//verifier, err := spk.NewVerifier()
|
||||
//if err != nil {
|
||||
// return err
|
||||
|
@@ -61,7 +61,7 @@ func buildSignature(size int) []byte {
|
||||
|
||||
func buildFullLeaseSet(n int) LeaseSet {
|
||||
lease_set_data := make([]byte, 0)
|
||||
lease_set_data = append(lease_set_data, buildDestination().KeysAndCert.KeyCertificate.RawBytes()...)
|
||||
lease_set_data = append(lease_set_data, buildDestination().KeysAndCert.keyCertificate.RawBytes()...)
|
||||
lease_set_data = append(lease_set_data, buildPublicKey()...)
|
||||
lease_set_data = append(lease_set_data, buildSigningKey()...)
|
||||
lease_set_data = append(lease_set_data, byte(n))
|
||||
|
@@ -2,11 +2,13 @@
|
||||
package router_address
|
||||
|
||||
import (
|
||||
"encoding/binary"
|
||||
"errors"
|
||||
"fmt"
|
||||
"net"
|
||||
"strconv"
|
||||
"strings"
|
||||
"time"
|
||||
|
||||
"github.com/go-i2p/go-i2p/lib/util/logger"
|
||||
"github.com/sirupsen/logrus"
|
||||
@@ -359,3 +361,57 @@ func ReadRouterAddress(data []byte) (router_address RouterAddress, remainder []b
|
||||
}
|
||||
return
|
||||
}
|
||||
|
||||
// NewRouterAddress creates a new RouterAddress with the provided parameters.
|
||||
// Returns a pointer to RouterAddress.
|
||||
func NewRouterAddress(cost uint8, expiration time.Time, transportType string, options map[string]string) (*RouterAddress, error) {
|
||||
log.Debug("Creating new RouterAddress")
|
||||
|
||||
// Create TransportCost as an Integer (1 byte)
|
||||
transportCost, err := NewIntegerFromInt(int(cost), 1)
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to create TransportCost Integer")
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Create ExpirationDate as a Date
|
||||
millis := expiration.UnixNano() / int64(time.Millisecond)
|
||||
dateBytes := make([]byte, DATE_SIZE)
|
||||
binary.BigEndian.PutUint64(dateBytes, uint64(millis))
|
||||
expirationDate, _, err := NewDate(dateBytes)
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to create ExpirationDate")
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Create TransportType as an I2PString
|
||||
transportTypeStr, err := ToI2PString(transportType)
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to create TransportType I2PString")
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Create TransportOptions as a Mapping
|
||||
transportOptions, err := GoMapToMapping(options)
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to create TransportOptions Mapping")
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Create RouterAddress
|
||||
ra := &RouterAddress{
|
||||
TransportCost: transportCost,
|
||||
ExpirationDate: expirationDate,
|
||||
TransportType: transportTypeStr,
|
||||
TransportOptions: transportOptions,
|
||||
}
|
||||
|
||||
log.WithFields(logrus.Fields{
|
||||
"cost": cost,
|
||||
"expiration": expiration,
|
||||
"transportType": transportType,
|
||||
"options": options,
|
||||
}).Debug("Successfully created new RouterAddress")
|
||||
|
||||
return ra, nil
|
||||
}
|
||||
|
@@ -2,7 +2,10 @@
|
||||
package router_identity
|
||||
|
||||
import (
|
||||
"github.com/go-i2p/go-i2p/lib/common/certificate"
|
||||
"github.com/go-i2p/go-i2p/lib/common/key_certificate"
|
||||
. "github.com/go-i2p/go-i2p/lib/common/keys_and_cert"
|
||||
"github.com/go-i2p/go-i2p/lib/crypto"
|
||||
"github.com/go-i2p/go-i2p/lib/util/logger"
|
||||
"github.com/sirupsen/logrus"
|
||||
)
|
||||
@@ -47,3 +50,30 @@ func ReadRouterIdentity(data []byte) (router_identity RouterIdentity, remainder
|
||||
}).Debug("Successfully read RouterIdentity")
|
||||
return
|
||||
}
|
||||
|
||||
func NewRouterIdentity(publicKey crypto.PublicKey, signingPublicKey crypto.SigningPublicKey, cert certificate.Certificate, padding []byte) (*RouterIdentity, error) {
|
||||
log.Debug("Creating new RouterIdentity")
|
||||
|
||||
// Step 1: Create keyCertificate from the provided certificate.
|
||||
// Assuming NewKeyCertificate is a constructor that takes a Certificate and returns a keyCertificate.
|
||||
keyCert := key_certificate.KeyCertificateFromCertificate(cert)
|
||||
|
||||
// Step 2: Create KeysAndCert instance.
|
||||
keysAndCert, err := NewKeysAndCert(keyCert, publicKey, padding, signingPublicKey)
|
||||
if err != nil {
|
||||
log.WithError(err).Error("NewKeysAndCert failed.")
|
||||
}
|
||||
|
||||
// Step 3: Initialize RouterIdentity with KeysAndCert.
|
||||
routerIdentity := RouterIdentity{
|
||||
KeysAndCert: *keysAndCert,
|
||||
}
|
||||
|
||||
log.WithFields(logrus.Fields{
|
||||
"public_key_type": keyCert.PublicKeyType(),
|
||||
"signing_public_key_type": keyCert.SigningPublicKeyType(),
|
||||
"padding_length": len(padding),
|
||||
}).Debug("Successfully created RouterIdentity")
|
||||
|
||||
return &routerIdentity, nil
|
||||
}
|
||||
|
@@ -2,9 +2,12 @@
|
||||
package router_info
|
||||
|
||||
import (
|
||||
"encoding/binary"
|
||||
"errors"
|
||||
"github.com/go-i2p/go-i2p/lib/crypto"
|
||||
"strconv"
|
||||
"strings"
|
||||
"time"
|
||||
|
||||
"github.com/go-i2p/go-i2p/lib/util/logger"
|
||||
"github.com/sirupsen/logrus"
|
||||
@@ -156,7 +159,9 @@ func (router_info *RouterInfo) RouterIdentity() *RouterIdentity {
|
||||
// IndentHash returns the identity hash (sha256 sum) for this RouterInfo.
|
||||
func (router_info *RouterInfo) IdentHash() Hash {
|
||||
log.Debug("Calculating IdentHash for RouterInfo")
|
||||
data, _ := router_info.RouterIdentity().KeyCertificate.Data()
|
||||
//data, _ := router_info.RouterIdentity().keyCertificate.Data()
|
||||
cert := router_info.RouterIdentity().KeysAndCert.Certificate()
|
||||
data := cert.Data()
|
||||
hash := HashData(data)
|
||||
log.WithField("hash", hash).Debug("Calculated IdentHash for RouterInfo")
|
||||
return HashData(data)
|
||||
@@ -293,6 +298,118 @@ func ReadRouterInfo(bytes []byte) (info RouterInfo, remainder []byte, err error)
|
||||
return
|
||||
}
|
||||
|
||||
// serializeWithoutSignature serializes the RouterInfo up to (but not including) the signature.
|
||||
func (ri *RouterInfo) serializeWithoutSignature() []byte {
|
||||
var bytes []byte
|
||||
// Serialize RouterIdentity
|
||||
bytes = append(bytes, ri.router_identity.Bytes()...)
|
||||
|
||||
// Serialize Published Date
|
||||
bytes = append(bytes, ri.published.Bytes()...)
|
||||
|
||||
// Serialize Size
|
||||
bytes = append(bytes, ri.size.Bytes()...)
|
||||
|
||||
// Serialize Addresses
|
||||
for _, addr := range ri.addresses {
|
||||
bytes = append(bytes, addr.Bytes()...)
|
||||
}
|
||||
|
||||
// Serialize PeerSize (always zero)
|
||||
bytes = append(bytes, ri.peer_size.Bytes()...)
|
||||
|
||||
// Serialize Options
|
||||
bytes = append(bytes, ri.options.Data()...)
|
||||
|
||||
return bytes
|
||||
}
|
||||
|
||||
func NewRouterInfo(
|
||||
routerIdentity *RouterIdentity,
|
||||
publishedTime time.Time,
|
||||
addresses []*RouterAddress,
|
||||
options map[string]string,
|
||||
signingPrivateKey crypto.SigningPrivateKey,
|
||||
) (*RouterInfo, error) {
|
||||
log.Debug("Creating new RouterInfo")
|
||||
|
||||
// 1. Create Published Date
|
||||
millis := publishedTime.UnixNano() / int64(time.Millisecond)
|
||||
dateBytes := make([]byte, DATE_SIZE)
|
||||
binary.BigEndian.PutUint64(dateBytes, uint64(millis))
|
||||
publishedDate, _, err := ReadDate(dateBytes)
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to create Published Date")
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// 2. Create Size Integer
|
||||
sizeInt, err := NewIntegerFromInt(len(addresses), 1)
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to create Size Integer")
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// 3. Create PeerSize Integer (always 0)
|
||||
peerSizeInt, err := NewIntegerFromInt(0, 1)
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to create PeerSize Integer")
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// 4. Convert options map to Mapping
|
||||
mapping, err := GoMapToMapping(options)
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to convert options map to Mapping")
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// 5. Assemble RouterInfo without signature
|
||||
routerInfo := &RouterInfo{
|
||||
router_identity: *routerIdentity,
|
||||
published: &publishedDate,
|
||||
size: sizeInt,
|
||||
addresses: addresses,
|
||||
peer_size: peerSizeInt,
|
||||
options: mapping,
|
||||
signature: nil, // To be set after signing
|
||||
}
|
||||
|
||||
// 6. Serialize RouterInfo without signature
|
||||
dataBytes := routerInfo.serializeWithoutSignature()
|
||||
|
||||
// 7. Compute signature over serialized data
|
||||
signer, err := signingPrivateKey.NewSigner()
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to create new signer")
|
||||
return nil, err
|
||||
}
|
||||
signatureBytes, err := signer.Sign(dataBytes)
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to sign")
|
||||
}
|
||||
|
||||
// 8. Create Signature struct from signatureBytes
|
||||
sig, _, err := ReadSignature(signatureBytes)
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to create Signature from signature bytes")
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// 9. Attach signature to RouterInfo
|
||||
routerInfo.signature = &sig
|
||||
|
||||
log.WithFields(logrus.Fields{
|
||||
"router_identity": routerIdentity,
|
||||
"published": publishedDate,
|
||||
"address_count": len(addresses),
|
||||
"options": options,
|
||||
"signature": sig,
|
||||
}).Debug("Successfully created RouterInfo")
|
||||
|
||||
return routerInfo, nil
|
||||
}
|
||||
|
||||
func (router_info *RouterInfo) RouterCapabilities() string {
|
||||
log.Debug("Retrieving RouterCapabilities")
|
||||
str, err := ToI2PString("caps")
|
||||
|
89
lib/common/router_info/router_info2_test.go
Normal file
89
lib/common/router_info/router_info2_test.go
Normal file
@@ -0,0 +1,89 @@
|
||||
package router_info
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"crypto/rand"
|
||||
"encoding/binary"
|
||||
"fmt"
|
||||
"github.com/go-i2p/go-i2p/lib/common/certificate"
|
||||
"github.com/go-i2p/go-i2p/lib/common/data"
|
||||
"github.com/go-i2p/go-i2p/lib/common/router_identity"
|
||||
"github.com/go-i2p/go-i2p/lib/crypto"
|
||||
"golang.org/x/crypto/openpgp/elgamal"
|
||||
"testing"
|
||||
"time"
|
||||
)
|
||||
|
||||
func TestCreateRouterInfo(t *testing.T) {
|
||||
// Generate signing key pair (Ed25519)
|
||||
var ed25519_privkey crypto.Ed25519PrivateKey
|
||||
_, err := (&ed25519_privkey).Generate()
|
||||
if err != nil {
|
||||
t.Fatalf("Failed to generate Ed25519 private key: %v\n", err)
|
||||
}
|
||||
ed25519_pubkey_raw, err := ed25519_privkey.Public()
|
||||
if err != nil {
|
||||
t.Fatalf("Failed to derive Ed25519 public key: %v\n", err)
|
||||
}
|
||||
ed25519_pubkey, ok := ed25519_pubkey_raw.(crypto.SigningPublicKey)
|
||||
if !ok {
|
||||
t.Fatalf("Failed to get SigningPublicKey from Ed25519 public key")
|
||||
}
|
||||
|
||||
// Generate encryption key pair (ElGamal)
|
||||
var elgamal_privkey elgamal.PrivateKey
|
||||
err = crypto.ElgamalGenerate(&elgamal_privkey, rand.Reader)
|
||||
if err != nil {
|
||||
t.Fatalf("Failed to generate ElGamal private key: %v\n", err)
|
||||
}
|
||||
|
||||
// Convert elgamal private key to crypto.ElgPrivateKey
|
||||
var elg_privkey crypto.ElgPrivateKey
|
||||
xBytes := elgamal_privkey.X.Bytes()
|
||||
if len(xBytes) > 256 {
|
||||
t.Fatalf("ElGamal private key X too large")
|
||||
}
|
||||
copy(elg_privkey[256-len(xBytes):], xBytes)
|
||||
|
||||
// Convert elgamal public key to crypto.ElgPublicKey
|
||||
var elg_pubkey crypto.ElgPublicKey
|
||||
yBytes := elgamal_privkey.PublicKey.Y.Bytes()
|
||||
if len(yBytes) > 256 {
|
||||
t.Fatalf("ElGamal public key Y too large")
|
||||
}
|
||||
copy(elg_pubkey[256-len(yBytes):], yBytes)
|
||||
|
||||
// Ensure that elg_pubkey implements crypto.PublicKey interface
|
||||
var _ crypto.PublicKey = elg_pubkey
|
||||
|
||||
// Create KeyCertificate specifying key types
|
||||
var payload bytes.Buffer
|
||||
|
||||
signingPublicKeyType, _ := data.NewIntegerFromInt(7, 2)
|
||||
cryptoPublicKeyType, _ := data.NewIntegerFromInt(0, 2)
|
||||
|
||||
err = binary.Write(&payload, binary.BigEndian, signingPublicKeyType)
|
||||
if err != nil {
|
||||
t.Fatalf("Failed to write signing public key type to payload: %v\n", err)
|
||||
}
|
||||
|
||||
err = binary.Write(&payload, binary.BigEndian, cryptoPublicKeyType)
|
||||
if err != nil {
|
||||
t.Fatalf("Failed to write crypto public key type to payload: %v\n", err)
|
||||
}
|
||||
|
||||
// Create KeyCertificate specifying key types
|
||||
cert, err := certificate.NewCertificateWithType(certificate.CERT_KEY, payload.Bytes())
|
||||
if err != nil {
|
||||
t.Fatalf("Failed to create new certificate: %v\n", err)
|
||||
}
|
||||
|
||||
// Create RouterIdentity
|
||||
routerIdentity, err := router_identity.NewRouterIdentity(elg_pubkey, ed25519_pubkey, *cert, nil)
|
||||
if err != nil {
|
||||
t.Fatalf("Failed to create router identity: %v\n", err)
|
||||
}
|
||||
|
||||
routerInfo, err := NewRouterInfo(routerIdentity, time.Now(), nil, nil, &ed25519_privkey)
|
||||
fmt.Printf("routerInfo:%v\n", routerInfo)
|
||||
}
|
@@ -2,6 +2,7 @@
|
||||
package signature
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"github.com/go-i2p/go-i2p/lib/util/logger"
|
||||
"github.com/sirupsen/logrus"
|
||||
)
|
||||
@@ -39,30 +40,42 @@ DSA_SHA1. As of release 0.9.12, other types may be supported, depending on conte
|
||||
// https://geti2p.net/spec/common-structures#signature
|
||||
type Signature []byte
|
||||
|
||||
// ReadSignature returns Signature from a []byte.
|
||||
// ReadSignature returns a Signature from a []byte.
|
||||
// The remaining bytes after the specified length are also returned.
|
||||
// Returns a list of errors that occurred during parsing.
|
||||
func ReadSignature(bytes []byte) (info Signature, remainder []byte, err error) {
|
||||
// TODO: stub
|
||||
log.Warn("ReadSignature is not implemented")
|
||||
// Returns an error if there is insufficient data to read the signature.
|
||||
//
|
||||
// Since the signature type and length are inferred from context (the type of key used),
|
||||
// and are not explicitly stated, this function assumes the default signature type (DSA_SHA1)
|
||||
// with a length of 40 bytes.
|
||||
//
|
||||
// If a different signature type is expected based on context, this function should be
|
||||
// modified accordingly to handle the correct signature length.
|
||||
func ReadSignature(data []byte) (sig Signature, remainder []byte, err error) {
|
||||
// Assume the default signature type DSA_SHA1 with length 40 bytes
|
||||
sigLength := DSA_SHA1_SIZE
|
||||
if len(data) < sigLength {
|
||||
err = fmt.Errorf("insufficient data to read signature: need %d bytes, have %d", sigLength, len(data))
|
||||
log.WithError(err).Error("Failed to read Signature")
|
||||
return
|
||||
}
|
||||
sig = data[:sigLength]
|
||||
remainder = data[sigLength:]
|
||||
return
|
||||
}
|
||||
|
||||
// NewSignature creates a new *Signature from []byte using ReadSignature.
|
||||
// Returns a pointer to Signature unlike ReadSignature.
|
||||
func NewSignature(data []byte) (session_tag *Signature, remainder []byte, err error) {
|
||||
func NewSignature(data []byte) (signature *Signature, remainder []byte, err error) {
|
||||
log.WithField("input_length", len(data)).Debug("Creating new Signature")
|
||||
// sessionTag, remainder, err := ReadSignature(data)
|
||||
sig, remainder, err := ReadSignature(data)
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to read Signature")
|
||||
return nil, remainder, err
|
||||
}
|
||||
session_tag = &sig
|
||||
signature = &sig
|
||||
log.WithFields(logrus.Fields{
|
||||
"signature_length": len(sig),
|
||||
"remainder_length": len(remainder),
|
||||
}).Debug("Successfully created new Signature")
|
||||
|
||||
return
|
||||
}
|
||||
|
@@ -12,7 +12,10 @@ import (
|
||||
"github.com/sirupsen/logrus"
|
||||
)
|
||||
|
||||
var Ed25519EncryptTooBig = errors.New("failed to encrypt data, too big for Ed25519")
|
||||
var (
|
||||
Ed25519EncryptTooBig = errors.New("failed to encrypt data, too big for Ed25519")
|
||||
ErrInvalidPublicKeySize = errors.New("failed to verify: invalid ed25519 public key size")
|
||||
)
|
||||
|
||||
type Ed25519PublicKey []byte
|
||||
|
||||
@@ -44,22 +47,36 @@ func createEd25519PublicKey(data []byte) (k *ed25519.PublicKey) {
|
||||
return
|
||||
}
|
||||
|
||||
func createEd25519Encryption(pub *ed25519.PublicKey, rand io.Reader) (enc *Ed25519Encryption, err error) {
|
||||
/*kbytes := make([]byte, 256)
|
||||
k := new(big.Int)
|
||||
for err == nil {
|
||||
_, err = io.ReadFull(rand, kbytes)
|
||||
k = new(big.Int).SetBytes(kbytes)
|
||||
k = k.Mod(k, pub.P)
|
||||
if k.Sign() != 0 {
|
||||
break
|
||||
}
|
||||
// createEd25519Encryption initializes the Ed25519Encryption struct using the public key.
|
||||
func createEd25519Encryption(pub *ed25519.PublicKey, randReader io.Reader) (*Ed25519Encryption, error) {
|
||||
// Define p = 2^255 - 19
|
||||
p := new(big.Int).Sub(new(big.Int).Lsh(big.NewInt(1), 255), big.NewInt(19))
|
||||
|
||||
// Validate public key length
|
||||
if len(*pub) != ed25519.PublicKeySize {
|
||||
log.WithField("pub_length", len(*pub)).Error("Invalid Ed25519 public key size")
|
||||
return nil, ErrInvalidPublicKeySize
|
||||
}
|
||||
if err == nil {
|
||||
enc = &Ed25519Encryption{}
|
||||
}*/
|
||||
log.Warn("createEd25519Encryption is not implemented")
|
||||
return
|
||||
|
||||
// Convert public key bytes to big.Int
|
||||
a := new(big.Int).SetBytes(*pub)
|
||||
|
||||
// Generate a random scalar b1 in [0, p)
|
||||
b1, err := rand.Int(randReader, p)
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to generate b1 for Ed25519Encryption")
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Initialize Ed25519Encryption struct
|
||||
enc := &Ed25519Encryption{
|
||||
p: p,
|
||||
a: a,
|
||||
b1: b1,
|
||||
}
|
||||
|
||||
log.Debug("Ed25519Encryption created successfully")
|
||||
return enc, nil
|
||||
}
|
||||
|
||||
type Ed25519Encryption struct {
|
||||
@@ -109,13 +126,18 @@ func (ed25519 *Ed25519Encryption) EncryptPadding(data []byte, zeroPadding bool)
|
||||
func (elg Ed25519PublicKey) NewEncrypter() (enc Encrypter, err error) {
|
||||
log.Debug("Creating new Ed25519 encrypter")
|
||||
k := createEd25519PublicKey(elg[:])
|
||||
if k == nil {
|
||||
return nil, errors.New("invalid public key format")
|
||||
}
|
||||
|
||||
enc, err = createEd25519Encryption(k, rand.Reader)
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to create Ed25519 encrypter")
|
||||
} else {
|
||||
log.Debug("Ed25519 encrypter created successfully")
|
||||
return nil, err
|
||||
}
|
||||
return
|
||||
|
||||
log.Debug("Ed25519 encrypter created successfully")
|
||||
return enc, nil
|
||||
}
|
||||
|
||||
func (v *Ed25519Verifier) VerifyHash(h, sig []byte) (err error) {
|
||||
@@ -158,6 +180,42 @@ func (v *Ed25519Verifier) Verify(data, sig []byte) (err error) {
|
||||
|
||||
type Ed25519PrivateKey ed25519.PrivateKey
|
||||
|
||||
func (k Ed25519PrivateKey) NewDecrypter() (Decrypter, error) {
|
||||
//TODO implement me
|
||||
panic("implement me")
|
||||
}
|
||||
|
||||
func (k Ed25519PrivateKey) NewSigner() (Signer, error) {
|
||||
if len(k) != ed25519.PrivateKeySize {
|
||||
return nil, errors.New("invalid ed25519 private key size")
|
||||
}
|
||||
return &Ed25519Signer{k: k}, nil
|
||||
}
|
||||
|
||||
func (k Ed25519PrivateKey) Len() int {
|
||||
return len(k)
|
||||
}
|
||||
|
||||
func (k *Ed25519PrivateKey) Generate() (SigningPrivateKey, error) {
|
||||
// Generate a new Ed25519 key pair
|
||||
_, priv, err := ed25519.GenerateKey(rand.Reader)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
// Assign the generated private key to the receiver
|
||||
*k = Ed25519PrivateKey(priv)
|
||||
return k, nil
|
||||
}
|
||||
|
||||
func (k Ed25519PrivateKey) Public() (SigningPublicKey, error) {
|
||||
if len(k) != ed25519.PrivateKeySize {
|
||||
return nil, errors.New("invalid ed25519 private key size")
|
||||
}
|
||||
// The public key is the first 32 bytes of the private key's seed
|
||||
pubKey := k[32:]
|
||||
return Ed25519PublicKey(pubKey), nil
|
||||
}
|
||||
|
||||
type Ed25519Signer struct {
|
||||
k []byte
|
||||
}
|
||||
|
@@ -27,7 +27,6 @@ type SigningPublicKey interface {
|
||||
// get the size of this public key
|
||||
Len() int
|
||||
}
|
||||
|
||||
type PublicKey interface {
|
||||
Len() int
|
||||
NewEncrypter() (Encrypter, error)
|
||||
|
@@ -53,7 +53,7 @@ func fileRSAPubKey(t *testing.T, filename string) *rsa.PublicKey {
|
||||
}
|
||||
var pubKey *rsa.PublicKey
|
||||
if k, ok := cert.PublicKey.(*rsa.PublicKey); !ok {
|
||||
t.Fatalf("expected rsa.PublicKey from file %s", filename)
|
||||
t.Fatalf("expected rsa.publicKey from file %s", filename)
|
||||
} else {
|
||||
pubKey = k
|
||||
}
|
||||
|
Reference in New Issue
Block a user