carlos / platform Public

Clone
git clone https://amadan.net/carlos/platform

Plain git — no account needed to clone.

Download

Download this file

1package host
2
3import (
4 "context"
5 "crypto/ed25519"
6 "crypto/rand"
7 "encoding/hex"
8 "net"
9 "net/http"
10 "os/exec"
11 "os/user"
12 "strconv"
13 "strings"
14 "time"
15
16 "github.com/carlosframework/platform/internal/hostbox"
17 "github.com/carlosframework/platform/internal/instancectl"
18)
19
20type StopControllerReader interface {
21 VerifiedController(context.Context, int) (string, error)
22}
23
24func NewProductionClaimStopHandler(c ClaimStopCoordinator, j hostbox.StopKernelJournalReader, controllers StopControllerReader, roots ...map[string]string) (http.Handler, error) {
25 if len(roots) != 1 || len(roots[0]) == 0 {
26 return nil, ErrClaimStopUnavailable
27 }
28 if len(c.EvidenceSigner) != ed25519.PrivateKeySize || c.RequestLimit != hostbox.RequestLimit || c.Claims == nil || c.Inventory == nil || c.Evidence == nil || j == nil || controllers == nil {
29 return nil, ErrClaimStopUnavailable
30 }
31 u, err := user.Lookup("carlos")
32 if err != nil {
33 return nil, err
34 }
35 uid, err := strconv.ParseUint(u.Uid, 10, 32)
36 if err != nil || uid == 0 {
37 return nil, ErrClaimStopIdentity
38 }
39 c.CarlosUID = uint32(uid)
40 c.Now = time.Now
41 c.NewID = func() string {
42 var b [16]byte
43 if _, err := rand.Read(b[:]); err != nil {
44 return ""
45 }
46 return hex.EncodeToString(b[:])
47 }
48 c.Kernel = newProductionStopKernel(j, roots[0], c.Guard.Root != nil)
49 authenticate := func(ctx context.Context, conn net.Conn) (StopPeer, error) {
50 ctx, cancel := context.WithTimeout(ctx, 3*time.Second)
51 defer cancel()
52 out, err := exec.CommandContext(ctx, "systemctl", "show", "-p", "MainPID", "--value", "carlos-edge.service").Output()
53 if err != nil {
54 return StopPeer{}, err
55 }
56 pid, err := strconv.Atoi(strings.TrimSpace(string(out)))
57 if err != nil || pid <= 0 {
58 return StopPeer{}, ErrClaimStopIdentity
59 }
60 controller, err := controllers.VerifiedController(ctx, pid)
61 if err != nil || controller == "" {
62 return StopPeer{}, ErrClaimStopIdentity
63 }
64 peer, err := instancectl.AuthenticatePeerTuple(conn, uint32(uid), pid, controller)
65 if err != nil {
66 return StopPeer{}, err
67 }
68 return StopPeer{UID: peer.UID, PID: peer.PID, ProcessStart: peer.ProcessStart, BootID: peer.BootID, ControllerID: peer.ControllerID}, nil
69 }
70 return ClaimStopHTTP{Coordinator: c, Authenticate: authenticate}, nil
71}
72