1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104
|
package verify
import (
"github.com/theupdateframework/go-tuf/data"
"github.com/theupdateframework/go-tuf/internal/roles"
"github.com/theupdateframework/go-tuf/pkg/keys"
)
type Role struct {
KeyIDs map[string]struct{}
Threshold int
}
func (r *Role) ValidKey(id string) bool {
_, ok := r.KeyIDs[id]
return ok
}
type DB struct {
roles map[string]*Role
verifiers map[string]keys.Verifier
}
func NewDB() *DB {
return &DB{
roles: make(map[string]*Role),
verifiers: make(map[string]keys.Verifier),
}
}
// NewDBFromDelegations returns a DB that verifies delegations
// of a given Targets.
func NewDBFromDelegations(d *data.Delegations) (*DB, error) {
db := &DB{
roles: make(map[string]*Role, len(d.Roles)),
verifiers: make(map[string]keys.Verifier, len(d.Keys)),
}
for _, r := range d.Roles {
if _, ok := roles.TopLevelRoles[r.Name]; ok {
return nil, ErrInvalidDelegatedRole
}
role := &data.Role{Threshold: r.Threshold, KeyIDs: r.KeyIDs}
if err := db.AddRole(r.Name, role); err != nil {
return nil, err
}
}
for id, k := range d.Keys {
if err := db.AddKey(id, k); err != nil {
return nil, err
}
}
return db, nil
}
func (db *DB) AddKey(id string, k *data.PublicKey) error {
verifier, err := keys.GetVerifier(k)
if err != nil {
return err // ErrInvalidKey
}
// TUF is considering in TAP-12 removing the
// requirement that the keyid hash algorithm be derived
// from the public key. So to be forwards compatible,
// we allow any key ID, rather than checking k.ContainsID(id)
//
// AddKey should be idempotent, so we allow re-adding the same PublicKey.
//
// TAP-12: https://github.com/theupdateframework/taps/blob/master/tap12.md
if oldVerifier, exists := db.verifiers[id]; exists && oldVerifier.Public() != verifier.Public() {
return ErrRepeatID{id}
}
db.verifiers[id] = verifier
return nil
}
func (db *DB) AddRole(name string, r *data.Role) error {
if r.Threshold < 1 {
return ErrInvalidThreshold
}
role := &Role{
KeyIDs: make(map[string]struct{}),
Threshold: r.Threshold,
}
for _, id := range r.KeyIDs {
role.KeyIDs[id] = struct{}{}
}
db.roles[name] = role
return nil
}
func (db *DB) GetVerifier(id string) (keys.Verifier, error) {
k, ok := db.verifiers[id]
if !ok {
return nil, ErrMissingKey
}
return k, nil
}
func (db *DB) GetRole(name string) *Role {
return db.roles[name]
}
|