routing: check for empty hops list
This commit fixes a crash that could be triggered by sending an empty hop list to the SendToRoute rpc.
This commit is contained in:
parent
4d647b6e5d
commit
b2cb760c65
@ -326,9 +326,12 @@ func newRoute(amtToSend, feeLimit lnwire.MilliSatoshi, sourceVertex Vertex,
|
||||
}
|
||||
|
||||
// With the base routing data expressed as hops, build the full route
|
||||
newRoute := NewRouteFromHops(
|
||||
newRoute, err := NewRouteFromHops(
|
||||
nextIncomingAmount, totalTimeLock, sourceVertex, hops,
|
||||
)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
// Invalidate this route if its total fees exceed our fee limit.
|
||||
if newRoute.TotalFees > feeLimit {
|
||||
@ -344,7 +347,11 @@ func newRoute(amtToSend, feeLimit lnwire.MilliSatoshi, sourceVertex Vertex,
|
||||
// information to perform the payment. It infers fee amounts and populates the
|
||||
// node, chan and prev/next hop maps.
|
||||
func NewRouteFromHops(amtToSend lnwire.MilliSatoshi, timeLock uint32,
|
||||
sourceVertex Vertex, hops []*Hop) *Route {
|
||||
sourceVertex Vertex, hops []*Hop) (*Route, error) {
|
||||
|
||||
if len(hops) == 0 {
|
||||
return nil, ErrNoRouteHopsProvided
|
||||
}
|
||||
|
||||
// First, we'll create a route struct and populate it with the fields
|
||||
// for which the values are provided as arguments of this function.
|
||||
@ -369,7 +376,7 @@ func NewRouteFromHops(amtToSend lnwire.MilliSatoshi, timeLock uint32,
|
||||
route.chanIndex[hop.ChannelID] = struct{}{}
|
||||
}
|
||||
|
||||
return route
|
||||
return route, nil
|
||||
}
|
||||
|
||||
// Vertex is a simple alias for the serialization of a compressed Bitcoin
|
||||
|
@ -1903,3 +1903,15 @@ func assertExpectedPath(t *testing.T, path []*channeldb.ChannelEdgePolicy,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// TestNewRouteFromEmptyHops tests that the NewRouteFromHops function returns an
|
||||
// error when the hop list is empty.
|
||||
func TestNewRouteFromEmptyHops(t *testing.T) {
|
||||
t.Parallel()
|
||||
|
||||
var source Vertex
|
||||
_, err := NewRouteFromHops(0, 0, source, []*Hop{})
|
||||
if err != ErrNoRouteHopsProvided {
|
||||
t.Fatalf("expected empty hops error: instead got: %v", err)
|
||||
}
|
||||
}
|
||||
|
@ -421,10 +421,13 @@ func TestChannelUpdateValidation(t *testing.T) {
|
||||
},
|
||||
}
|
||||
|
||||
route := NewRouteFromHops(
|
||||
route, err := NewRouteFromHops(
|
||||
lnwire.MilliSatoshi(10000), 100,
|
||||
NewVertex(ctx.aliases["a"]), hops,
|
||||
)
|
||||
if err != nil {
|
||||
t.Fatalf("unable to create route: %v", err)
|
||||
}
|
||||
|
||||
// Set up a channel update message with an invalid signature to be
|
||||
// returned to the sender.
|
||||
|
@ -3848,12 +3848,15 @@ func (r *rpcServer) unmarshallRoute(rpcroute *lnrpc.Route,
|
||||
prevNodePubKey = routeHop.PubKeyBytes
|
||||
}
|
||||
|
||||
route := routing.NewRouteFromHops(
|
||||
route, err := routing.NewRouteFromHops(
|
||||
lnwire.MilliSatoshi(rpcroute.TotalAmtMsat),
|
||||
rpcroute.TotalTimeLock,
|
||||
sourceNode.PubKeyBytes,
|
||||
hops,
|
||||
)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return route, nil
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user