// Copyright 2015 The Vanadium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.

package signing

import "v.io/v23/security"

// A DataWithSignature represents a signed, and possibily validated, collection
// of Item structs.
//
// If IsValidated==false and the AuthorSigned signature is valid, it means:
//    The signer whose Blessings have hash BlessingsHash asserts Data.
//
// If IsValidated==true and both AuthorSigned and ValidatorSigned signatures are is valid,
// it means both:
// 1) The signer whose Blessings b have hash BlessingsHash asserts Data.
// 2) If vd is the ValidatorData with hash ValidatorDataHash, the owner of
//    vd.PublicKey asserts that it checked that at least the names vd.Names[] were
//    valid in b.
//
// The sender obtains:
// - BlessingsHash (and the wire form of the blessings) with ValidationCache.AddBlessings().  
// - ValidatorDataHash (and the wire form of the ValidataData)  with ValidationCache.AddValidatorData().
//
// The receiver looks up:
// - BlessingsHash with ValidationCache.LookupBlessingsData()
// - ValidatorDataHash with ValidationCache.LookupValidatorData()
//
// If not yet there, the receiver inserts the valus into its ValidationCache with:
// - ValidationCache.AddWireBlessings()
// - ValidationCache.AddValidatorData()
type DataWithSignature struct {
	Data          []Item
        // BlessingsHash is a key for the validation cache; the corresponding
        // cached value is a security.Blessings.
	BlessingsHash []byte
	// AuthorSigned is the signature of Data and BlessingsHash using the
	// private key associated with the blessings hashed in BlessingsHash.
	AuthorSigned  security.Signature

	IsValidated bool // Whether fields below are meaningful.

        // ValidatorDataHash is a key for the validation cache returned by
        // ValidatorData.Hash(); the corresponding cached value is the
        // ValidatorData.
	ValidatorDataHash []byte
	ValidatorSigned   security.Signature
}

// An Item represents either a marshalled data item or its SHA-256 hash.
// The Data field is a []byte, rather than an "any" to make signatures
// determistic.  VOM encoding is not deterministic for two reasons:
// - map elements may be marshalled in any order
// - different versions of VOM may marshal in different ways.
// Thus, the initial producer of a data item marshals the data once, and it is
// this marshalled form that is transmitted from device to device.  If the
// data were unmarshalled and then remarsahalled, the signatures might not
// match.  The Hash field is used instead of the Data field when the recipient
// of the DataWithSignature is not permitted to see certain Items' Data
// fields.
type Item union {
	Data []byte   // Marshalled form of data.
	Hash []byte   // Hash of what would have been in Data, as returned by SumByteVectorWithLength(Data).
}

// WireValidatorData is the wire form of ValidatorData.
// It excludes the unmarshalled form of the public key.
type WireValidatorData struct {
	Names               []string  // Names of valid signing blessings in the Blessings referred to by BlessingsHash.
	MarshalledPublicKey []byte    // PublicKey, marshalled with MarshalBinary().
}
