Commit e829d72e authored by Sietse Ringers's avatar Sietse Ringers
Browse files

Add verify command to scheme manager tool

parent 1714ca89
......@@ -22,7 +22,7 @@ type SchemeManager struct {
XMLVersion int `xml:"version,attr"`
XMLName xml.Name `xml:"SchemeManager"`
index SchemeManagerIndex
Index SchemeManagerIndex `xml:"-"`
}
// Issuer describes an issuer.
......
......@@ -225,6 +225,9 @@ func iterateSubfolders(path string, handler func(string) error) error {
if !stat.IsDir() {
continue
}
if strings.HasSuffix(dir, "/.git") {
continue
}
err = handler(dir)
if err != nil {
return err
......@@ -513,15 +516,15 @@ func (conf *Configuration) ParseIndex(manager *SchemeManager, dir string) error
if err != nil {
return err
}
manager.index = make(map[string]ConfigurationFileHash)
return manager.index.FromString(string(indexbts))
manager.Index = make(map[string]ConfigurationFileHash)
return manager.Index.FromString(string(indexbts))
}
// ReadAuthenticatedFile reads the file at the specified path
// and verifies its authenticity by checking that the file hash
// is present in the (signed) scheme manager index file.
func (conf *Configuration) ReadAuthenticatedFile(manager *SchemeManager, path string) ([]byte, error) {
signedHash, ok := manager.index[path]
signedHash, ok := manager.Index[path]
if !ok {
return nil, errors.New("File not present in scheme manager index")
}
......@@ -533,7 +536,7 @@ func (conf *Configuration) ReadAuthenticatedFile(manager *SchemeManager, path st
computedHash := sha256.Sum256(bts)
if !bytes.Equal(computedHash[:], signedHash) {
return nil, errors.New("File hash invalid")
return nil, errors.Errorf("Hash of %s does not match scheme manager index", path)
}
return bts, nil
}
......@@ -541,7 +544,18 @@ func (conf *Configuration) ReadAuthenticatedFile(manager *SchemeManager, path st
// VerifySignature verifies the signature on the scheme manager index file
// (which contains the SHA256 hashes of all files under this scheme manager,
// which are used for verifying file authenticity).
func (conf *Configuration) VerifySignature(id SchemeManagerIdentifier) (bool, error) {
func (conf *Configuration) VerifySignature(id SchemeManagerIdentifier) (valid bool, err error) {
defer func() {
if r := recover(); r != nil {
valid = false
if e, ok := r.(error); ok {
err = errors.Errorf("Scheme manager index signature failed to verify: %s", e.Error())
} else {
err = errors.New("Scheme manager index signature failed to verify")
}
}
}()
dir := filepath.Join(conf.path, id.String())
if err := fs.AssertPathExists(dir+"/index", dir+"/index.sig", dir+"/pk.pem"); err != nil {
return false, errors.New("Missing scheme manager index file, signature, or public key")
......@@ -580,3 +594,7 @@ func (conf *Configuration) VerifySignature(id SchemeManagerIdentifier) (bool, er
// Verify signature
return ecdsa.Verify(pk, indexhash[:], ints[0], ints[1]), nil
}
func (hash ConfigurationFileHash) String() string {
return hex.EncodeToString(hash)
}
package cmd
import (
"path/filepath"
"fmt"
"github.com/credentials/irmago"
"github.com/go-errors/errors"
"github.com/spf13/cobra"
)
// verifyCmd represents the verify command
var verifyCmd = &cobra.Command{
Use: "verify irma_configuration_path",
Short: "Verify irma_configuration folder correctness and authenticity",
Long: `The verify command parses the specified irma_configuration folder and checks the signatures of the contained scheme managers.`,
Args: cobra.ExactArgs(1),
RunE: func(cmd *cobra.Command, args []string) error {
path, err := filepath.Abs(args[0])
if err != nil {
return err
}
if filepath.Base(path) != "irma_configuration" {
return errors.New("Path is not irma_configuration")
}
conf, err := irma.NewConfiguration(path, "")
if err != nil {
return err
}
if err := conf.ParseFolder(); err != nil {
return err
}
for _, manager := range conf.SchemeManagers {
for file := range manager.Index {
// Don't care about the actual bytes
if _, err := conf.ReadAuthenticatedFile(manager, file); err != nil {
return err
}
}
}
fmt.Println()
fmt.Println("irma_configuration parsed and authenticated successfully.")
return nil
},
}
func init() {
RootCmd.AddCommand(verifyCmd)
}
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment