mirror of
https://github.com/google/go-attestation.git
synced 2025-04-15 15:06:43 +00:00
Handle StartupLocality events
Systems with TXT enabled may issue the TPM2_Startup() command from a locality other than 0. In this case, the initial value of PCR0 will represent the locality that the call was made from. This is exposed to higher layers by an EV_NO_ACTION event that has data containing the NULL-terminated string "StartupLocality" followed by a single byte representing the state of the locality. As this event is EV_NO_ACTION, it does not represent an extension in itself. So: 1) Ignore events that are EV_NO_ACTION when replaying the log, except: 2) For PCR0, if an event is EV_NO_ACTION and contains the string "StartupLocality", use the final byte of the event data as the initial value of PCR0 for the replay.
This commit is contained in:
parent
5e360d3104
commit
fe22f29ec8
@ -25,6 +25,7 @@ import (
|
||||
"fmt"
|
||||
"io"
|
||||
"sort"
|
||||
"strings"
|
||||
|
||||
// Ensure hashes are available.
|
||||
_ "crypto/sha256"
|
||||
@ -287,7 +288,7 @@ func (a *AKPublic) validate20Quote(quote Quote, pcrs []PCR, nonce []byte) error
|
||||
return nil
|
||||
}
|
||||
|
||||
func extend(pcr PCR, replay []byte, e rawEvent) (pcrDigest []byte, eventDigest []byte, err error) {
|
||||
func extend(pcr PCR, replay []byte, e rawEvent, locality byte) (pcrDigest []byte, eventDigest []byte, err error) {
|
||||
h := pcr.DigestAlg
|
||||
|
||||
for _, digest := range e.digests {
|
||||
@ -295,13 +296,14 @@ func extend(pcr PCR, replay []byte, e rawEvent) (pcrDigest []byte, eventDigest [
|
||||
continue
|
||||
}
|
||||
if len(digest.data) != len(pcr.Digest) {
|
||||
return nil, nil, fmt.Errorf("digest data length (%d) doesn't match PCR digest length (%d)", len(digest.data), len(pcr.Digest));
|
||||
return nil, nil, fmt.Errorf("digest data length (%d) doesn't match PCR digest length (%d)", len(digest.data), len(pcr.Digest))
|
||||
}
|
||||
hash := h.New()
|
||||
if len(replay) != 0 {
|
||||
hash.Write(replay)
|
||||
} else {
|
||||
b := make([]byte, h.Size())
|
||||
b[h.Size()-1] = locality
|
||||
hash.Write(b)
|
||||
}
|
||||
hash.Write(digest.data)
|
||||
@ -318,14 +320,25 @@ func replayPCR(rawEvents []rawEvent, pcr PCR) ([]Event, bool) {
|
||||
var (
|
||||
replay []byte
|
||||
outEvents []Event
|
||||
locality byte
|
||||
)
|
||||
|
||||
for _, e := range rawEvents {
|
||||
if e.index != pcr.Index {
|
||||
continue
|
||||
}
|
||||
|
||||
replayValue, digest, err := extend(pcr, replay, e)
|
||||
// If TXT is enabled then the first event for PCR0
|
||||
// should be a StartupLocality event. The final byte
|
||||
// of this event indicates the locality from which
|
||||
// TPM2_Startup() was issued. The initial value of
|
||||
// PCR0 is equal to the locality.
|
||||
if e.typ == eventTypeNoAction {
|
||||
if pcr.Index == 0 && len(e.data) == 17 && strings.HasPrefix(string(e.data), "StartupLocality") {
|
||||
locality = e.data[len(e.data)-1]
|
||||
}
|
||||
continue
|
||||
}
|
||||
replayValue, digest, err := extend(pcr, replay, e, locality)
|
||||
if err != nil {
|
||||
return nil, false
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user