2023-01-18 22:32:23 +00:00
|
|
|
package client
|
|
|
|
|
|
|
|
import (
|
|
|
|
"encoding/json"
|
|
|
|
"fmt"
|
2023-01-24 11:03:08 +00:00
|
|
|
"strings"
|
2023-01-18 22:32:23 +00:00
|
|
|
|
|
|
|
"github.com/kairos-io/kairos-challenger/pkg/constants"
|
2023-01-24 11:03:08 +00:00
|
|
|
"github.com/kairos-io/kairos-challenger/pkg/payload"
|
2023-01-18 22:32:23 +00:00
|
|
|
|
|
|
|
"github.com/jaypipes/ghw/pkg/block"
|
|
|
|
"github.com/kairos-io/tpm-helpers"
|
|
|
|
"github.com/mudler/yip/pkg/utils"
|
|
|
|
"github.com/pkg/errors"
|
|
|
|
)
|
|
|
|
|
2023-01-19 14:24:39 +00:00
|
|
|
const DefaultNVIndex = "0x1500000"
|
|
|
|
|
2023-02-09 07:52:51 +00:00
|
|
|
func getPass(server, certificate string, partition *block.Partition) (string, bool, error) {
|
2023-01-18 22:32:23 +00:00
|
|
|
msg, err := tpm.Get(server,
|
2023-02-09 07:52:51 +00:00
|
|
|
tpm.WithCAs([]byte(certificate)),
|
2023-02-09 09:24:10 +00:00
|
|
|
tpm.AppendCustomCAToSystemCA,
|
2023-01-18 22:32:23 +00:00
|
|
|
tpm.WithAdditionalHeader("label", partition.Label),
|
|
|
|
tpm.WithAdditionalHeader("name", partition.Name),
|
|
|
|
tpm.WithAdditionalHeader("uuid", partition.UUID))
|
|
|
|
if err != nil {
|
|
|
|
return "", false, err
|
|
|
|
}
|
2023-01-24 11:03:08 +00:00
|
|
|
result := payload.Data{}
|
2023-01-18 22:32:23 +00:00
|
|
|
err = json.Unmarshal(msg, &result)
|
|
|
|
if err != nil {
|
|
|
|
return "", false, errors.Wrap(err, string(msg))
|
|
|
|
}
|
2023-01-24 11:03:08 +00:00
|
|
|
|
|
|
|
if result.HasPassphrase() {
|
|
|
|
return fmt.Sprint(result.Passphrase), result.HasBeenGenerated() && result.GeneratedBy == constants.TPMSecret, nil
|
|
|
|
} else if result.HasError() {
|
|
|
|
if strings.Contains(result.Error, "No secret found for") {
|
|
|
|
return "", false, errPartNotFound
|
|
|
|
}
|
2023-02-09 08:49:32 +00:00
|
|
|
if strings.Contains(result.Error, "x509: certificate signed by unknown authority") {
|
|
|
|
return "", false, errBadCertificate
|
|
|
|
}
|
2023-01-24 11:03:08 +00:00
|
|
|
return "", false, fmt.Errorf(result.Error)
|
2023-01-18 22:32:23 +00:00
|
|
|
}
|
2023-01-24 11:03:08 +00:00
|
|
|
|
2023-01-19 13:24:33 +00:00
|
|
|
return "", false, errPartNotFound
|
2023-01-18 22:32:23 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
func genAndStore(k Config) (string, error) {
|
|
|
|
opts := []tpm.TPMOption{}
|
2023-01-19 13:24:33 +00:00
|
|
|
if k.Kcrypt.Challenger.TPMDevice != "" {
|
|
|
|
opts = append(opts, tpm.WithDevice(k.Kcrypt.Challenger.TPMDevice))
|
2023-01-18 22:32:23 +00:00
|
|
|
}
|
2023-01-19 13:24:33 +00:00
|
|
|
if k.Kcrypt.Challenger.CIndex != "" {
|
|
|
|
opts = append(opts, tpm.WithIndex(k.Kcrypt.Challenger.CIndex))
|
2023-01-18 22:32:23 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
// Generate a new one, and return it to luks
|
|
|
|
rand := utils.RandomString(32)
|
2023-01-19 14:06:53 +00:00
|
|
|
blob, err := tpm.EncryptBlob([]byte(rand))
|
2023-01-18 22:32:23 +00:00
|
|
|
if err != nil {
|
|
|
|
return "", err
|
|
|
|
}
|
2023-01-19 14:24:39 +00:00
|
|
|
nvindex := DefaultNVIndex
|
2023-01-19 13:24:33 +00:00
|
|
|
if k.Kcrypt.Challenger.NVIndex != "" {
|
|
|
|
nvindex = k.Kcrypt.Challenger.NVIndex
|
2023-01-18 22:32:23 +00:00
|
|
|
}
|
|
|
|
opts = append(opts, tpm.WithIndex(nvindex))
|
|
|
|
return rand, tpm.StoreBlob(blob, opts...)
|
|
|
|
}
|
|
|
|
|
|
|
|
func localPass(k Config) (string, error) {
|
2023-01-19 14:24:39 +00:00
|
|
|
index := DefaultNVIndex
|
2023-01-19 13:24:33 +00:00
|
|
|
if k.Kcrypt.Challenger.NVIndex != "" {
|
|
|
|
index = k.Kcrypt.Challenger.NVIndex
|
2023-01-18 22:32:23 +00:00
|
|
|
}
|
|
|
|
opts := []tpm.TPMOption{tpm.WithIndex(index)}
|
2023-01-19 13:24:33 +00:00
|
|
|
if k.Kcrypt.Challenger.TPMDevice != "" {
|
|
|
|
opts = append(opts, tpm.WithDevice(k.Kcrypt.Challenger.TPMDevice))
|
2023-01-18 22:32:23 +00:00
|
|
|
}
|
|
|
|
encodedPass, err := tpm.ReadBlob(opts...)
|
|
|
|
if err != nil {
|
|
|
|
// Generate if we fail to read from the assigned blob
|
|
|
|
return genAndStore(k)
|
|
|
|
}
|
|
|
|
|
|
|
|
// Decode and give it back
|
|
|
|
opts = []tpm.TPMOption{}
|
2023-01-19 13:24:33 +00:00
|
|
|
if k.Kcrypt.Challenger.CIndex != "" {
|
|
|
|
opts = append(opts, tpm.WithIndex(k.Kcrypt.Challenger.CIndex))
|
2023-01-18 22:32:23 +00:00
|
|
|
}
|
2023-01-19 13:24:33 +00:00
|
|
|
if k.Kcrypt.Challenger.TPMDevice != "" {
|
|
|
|
opts = append(opts, tpm.WithDevice(k.Kcrypt.Challenger.TPMDevice))
|
2023-01-18 22:32:23 +00:00
|
|
|
}
|
2023-01-19 14:06:53 +00:00
|
|
|
pass, err := tpm.DecryptBlob(encodedPass, opts...)
|
2023-01-18 22:32:23 +00:00
|
|
|
return string(pass), err
|
|
|
|
}
|