rpcserver: allow to bake macaroons for specific URIs

To support the new URI specific permissions, we allow them to be added
in the BakeMacaroon call.
This commit is contained in:
Oliver Gugger 2020-09-04 09:22:36 +02:00
parent 6d201ef4fc
commit 84879fddc6
No known key found for this signature in database
GPG Key ID: 8E4256593F177720

@ -193,6 +193,7 @@ var (
validEntities = []string{ validEntities = []string{
"onchain", "offchain", "address", "message", "onchain", "offchain", "address", "message",
"peers", "info", "invoices", "signer", "macaroon", "peers", "info", "invoices", "signer", "macaroon",
macaroons.PermissionEntityCustomURI,
} }
// If the --no-macaroons flag is used to start lnd, the macaroon service // If the --no-macaroons flag is used to start lnd, the macaroon service
@ -525,6 +526,10 @@ type rpcServer struct {
// selfNode is our own pubkey. // selfNode is our own pubkey.
selfNode route.Vertex selfNode route.Vertex
// allPermissions is a map of all registered gRPC URIs (including
// internal and external subservers) to the permissions they require.
allPermissions map[string][]bakery.Op
} }
// A compile time check to ensure that rpcServer fully implements the // A compile time check to ensure that rpcServer fully implements the
@ -732,6 +737,7 @@ func newRPCServer(cfg *Config, s *server, macService *macaroons.Service,
quit: make(chan struct{}, 1), quit: make(chan struct{}, 1),
macService: macService, macService: macService,
selfNode: selfNode.PubKeyBytes, selfNode: selfNode.PubKeyBytes,
allPermissions: permissions,
} }
lnrpc.RegisterLightningServer(grpcServer, rootRPCServer) lnrpc.RegisterLightningServer(grpcServer, rootRPCServer)
@ -6452,15 +6458,27 @@ func (r *rpcServer) BakeMacaroon(ctx context.Context,
// the bakery. // the bakery.
requestedPermissions := make([]bakery.Op, len(req.Permissions)) requestedPermissions := make([]bakery.Op, len(req.Permissions))
for idx, op := range req.Permissions { for idx, op := range req.Permissions {
if !stringInSlice(op.Action, validActions) {
return nil, fmt.Errorf("invalid permission action. %s",
helpMsg)
}
if !stringInSlice(op.Entity, validEntities) { if !stringInSlice(op.Entity, validEntities) {
return nil, fmt.Errorf("invalid permission entity. %s", return nil, fmt.Errorf("invalid permission entity. %s",
helpMsg) helpMsg)
} }
// Either we have the special entity "uri" which specifies a
// full gRPC URI or we have one of the pre-defined actions.
if op.Entity == macaroons.PermissionEntityCustomURI {
_, ok := r.allPermissions[op.Action]
if !ok {
return nil, fmt.Errorf("invalid permission " +
"action, must be an existing URI in " +
"the format /package.Service/" +
"MethodName")
}
} else if !stringInSlice(op.Action, validActions) {
return nil, fmt.Errorf("invalid permission action. %s",
helpMsg)
}
requestedPermissions[idx] = bakery.Op{ requestedPermissions[idx] = bakery.Op{
Entity: op.Entity, Entity: op.Entity,
Action: op.Action, Action: op.Action,