mirror of
https://github.com/kaspanet/kaspad.git
synced 2025-05-30 02:36:42 +00:00

* [NOD-1575] Implement Clone and Equal for all model types * [NOD-1575] Add assertion for transaction ID equality * [NOD-1575] Use DomainTransaction.Equal to compare to expected coinbase transaction * [NOD-1575] Add TestDomainBlockHeader_Clone * [NOD-1575] Don't clone nil values * [NOD-1575] Add type assertions * [NOD-1575] Don't clone nil values * [NOD-1575] Add missing Equals * [NOD-1575] Add length checks * [NOD-1575] Update comment * [NOD-1575] Check length for TransactionAcceptanceData * [NOD-1575] Explicitly clone nils where needed * [NOD-1575] Clone tx id * [NOD-1575] Flip condition * Nod 1576 make coverage tests for equal clone inside model externalapi (#1177) * [NOD-1576] Make coverage tests for equal and clone inside model and externalapi * Some formatting and naming fixes * Made transactionToCompare type exported * Added some tests and made some changes to the tests code * No changes made * Some formatting and naming changes made * Made better test coverage for externalapi clone and equal functions * Changed expected result for two cases * Added equal and clone functions tests for ghostdag and utxodiff * Added tests * [NOD-1576] Implement reachabilitydata equal/clone unit tests * [NOD-1576] Full coverage of reachabilitydata equal/clone unit tests * Made changes and handling panic to transaction_equal_clone_test.go and formating of utxodiff_equal_clone_test.go * Added recoverForEqual2 for handling panic to transaction_equal_clone_test.go * [NOD-1576] Full coverage of transaction equal unit test * [NOD-1576] Add expects panic * [NOD-1576] Allow composites in go vet * [NOD-1576] Code review fixes (#1223) * [NOD-1576] Code review fixes * [NOD-1576] Code review fixes part 2 * [NOD-1576] Fix wrong name Co-authored-by: karim1king <karimkaspersky@yahoo.com> Co-authored-by: Ori Newman <orinewman1@gmail.com> Co-authored-by: Karim <karim1king@users.noreply.github.com> * Fix merge errors * Use Equal where possible * Use Equal where possible * Use Equal where possible Co-authored-by: andrey-hash <74914043+andrey-hash@users.noreply.github.com> Co-authored-by: karim1king <karimkaspersky@yahoo.com> Co-authored-by: Karim <karim1king@users.noreply.github.com>
108 lines
3.6 KiB
Go
108 lines
3.6 KiB
Go
package handshake
|
|
|
|
import (
|
|
"github.com/kaspanet/kaspad/app/appmessage"
|
|
"github.com/kaspanet/kaspad/app/protocol/common"
|
|
peerpkg "github.com/kaspanet/kaspad/app/protocol/peer"
|
|
"github.com/kaspanet/kaspad/app/protocol/protocolerrors"
|
|
"github.com/kaspanet/kaspad/infrastructure/logger"
|
|
"github.com/kaspanet/kaspad/infrastructure/network/netadapter/router"
|
|
)
|
|
|
|
var (
|
|
// allowSelfConnections is only used to allow the tests to bypass the self
|
|
// connection detecting and disconnect logic since they intentionally
|
|
// do so for testing purposes.
|
|
allowSelfConnections bool
|
|
|
|
// minAcceptableProtocolVersion is the lowest protocol version that a
|
|
// connected peer may support.
|
|
minAcceptableProtocolVersion = appmessage.ProtocolVersion
|
|
)
|
|
|
|
type receiveVersionFlow struct {
|
|
HandleHandshakeContext
|
|
incomingRoute, outgoingRoute *router.Route
|
|
peer *peerpkg.Peer
|
|
}
|
|
|
|
// ReceiveVersion waits for the peer to send a version message, sends a
|
|
// verack in response, and updates its info accordingly.
|
|
func ReceiveVersion(context HandleHandshakeContext, incomingRoute *router.Route, outgoingRoute *router.Route,
|
|
peer *peerpkg.Peer) (*appmessage.NetAddress, error) {
|
|
|
|
flow := &receiveVersionFlow{
|
|
HandleHandshakeContext: context,
|
|
incomingRoute: incomingRoute,
|
|
outgoingRoute: outgoingRoute,
|
|
peer: peer,
|
|
}
|
|
|
|
return flow.start()
|
|
}
|
|
|
|
func (flow *receiveVersionFlow) start() (*appmessage.NetAddress, error) {
|
|
onEnd := logger.LogAndMeasureExecutionTime(log, "receiveVersionFlow.start()")
|
|
defer onEnd()
|
|
|
|
message, err := flow.incomingRoute.DequeueWithTimeout(common.DefaultTimeout)
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
|
|
log.Debugf("Got version message")
|
|
|
|
msgVersion, ok := message.(*appmessage.MsgVersion)
|
|
if !ok {
|
|
return nil, protocolerrors.New(true, "a version message must precede all others")
|
|
}
|
|
|
|
if !allowSelfConnections && flow.NetAdapter().ID().IsEqual(msgVersion.ID) {
|
|
return nil, protocolerrors.New(true, "connected to self")
|
|
}
|
|
|
|
// Disconnect and ban peers from a different network
|
|
if msgVersion.Network != flow.Config().ActiveNetParams.Name {
|
|
return nil, protocolerrors.Errorf(true, "wrong network")
|
|
}
|
|
|
|
// Notify and disconnect clients that have a protocol version that is
|
|
// too old.
|
|
//
|
|
// NOTE: If minAcceptableProtocolVersion is raised to be higher than
|
|
// appmessage.RejectVersion, this should send a reject packet before
|
|
// disconnecting.
|
|
if msgVersion.ProtocolVersion < minAcceptableProtocolVersion {
|
|
return nil, protocolerrors.Errorf(false, "protocol version must be %d or greater",
|
|
minAcceptableProtocolVersion)
|
|
}
|
|
|
|
// Disconnect from partial nodes in networks that don't allow them
|
|
if !flow.Config().ActiveNetParams.EnableNonNativeSubnetworks && msgVersion.SubnetworkID != nil {
|
|
return nil, protocolerrors.New(true, "partial nodes are not allowed")
|
|
}
|
|
|
|
// Disconnect if:
|
|
// - we are a full node and the outbound connection we've initiated is a partial node
|
|
// - the remote node is partial and our subnetwork doesn't match their subnetwork
|
|
localSubnetworkID := flow.Config().SubnetworkID
|
|
isLocalNodeFull := localSubnetworkID == nil
|
|
isRemoteNodeFull := msgVersion.SubnetworkID == nil
|
|
isOutbound := flow.peer.Connection().IsOutbound()
|
|
if (isLocalNodeFull && !isRemoteNodeFull && isOutbound) ||
|
|
(!isLocalNodeFull && !isRemoteNodeFull && !msgVersion.SubnetworkID.Equal(localSubnetworkID)) {
|
|
|
|
return nil, protocolerrors.New(false, "incompatible subnetworks")
|
|
}
|
|
|
|
flow.peer.UpdateFieldsFromMsgVersion(msgVersion)
|
|
err = flow.outgoingRoute.Enqueue(appmessage.NewMsgVerAck())
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
|
|
flow.peer.Connection().SetID(msgVersion.ID)
|
|
|
|
return msgVersion.Address, nil
|
|
}
|