mirror of
https://github.com/edgelesssys/constellation.git
synced 2025-07-28 09:44:08 -04:00
update state disk passphrase on activation
Signed-off-by: Malte Poll <mp@edgeless.systems>
This commit is contained in:
parent
1b6ecf27ee
commit
3ce3978063
11 changed files with 906 additions and 389 deletions
|
@ -16,18 +16,64 @@ import (
|
|||
kubeadm "k8s.io/kubernetes/cmd/kubeadm/app/apis/kubeadm/v1beta3"
|
||||
)
|
||||
|
||||
/*
|
||||
+-------------+ +-------+
|
||||
| coordinator | | node |
|
||||
+-------------+ +-------+
|
||||
| |
|
||||
| initial request |
|
||||
|-------------------->|
|
||||
| | -------------------------------------------\
|
||||
| |-| update state "NodeWaitingForClusterJoin" |
|
||||
| | |------------------------------------------|
|
||||
| | ------------\
|
||||
| |-| setup VPN |
|
||||
| | |-----------|
|
||||
| | ---------------------\
|
||||
| |-| persist node state |
|
||||
| | |--------------------|
|
||||
| |
|
||||
| state disk uuid |
|
||||
|<--------------------|
|
||||
------------------------\ | |
|
||||
| derive state disk key |-| |
|
||||
|-----------------------| | |
|
||||
| |
|
||||
| state disk key |
|
||||
|-------------------->|
|
||||
| | -------------------------------\
|
||||
| |-| update state disk passphrase |
|
||||
| | |------------------------------|
|
||||
| |
|
||||
| VPN public key |
|
||||
|<--------------------|
|
||||
| |
|
||||
*/
|
||||
|
||||
// ActivateAsNode is the RPC call to activate a Node.
|
||||
func (a *API) ActivateAsNode(ctx context.Context, in *pubproto.ActivateAsNodeRequest) (resp *pubproto.ActivateAsNodeResponse, reterr error) {
|
||||
func (a *API) ActivateAsNode(stream pubproto.API_ActivateAsNodeServer) (reterr error) {
|
||||
a.mut.Lock()
|
||||
defer a.mut.Unlock()
|
||||
|
||||
if err := a.core.RequireState(state.AcceptingInit); err != nil {
|
||||
return nil, status.Errorf(codes.FailedPrecondition, "node is not in required state for activation: %v", err)
|
||||
return status.Errorf(codes.FailedPrecondition, "node is not in required state for activation: %v", err)
|
||||
}
|
||||
|
||||
/*
|
||||
coordinator -> initial request -> node
|
||||
*/
|
||||
message, err := stream.Recv()
|
||||
if err != nil {
|
||||
return status.Errorf(codes.Internal, "could not receive initial request from coordinator: %v", err)
|
||||
}
|
||||
initialRequest, ok := message.GetRequest().(*pubproto.ActivateAsNodeRequest_InitialRequest)
|
||||
if !ok {
|
||||
return status.Error(codes.Internal, "expected initial request but got different message type")
|
||||
}
|
||||
in := initialRequest.InitialRequest
|
||||
if len(in.OwnerId) == 0 || len(in.ClusterId) == 0 {
|
||||
a.logger.Error("missing data to taint worker node as initialized")
|
||||
return nil, status.Error(codes.InvalidArgument, "missing data to taint worker node as initialized")
|
||||
return status.Error(codes.InvalidArgument, "missing data to taint worker node as initialized")
|
||||
}
|
||||
|
||||
// If any of the following actions fail, we cannot revert.
|
||||
|
@ -42,33 +88,75 @@ func (a *API) ActivateAsNode(ctx context.Context, in *pubproto.ActivateAsNodeReq
|
|||
// This ensures the node is marked as initialzed before the node is in a state that allows code execution
|
||||
// Any new additions to ActivateAsNode MUST come after
|
||||
if err := a.core.AdvanceState(state.NodeWaitingForClusterJoin, in.OwnerId, in.ClusterId); err != nil {
|
||||
return nil, status.Errorf(codes.Internal, "advance node state: %v", err)
|
||||
return status.Errorf(codes.Internal, "advance node state: %v", err)
|
||||
}
|
||||
|
||||
vpnPubKey, err := a.core.GetVPNPubKey()
|
||||
if err != nil {
|
||||
return nil, status.Errorf(codes.Internal, "get vpn publicKey: %v", err)
|
||||
return status.Errorf(codes.Internal, "get vpn publicKey: %v", err)
|
||||
}
|
||||
|
||||
if err := a.core.SetVPNIP(in.NodeVpnIp); err != nil {
|
||||
return nil, status.Errorf(codes.Internal, "setting node vpn IP address: %v", err)
|
||||
return status.Errorf(codes.Internal, "setting node vpn IP address: %v", err)
|
||||
}
|
||||
|
||||
// add initial peers
|
||||
if err := a.core.UpdatePeers(peer.FromPubProto(in.Peers)); err != nil {
|
||||
return nil, status.Errorf(codes.Internal, "synchronizing peers with vpn state: %v", err)
|
||||
return status.Errorf(codes.Internal, "synchronizing peers with vpn state: %v", err)
|
||||
}
|
||||
|
||||
// persist node state on disk
|
||||
if err := a.core.PersistNodeState(role.Node, in.OwnerId, in.ClusterId); err != nil {
|
||||
return nil, status.Errorf(codes.Internal, "persist node state: %v", err)
|
||||
return status.Errorf(codes.Internal, "persist node state: %v", err)
|
||||
}
|
||||
|
||||
/*
|
||||
coordinator <- state disk uuid <- node
|
||||
*/
|
||||
diskUUID, err := a.core.GetDiskUUID()
|
||||
if err != nil {
|
||||
return status.Errorf(codes.Internal, "get disk uuid: %v", err)
|
||||
}
|
||||
if err := stream.Send(&pubproto.ActivateAsNodeResponse{
|
||||
Response: &pubproto.ActivateAsNodeResponse_StateDiskUuid{StateDiskUuid: diskUUID},
|
||||
}); err != nil {
|
||||
return status.Errorf(codes.Internal, "%v", err)
|
||||
}
|
||||
|
||||
/*
|
||||
coordinator -> state disk key -> node
|
||||
*/
|
||||
message, err = stream.Recv()
|
||||
if err != nil {
|
||||
return status.Errorf(codes.Internal, "could not receive state disk key from coordinator: %v", err)
|
||||
}
|
||||
diskKey, ok := message.GetRequest().(*pubproto.ActivateAsNodeRequest_StateDiskKey)
|
||||
if !ok {
|
||||
return status.Error(codes.Internal, "expected state disk key but got different message type")
|
||||
}
|
||||
if diskKey.StateDiskKey == nil {
|
||||
return status.Error(codes.Internal, "empty state disk key message from coordinator")
|
||||
}
|
||||
if err := a.core.UpdateDiskPassphrase(string(diskKey.StateDiskKey)); err != nil {
|
||||
return status.Errorf(codes.Internal, "%v", err)
|
||||
}
|
||||
|
||||
// regularly get (peer) updates from Coordinator
|
||||
a.wgClose.Add(1)
|
||||
go a.updateLoop()
|
||||
|
||||
return &pubproto.ActivateAsNodeResponse{NodeVpnPubKey: vpnPubKey}, nil
|
||||
/*
|
||||
coordinator <- VPN public key <- node
|
||||
*/
|
||||
if err := stream.Send(&pubproto.ActivateAsNodeResponse{
|
||||
Response: &pubproto.ActivateAsNodeResponse_NodeVpnPubKey{
|
||||
NodeVpnPubKey: vpnPubKey,
|
||||
},
|
||||
}); err != nil {
|
||||
return status.Errorf(codes.Internal, "%v", err)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// JoinCluster is the RPC call to request this node to join the cluster.
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue