carlos / platform Public

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

Plain git — no account needed to clone.

Download

Download this file

1package hostguard
2
3import (
4 "context"
5
6 "github.com/carlosframework/platform/internal/hostclaim"
7)
8
9// WithServingRetirement holds both root and shared host locks. Unlike Work,
10// retirement may precede installation of the newly admitted stamp. The callback
11// must authenticate the older installation and stop receipts before effects.
12// It must not call a lock-taking Guard or RootAuthority method.
13func (g Guard) WithServingRetirement(ctx context.Context, host string, current Captured, fn func(hostclaim.Observed, FenceView) error) error {
14 if ctx == nil || g.Root == nil || g.FenceView != nil || current.Incarnation == "" || current.Stamp == 0 || fn == nil {
15 return ErrInvalidInput
16 }
17 return g.locked(ctx, host, func(d *recordDir) error {
18 o, err := g.freshObserved(ctx, host)
19 if err != nil {
20 return err
21 }
22 c, h := o.Claim, o.Claim.Holder
23 if h.Incarnation != current.Incarnation || h.Stamp != current.Stamp || h.Session != current.Stamp || c.Op.Kind != hostclaim.KindServing || c.Op.ID != "" || c.Op.Phase != "" {
24 return ErrStampMismatch
25 }
26 r, err := d.read(host)
27 if err != nil {
28 return err
29 }
30 if r.quarantined || r.pendingInstallation != nil || r.barrier != nil {
31 return ErrFenced
32 }
33 if r.ActiveFence != nil {
34 completed := false
35 for _, receipt := range r.FenceJournal {
36 completed = completed || receipt.Target == *r.ActiveFence
37 }
38 if !completed || r.ActiveFence.Incarnation != current.Incarnation || r.ActiveFence.Stamp >= current.Stamp {
39 return ErrFenced
40 }
41 }
42 if r.Incarnation != current.Incarnation || r.ActiveStamp == 0 || r.ActiveStamp > current.Stamp {
43 return ErrStampMismatch
44 }
45 for _, retired := range r.rootRetired {
46 if retired == current {
47 return ErrRetiredStamp
48 }
49 }
50 for _, receipt := range r.FenceJournal {
51 if receipt.Target.matchesSession(c, current) {
52 return ErrFenced
53 }
54 }
55 view, err := g.Root.viewLocked(host, Captured{Incarnation: r.Incarnation, Stamp: r.ActiveStamp})
56 if err != nil {
57 return err
58 }
59 if err = view.validate(host, view.Captured); err != nil {
60 return err
61 }
62 if err = ctx.Err(); err != nil {
63 return err
64 }
65 return fn(o, view)
66 })
67}
68