github.com/jlmucb/cloudproxy@v0.0.0-20170830161738-b5aa0b619bc4/go/tao/stacked_host.go (about) 1 // Copyright (c) 2014, Google Inc. All rights reserved. 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 15 package tao 16 17 import ( 18 "github.com/golang/protobuf/proto" 19 "github.com/jlmucb/cloudproxy/go/tao/auth" 20 ) 21 22 // A StackedHost implements Host over an existing host Tao. 23 type StackedHost struct { 24 taoHostName auth.Prin 25 hostTao Tao 26 keys *Keys 27 } 28 29 // NewTaoStackedHostFromKeys takes ownership of an existing set of keys and 30 // returns a StackedHost that uses these keys over an existing host Tao. 31 func NewTaoStackedHostFromKeys(k *Keys, t Tao) (Host, error) { 32 n, err := t.GetTaoName() 33 if err != nil { 34 return nil, err 35 } 36 37 tsh := &StackedHost{ 38 keys: k, 39 taoHostName: n, 40 hostTao: t, 41 } 42 43 return tsh, nil 44 } 45 46 // NewTaoStackedHost generates a new StackedHost with a fresh set of temporary 47 // keys. 48 func NewTaoStackedHost(t Tao) (Host, error) { 49 k, err := NewTemporaryKeys(Signing | Crypting) 50 if err != nil { 51 return nil, err 52 } 53 54 return NewTaoStackedHostFromKeys(k, t) 55 } 56 57 // GetRandomBytes returns a slice of n random bytes. 58 func (t *StackedHost) GetRandomBytes(childSubprin auth.SubPrin, n int) (bytes []byte, err error) { 59 return t.hostTao.GetRandomBytes(n) 60 } 61 62 // GetSharedSecret returns a slice of n secret bytes. 63 func (t *StackedHost) GetSharedSecret(tag string, n int) (bytes []byte, err error) { 64 // TODO(tmroeder): this should be implemented using the underlying host 65 if t.keys.DerivingKey == nil { 66 return nil, newError("this StackedHost does not implement shared secrets") 67 } 68 69 // For now, all our key deriving with keys.DerivingKey uses a fixed 0-length salt. 70 var salt []byte 71 material := make([]byte, n) 72 if err := t.keys.DerivingKey.Derive(salt, []byte(tag), material); err != nil { 73 return nil, err 74 } 75 76 return material, nil 77 } 78 79 // Attest requests the Tao host sign a statement on behalf of the caller. 80 func (t *StackedHost) Attest(childSubprin auth.SubPrin, issuer *auth.Prin, 81 time, expiration *int64, message auth.Form) (*Attestation, error) { 82 83 child := t.taoHostName.MakeSubprincipal(childSubprin) 84 if issuer != nil { 85 if !auth.SubprinOrIdentical(*issuer, child) { 86 return nil, newError("invalid issuer in statement") 87 } 88 } else { 89 issuer = &child 90 } 91 92 if t.keys == nil || t.keys.SigningKey == nil { 93 return t.hostTao.Attest(issuer, time, expiration, message) 94 } 95 96 stmt := auth.Says{Speaker: *issuer, Time: time, Expiration: expiration, Message: message} 97 98 var d []byte 99 if t.keys.Delegation != nil { 100 var err error 101 d, err = proto.Marshal(t.keys.Delegation) 102 if err != nil { 103 return nil, err 104 } 105 } 106 107 return GenerateAttestation(t.keys.SigningKey, d, stmt) 108 } 109 110 // Encrypt data so that only this host can access it. 111 func (t *StackedHost) Encrypt(data []byte) (encrypted []byte, err error) { 112 if t.keys == nil || t.keys.CryptingKey == nil { 113 // TODO(tmroeder) (from TODO(kwalsh) in tao_stacked_host.cc): 114 // where should the policy come from here? 115 return t.hostTao.Seal(data, SealPolicyDefault) 116 } 117 118 return t.keys.CryptingKey.Encrypt(data) 119 } 120 121 // Decrypt data that only this host can access. 122 func (t *StackedHost) Decrypt(encrypted []byte) (data []byte, err error) { 123 if t.keys != nil && t.keys.CryptingKey != nil { 124 return t.keys.CryptingKey.Decrypt(encrypted) 125 } 126 127 // TODO(tmroeder) (from TODO(kwalsh) in tao_stacked_host.cc): 128 // where should the policy come from here? 129 var policy string 130 data, policy, err = t.hostTao.Unseal(encrypted) 131 if err != nil { 132 return nil, err 133 } 134 135 if policy != SealPolicyDefault { 136 return nil, newError("unsealed data with uncertain provenance") 137 } 138 139 return data, nil 140 } 141 142 // AddedHostedProgram notifies this Host that a new hosted program has been 143 // created. 144 func (t *StackedHost) AddedHostedProgram(childSubprin auth.SubPrin) error { 145 return nil 146 } 147 148 // RemovedHostedProgram notifies this Host that a hosted program has been 149 // killed. 150 func (t *StackedHost) RemovedHostedProgram(childSubprin auth.SubPrin) error { 151 return nil 152 } 153 154 // HostName gets the Tao principal name assigned to this hosted Tao host. 155 // The name encodes the full path from the root Tao, through all intermediary 156 // Tao hosts, to this hosted Tao host. 157 func (t *StackedHost) HostName() auth.Prin { 158 return t.taoHostName 159 } 160 161 func (s *StackedHost) InitCounter(label string, c int64) error { 162 return s.hostTao.InitCounter(label, c) 163 } 164 165 func (s *StackedHost) GetCounter(label string) (int64, error) { 166 return s.hostTao.GetCounter(label) 167 } 168 169 func (s *StackedHost) RollbackProtectedSeal(label string, data []byte, policy string) ([]byte, error) { 170 return s.hostTao.RollbackProtectedSeal(label, data, policy) 171 } 172 173 func (s *StackedHost) RollbackProtectedUnseal(sealed []byte) ([]byte, string, error) { 174 return s.hostTao.RollbackProtectedUnseal(sealed) 175 }