2024-01-30 03:35:00 +00:00
package protocol
2024-01-06 11:33:46 +00:00
import (
2024-01-30 22:26:06 +00:00
"bytes"
2024-01-06 11:33:46 +00:00
"crypto/ed25519"
"errors"
2024-01-29 06:10:04 +00:00
"git.lumeweb.com/LumeWeb/libs5-go/config"
2024-01-06 11:33:46 +00:00
"git.lumeweb.com/LumeWeb/libs5-go/encoding"
"git.lumeweb.com/LumeWeb/libs5-go/types"
"github.com/vmihailenco/msgpack/v5"
2024-01-09 17:49:16 +00:00
"go.uber.org/zap"
2024-01-08 03:57:03 +00:00
"io"
2024-01-06 11:33:46 +00:00
)
var (
2024-01-30 03:35:00 +00:00
_ IncomingMessage = ( * SignedMessage ) ( nil )
_ msgpack . CustomDecoder = ( * signedMessageReader ) ( nil )
_ msgpack . CustomEncoder = ( * SignedMessage ) ( nil )
2024-01-06 11:33:46 +00:00
)
var (
errInvalidSignature = errors . New ( "Invalid signature found" )
)
type SignedMessage struct {
nodeId * encoding . NodeId
signature [ ] byte
message [ ] byte
2024-01-30 03:35:00 +00:00
HandshakeRequirement
2024-01-06 11:33:46 +00:00
}
2024-01-08 13:40:18 +00:00
func ( s * SignedMessage ) NodeId ( ) * encoding . NodeId {
return s . nodeId
}
2024-01-07 14:07:37 +00:00
func ( s * SignedMessage ) SetNodeId ( nodeId * encoding . NodeId ) {
s . nodeId = nodeId
}
func ( s * SignedMessage ) SetSignature ( signature [ ] byte ) {
s . signature = signature
}
func ( s * SignedMessage ) SetMessage ( message [ ] byte ) {
s . message = message
}
func NewSignedMessageRequest ( message [ ] byte ) * SignedMessage {
return & SignedMessage { message : message }
}
2024-01-29 04:39:40 +00:00
type signedMessageReader struct {
2024-01-06 11:33:46 +00:00
kind int
message msgpack . RawMessage
}
2024-01-29 04:39:40 +00:00
func ( s * signedMessageReader ) DecodeMsgpack ( dec * msgpack . Decoder ) error {
2024-01-06 11:33:46 +00:00
kind , err := dec . DecodeInt ( )
if err != nil {
return err
}
s . kind = kind
2024-01-08 03:57:03 +00:00
message , err := io . ReadAll ( dec . Buffered ( ) )
2024-01-06 11:33:46 +00:00
if err != nil {
return err
}
s . message = message
return nil
}
func NewSignedMessage ( ) * SignedMessage {
2024-01-13 16:22:01 +00:00
sm := & SignedMessage { }
sm . SetRequiresHandshake ( false )
return sm
2024-01-06 11:33:46 +00:00
}
2024-01-30 03:35:00 +00:00
func ( s * SignedMessage ) HandleMessage ( message IncomingMessageData ) error {
2024-01-29 04:39:40 +00:00
var payload signedMessageReader
peer := message . Peer
2024-01-29 06:55:36 +00:00
logger := message . Logger
2024-01-06 11:33:46 +00:00
err := msgpack . Unmarshal ( s . message , & payload )
if err != nil {
return err
}
2024-01-30 03:35:00 +00:00
if msgHandler , valid := GetSignedMessageType ( payload . kind ) ; valid {
2024-01-29 06:55:36 +00:00
logger . Debug ( "SignedMessage" , zap . Any ( "type" , types . ProtocolMethodMap [ types . ProtocolMethod ( payload . kind ) ] ) )
2024-01-13 16:22:01 +00:00
if msgHandler . RequiresHandshake ( ) && ! peer . IsHandshakeDone ( ) {
2024-03-10 13:17:13 +00:00
nid , err := s . nodeId . ToString ( )
if err != nil {
return err
}
logger . Debug ( "Peer is not handshake done, ignoring message" , zap . Any ( "type" , types . ProtocolMethodMap [ types . ProtocolMethod ( payload . kind ) ] ) , zap . String ( "peerIP" , peer . GetIPString ( ) ) , zap . String ( "nodeId" , nid ) )
2024-01-13 16:22:01 +00:00
return nil
}
2024-01-06 11:33:46 +00:00
2024-01-30 22:26:06 +00:00
signedDec := msgpack . NewDecoder ( bytes . NewReader ( payload . message ) )
signedMsg := IncomingMessageDataSigned {
2024-01-29 04:39:40 +00:00
IncomingMessageData : message ,
NodeId : s . nodeId ,
}
2024-01-30 22:26:06 +00:00
err = msgHandler . DecodeMessage ( signedDec , signedMsg )
2024-01-06 11:33:46 +00:00
if err != nil {
2024-01-30 22:26:06 +00:00
logger . Error ( "Error decoding signed message" , zap . Error ( err ) )
return err
}
if err = msgHandler . HandleMessage ( signedMsg ) ; err != nil {
logger . Error ( "Error handling signed message" , zap . Error ( err ) )
2024-01-06 11:33:46 +00:00
return err
}
}
return nil
}
2024-01-30 03:35:00 +00:00
func ( s * SignedMessage ) DecodeMessage ( dec * msgpack . Decoder , message IncomingMessageData ) error {
2024-01-06 11:33:46 +00:00
nodeId , err := dec . DecodeBytes ( )
if err != nil {
return err
}
s . nodeId = encoding . NewNodeId ( nodeId )
signature , err := dec . DecodeBytes ( )
if err != nil {
return err
}
s . signature = signature
2024-01-29 04:39:40 +00:00
signedMessage , err := dec . DecodeBytes ( )
2024-01-06 11:33:46 +00:00
if err != nil {
return err
}
2024-01-29 04:39:40 +00:00
s . message = signedMessage
2024-01-06 11:33:46 +00:00
2024-01-08 03:38:19 +00:00
if ! ed25519 . Verify ( s . nodeId . Raw ( ) [ 1 : ] , s . message , s . signature ) {
2024-01-06 11:33:46 +00:00
return errInvalidSignature
}
return nil
2024-01-07 14:07:37 +00:00
}
func ( s * SignedMessage ) EncodeMsgpack ( enc * msgpack . Encoder ) error {
err := enc . EncodeInt ( int64 ( types . ProtocolMethodSignedMessage ) )
if err != nil {
return err
}
err = enc . EncodeBytes ( s . nodeId . Raw ( ) )
if err != nil {
return err
}
err = enc . EncodeBytes ( s . signature )
if err != nil {
return err
}
err = enc . EncodeBytes ( s . message )
if err != nil {
return err
}
return nil
}
2024-01-29 06:10:04 +00:00
func ( s * SignedMessage ) Sign ( cfg * config . NodeConfig ) error {
2024-01-07 14:07:37 +00:00
if s . nodeId == nil {
panic ( "nodeId is nil" )
}
2024-01-06 11:33:46 +00:00
2024-01-07 14:07:37 +00:00
if s . message == nil {
panic ( "message is nil" )
}
2024-01-29 06:10:04 +00:00
s . signature = ed25519 . Sign ( cfg . KeyPair . ExtractBytes ( ) , s . message )
2024-01-07 14:07:37 +00:00
return nil
2024-01-06 11:33:46 +00:00
}