internal/pkg: optionally force implementation entry

For validation of build determinism.

Signed-off-by: Ophestra <cat@gensokyo.uk>
This commit is contained in:
2026-07-08 15:26:42 +09:00
parent 3c6e9b3d05
commit 472849cfd6
2 changed files with 50 additions and 10 deletions
+10 -1
View File
@@ -696,6 +696,7 @@ func main() {
flagNoReply bool flagNoReply bool
flagFaults bool flagFaults bool
flagPop bool flagPop bool
flagRebuild bool
flagBoot bool flagBoot bool
flagStd bool flagStd bool
@@ -724,7 +725,11 @@ func main() {
default: default:
var pathname *check.Absolute var pathname *check.Absolute
err := cm.Do(func(cache *pkg.Cache) (err error) { err := cm.Do(func(cache *pkg.Cache) (err error) {
pathname, _, err = cache.Cure(a) if flagRebuild {
pathname, _, err = cache.CureNew(a)
} else {
pathname, _, err = cache.Cure(a)
}
return return
}) })
if err != nil { if err != nil {
@@ -885,6 +890,10 @@ func main() {
&flagPop, &flagPop,
"pop", command.BoolFlag(false), "pop", command.BoolFlag(false),
"Display and destroy the most recent fault entry", "Display and destroy the most recent fault entry",
).Flag(
&flagRebuild,
"rebuild", command.BoolFlag(false),
"Always enter the artifact implementation",
) )
} }
+40 -9
View File
@@ -6,6 +6,7 @@ import (
"bytes" "bytes"
"cmp" "cmp"
"context" "context"
"crypto/rand"
"crypto/sha512" "crypto/sha512"
"encoding/base64" "encoding/base64"
"encoding/binary" "encoding/binary"
@@ -303,7 +304,7 @@ func (c *common) Open(a Artifact) (r io.ReadCloser, err error) {
} }
var pathname *check.Absolute var pathname *check.Absolute
if pathname, _, _, err = c.cache.cure(a, true); err != nil { if pathname, _, _, err = c.cache.cure(a, true, false); err != nil {
return return
} }
@@ -1633,7 +1634,7 @@ func (c *Cache) Cure(a Artifact) (
return return
} }
pathname, checksum, _, err = c.cure(a, true) pathname, checksum, _, err = c.cure(a, true, false)
return return
} }
@@ -1651,7 +1652,29 @@ func (c *Cache) CureWhence(a Artifact) (
return return
} }
return c.cure(a, true) return c.cure(a, true, false)
}
// CureNew is like Cure, but always enters the implementation.
func (c *Cache) CureNew(a Artifact) (
pathname *check.Absolute,
checksum unique.Handle[Checksum],
err error,
) {
c.abortMu.RLock()
defer c.abortMu.RUnlock()
if err = c.toplevel.Load().ctx.Err(); err != nil {
return
}
var whence int
retry:
pathname, checksum, whence, err = c.cure(a, true, true)
if err != nil || whence == WNew {
return
}
goto retry
} }
// CureError wraps a non-nil error returned attempting to cure an [Artifact]. // CureError wraps a non-nil error returned attempting to cure an [Artifact].
@@ -2020,13 +2043,19 @@ func WhenceString(whence int) string {
// cure implements Cure without acquiring a read lock on abortMu. cure must not // cure implements Cure without acquiring a read lock on abortMu. cure must not
// be entered during Abort. // be entered during Abort.
func (c *Cache) cure(a Artifact, curesExempt bool) ( func (c *Cache) cure(a Artifact, curesExempt, rebuild bool) (
pathname *check.Absolute, pathname *check.Absolute,
checksum unique.Handle[Checksum], checksum unique.Handle[Checksum],
whence int, whence int,
err error, err error,
) { ) {
id := c.Ident(a) id := c.Ident(a)
if rebuild {
var v ID
_, _ = rand.Read(v[:])
id = unique.Make(v)
}
ids := Encode(id.Value()) ids := Encode(id.Value())
pathname = c.base.Append( pathname = c.base.Append(
dirIdentifier, dirIdentifier,
@@ -2354,7 +2383,7 @@ func (c *Cache) cure(a Artifact, curesExempt bool) (
substitutes, substitutes,
) )
if c.flags&CIgnoreSubstitutes == 0 { if !rebuild && c.flags&CIgnoreSubstitutes == 0 {
var substituteChecksum unique.Handle[Checksum] var substituteChecksum unique.Handle[Checksum]
substituteChecksum, err = c.loadSubstitute(substitute) substituteChecksum, err = c.loadSubstitute(substitute)
if err != nil { if err != nil {
@@ -2419,8 +2448,10 @@ func (c *Cache) cure(a Artifact, curesExempt bool) (
return return
} else if err = externStatus.Close(); err != nil { } else if err = externStatus.Close(); err != nil {
return return
} else if err = f.linkSubstitute(ids, substitutes); err != nil { } else if !rebuild {
return if err = f.linkSubstitute(ids, substitutes); err != nil {
return
}
} }
} }
return return
@@ -2432,7 +2463,7 @@ func (c *Cache) cure(a Artifact, curesExempt bool) (
err = ca.Cure(&f) err = ca.Cure(&f)
c.exitCure(a, curesExempt) c.exitCure(a, curesExempt)
if err == nil { if !rebuild && err == nil {
err = f.linkSubstitute(ids, substitutes) err = f.linkSubstitute(ids, substitutes)
} }
if err != nil { if err != nil {
@@ -2526,7 +2557,7 @@ func (pending *pendingArtifactDep) cure(c *Cache) {
defer pending.Done() defer pending.Done()
var err error var err error
pending.resP.pathname, pending.resP.checksum, _, err = c.cure(pending.a, false) pending.resP.pathname, pending.resP.checksum, _, err = c.cure(pending.a, false, false)
if err == nil { if err == nil {
return return
} }