github.com/jlmucb/cloudproxy@v0.0.0-20170830161738-b5aa0b619bc4/go/tao/acl_guard_test.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 "fmt" 19 "errors" 20 "io/ioutil" 21 "os" 22 "path" 23 "strconv" 24 "testing" 25 26 "github.com/golang/protobuf/proto" 27 "github.com/jlmucb/cloudproxy/go/tao/auth" 28 ) 29 30 func generateSigner() (*Signer, error) { 31 32 keyName := "TestSigningKey" 33 keyEpoch := int32(1) 34 keyPurpose := "signing" 35 keyStatus := "active" 36 keyType := SignerTypeFromSuiteName(TaoCryptoSuite) 37 if keyType == nil { 38 return nil, errors.New("unsupported sealer crypter") 39 } 40 ck := GenerateCryptoKey(*keyType, &keyName, &keyEpoch, &keyPurpose, &keyStatus) 41 if ck == nil { 42 return nil, errors.New("Can't generate signing key") 43 } 44 s := SignerFromCryptoKey(*ck) 45 if s == nil { 46 return nil, errors.New("Can't get signer from signing key") 47 } 48 return s, nil 49 } 50 51 func makeACLGuard() (*ACLGuard, *Keys, string, error) { 52 tmpDir, err := ioutil.TempDir("", "acl_guard_test") 53 if err != nil { 54 return nil, nil, "", 55 fmt.Errorf("Couldn't get a temp directory for the ACL guard test") 56 } 57 keys, err := NewTemporaryKeys(Signing) 58 if err != nil { 59 return nil, nil, "", err 60 } 61 62 config := ACLGuardDetails{ 63 SignedAclsPath: proto.String(path.Join(tmpDir, "acls")), 64 } 65 tg := NewACLGuard(keys.VerifyingKey, config) 66 67 // Add a bogus rule. 68 p := auth.NewKeyPrin([]byte(`Fake key`)) 69 if err := tg.Authorize(p, "Write", []string{"filename"}); err != nil { 70 return nil, nil, "", err 71 } 72 73 return tg.(*ACLGuard), keys, tmpDir, err 74 } 75 76 func testNewACLGuard(t *testing.T, v *Verifier) (Guard, string) { 77 tmpdir, err := ioutil.TempDir("/tmp", "acl_guard_test") 78 if err != nil { 79 t.Fatal("Couldn't get a temp directory for the new ACL guard:", err) 80 } 81 82 config := ACLGuardDetails{SignedAclsPath: proto.String(path.Join(tmpdir, "acls"))} 83 tg := NewACLGuard(v, config) 84 return tg, tmpdir 85 } 86 87 func TestACLGuardSaveACLs(t *testing.T) { 88 s, err := generateSigner() 89 if err != nil { 90 t.Fatal("Couldn't generate a signer") 91 } 92 93 tg, tmpdir := testNewACLGuard(t, s.GetVerifierFromSigner()) 94 defer os.RemoveAll(tmpdir) 95 96 p := auth.NewKeyPrin([]byte(`Fake key`)) 97 if err := tg.Authorize(p, "Write", []string{"filename"}); err != nil { 98 t.Fatal("Couldn't authorize a simple operation:", err) 99 } 100 101 if err := tg.Save(s); err != nil { 102 t.Fatal("Couldn't save the file") 103 } 104 105 config := ACLGuardDetails{SignedAclsPath: proto.String(path.Join(tmpdir, "acls"))} 106 v := s.GetVerifierFromSigner() 107 aclg, err := LoadACLGuard(v, config) 108 if err != nil { 109 t.Fatal("Couldn't load the ACLs:", err) 110 } 111 112 if aclg.RuleCount() != tg.RuleCount() { 113 t.Fatal("Wrong number of rules in loaded ACLGuard") 114 } 115 116 if aclg.String() != tg.String() { 117 t.Fatal("Wrong string representation of loaded ACLGuard") 118 } 119 } 120 121 func TestACLGuardEmptySave(t *testing.T) { 122 s, err := generateSigner() 123 if err != nil { 124 t.Fatal("Couldn't generate a signer") 125 } 126 127 tg, tmpdir := testNewACLGuard(t, s.GetVerifierFromSigner()) 128 defer os.RemoveAll(tmpdir) 129 130 if err := tg.Save(s); err != nil { 131 t.Fatal("Couldn't save the file") 132 } 133 134 config := ACLGuardDetails{SignedAclsPath: proto.String(path.Join(tmpdir, "acls"))} 135 v := s.GetVerifierFromSigner() 136 aclg, err := LoadACLGuard(v, config) 137 if err != nil { 138 t.Fatal("Couldn't load the ACLs:", err) 139 } 140 141 if aclg.RuleCount() != tg.RuleCount() { 142 t.Fatal("Wrong number of rules in loaded ACLGuard") 143 } 144 145 if aclg.String() != tg.String() { 146 t.Fatal("Wrong string representation of loaded ACLGuard") 147 } 148 } 149 150 func TestACLGuardAuthorize(t *testing.T) { 151 s, err := generateSigner() 152 if err != nil { 153 t.Fatal("Couldn't generate a signer") 154 } 155 156 tg, tmpdir := testNewACLGuard(t, s.GetVerifierFromSigner()) 157 defer os.RemoveAll(tmpdir) 158 159 p := auth.NewKeyPrin([]byte(`Fake key`)) 160 if err := tg.Authorize(p, "Write", []string{"filename"}); err != nil { 161 t.Fatal("Couldn't authorize a simple operation:", err) 162 } 163 164 if !tg.IsAuthorized(p, "Write", []string{"filename"}) { 165 t.Fatal("A rule that was added to the ACL was not present") 166 } 167 168 if tg.IsAuthorized(p, "Write", []string{"file"}) { 169 t.Fatal("A rule was authorized even though it has the wrong file name") 170 } 171 172 if tg.IsAuthorized(p, "Read", []string{"filename"}) { 173 t.Fatal("A rule was authorized even though it has the wrong op") 174 } 175 176 if tg.IsAuthorized(auth.Prin{}, "Write", []string{"filename"}) { 177 t.Fatal("A rule was authorized even though it has the wrong principal") 178 } 179 180 if err := tg.Retract(p, "Write", []string{"filename"}); err != nil { 181 t.Fatal("Couldn't retract an existing rule:", err) 182 } 183 184 if tg.IsAuthorized(p, "Write", []string{"filename"}) { 185 t.Fatal("A rule was still authorized after it was retracted") 186 } 187 } 188 189 func TestACLGuardDoubleAuthorize(t *testing.T) { 190 s, err := generateSigner() 191 if err != nil { 192 t.Fatal("Couldn't generate a signer") 193 } 194 195 tg, tmpdir := testNewACLGuard(t, s.GetVerifierFromSigner()) 196 defer os.RemoveAll(tmpdir) 197 198 p := auth.NewKeyPrin([]byte(`Fake key`)) 199 if err := tg.Authorize(p, "Write", []string{"filename"}); err != nil { 200 t.Fatal("Couldn't authorize a simple operation:", err) 201 } 202 203 // So nice, we authorize it twice. 204 if err := tg.Authorize(p, "Write", []string{"filename"}); err != nil { 205 t.Fatal("Couldn't authorize a simple operation:", err) 206 } 207 208 if !tg.IsAuthorized(p, "Write", []string{"filename"}) { 209 t.Fatal("A rule that was added to the ACL was not present") 210 } 211 212 if err := tg.Retract(p, "Write", []string{"filename"}); err != nil { 213 t.Fatal("Couldn't retract an existing double-added rule:", err) 214 } 215 216 if tg.IsAuthorized(p, "Write", []string{"filename"}) { 217 t.Fatal("A rule was still authorized after it was retracted") 218 } 219 } 220 221 func TestACLGuardAddRule(t *testing.T) { 222 s, err := generateSigner() 223 if err != nil { 224 t.Fatal("Couldn't generate a signer") 225 } 226 227 tg, tmpdir := testNewACLGuard(t, s.GetVerifierFromSigner()) 228 defer os.RemoveAll(tmpdir) 229 230 if err := tg.AddRule("Fake rule"); err != nil { 231 t.Fatal("Couldn't add a fake rule to the ACL") 232 } 233 234 ret, err := tg.Query("Fake rule") 235 if err != nil { 236 t.Fatal("Couldn't query a fake rule from the ACLGuard:", err) 237 } 238 239 if !ret { 240 t.Fatal("ACLGuard.Query did not return true for a rule that was added by AddRule") 241 } 242 243 if err := tg.Clear(); err != nil { 244 t.Fatal("Couldn't clear the ACLGuard:", err) 245 } 246 247 ret, err = tg.Query("Fake rule") 248 if err != nil { 249 t.Fatal("Couldn't query a fake rule after clearing the ACLGuard:", err) 250 } 251 252 if ret { 253 t.Fatal("ACLGuard.Query returned true for a rule after clearing the ACLGuard") 254 } 255 } 256 257 func TestACLGuardRetractRule(t *testing.T) { 258 s, err := generateSigner() 259 if err != nil { 260 t.Fatal("Couldn't generate a signer") 261 } 262 263 tg, tmpdir := testNewACLGuard(t, s.GetVerifierFromSigner()) 264 defer os.RemoveAll(tmpdir) 265 266 if err := tg.AddRule("Fake rule"); err != nil { 267 t.Fatal("Couldn't add a fake rule to the ACL") 268 } 269 270 ret, err := tg.Query("Fake rule") 271 if err != nil { 272 t.Fatal("Couldn't query a fake rule from the ACLGuard:", err) 273 } 274 275 if !ret { 276 t.Fatal("ACLGuard.Query did not return true for a rule that was added by AddRule") 277 } 278 279 if err := tg.RetractRule("Fake rule"); err != nil { 280 t.Fatal("Couldn't clear the ACLGuard:", err) 281 } 282 283 ret, err = tg.Query("Fake rule") 284 if err != nil { 285 t.Fatal("Couldn't query a fake rule after clearing the ACLGuard:", err) 286 } 287 288 if ret { 289 t.Fatal("ACLGuard.Query returned true for a rule after retracting the rule") 290 } 291 } 292 293 func TestACLGuardRuleCount(t *testing.T) { 294 s, err := generateSigner() 295 if err != nil { 296 t.Fatal("Couldn't generate a signer") 297 } 298 299 tg, tmpdir := testNewACLGuard(t, s.GetVerifierFromSigner()) 300 defer os.RemoveAll(tmpdir) 301 302 count := 20 303 for i := 0; i < count; i++ { 304 if err := tg.AddRule(strconv.Itoa(i)); err != nil { 305 t.Fatal("Couldn't add a rule that was a single integer as a string:", err) 306 } 307 } 308 309 if tg.RuleCount() != count { 310 t.Fatal("Wrong rule count after adding 20 rules") 311 } 312 313 // add the same rule again and make sure the RuleCount goes up. 314 if err := tg.AddRule("0"); err != nil { 315 t.Fatal("Couldn't add the same rule twice to the list:", err) 316 } 317 318 if tg.RuleCount() != count+1 { 319 t.Fatal("Wrong rule count after adding a rule twice") 320 } 321 322 if err := tg.RetractRule("0"); err != nil { 323 t.Fatal("Couldn't retract a rule that had been added twice:", err) 324 } 325 326 if tg.RuleCount() != count-1 { 327 t.Fatal("Wrong rule count after removing a rule that had been added twice") 328 } 329 } 330 331 func TestACLGuardGetRule(t *testing.T) { 332 s, err := generateSigner() 333 if err != nil { 334 t.Fatal("Couldn't generate a signer") 335 } 336 337 tg, tmpdir := testNewACLGuard(t, s.GetVerifierFromSigner()) 338 defer os.RemoveAll(tmpdir) 339 340 count := 20 341 for i := 0; i < count; i++ { 342 if err := tg.AddRule(strconv.Itoa(i)); err != nil { 343 t.Fatal("Couldn't add a rule that was a single integer as a string:", err) 344 } 345 } 346 347 if tg.GetRule(0) != "0" { 348 t.Fatal("Got the wrong rule from GetRule") 349 } 350 351 if tg.GetRule(200) != "" { 352 t.Fatal("Got a non-empty rule string for a non-existent rule") 353 } 354 355 if tg.GetRule(-1) != "" { 356 t.Fatal("Got a non-empty rule string for a negative rule index") 357 } 358 } 359 360 func TestACLGuardRuleDebugString(t *testing.T) { 361 s, err := generateSigner() 362 if err != nil { 363 t.Fatal("Couldn't generate a signer") 364 } 365 366 tg, tmpdir := testNewACLGuard(t, s.GetVerifierFromSigner()) 367 defer os.RemoveAll(tmpdir) 368 369 count := 20 370 for i := 0; i < count; i++ { 371 if err := tg.AddRule(strconv.Itoa(i)); err != nil { 372 t.Fatal("Couldn't add a rule that was a single integer as a string:", err) 373 } 374 } 375 376 if tg.RuleDebugString(0) != "0" { 377 t.Fatal("Got the wrong rule from GetRule") 378 } 379 380 if tg.RuleDebugString(200) != "" { 381 t.Fatal("Got a non-empty rule string for a non-existent rule") 382 } 383 384 if tg.RuleDebugString(-1) != "" { 385 t.Fatal("Got a non-empty rule string for a negative rule index") 386 } 387 } 388 389 func TestACLGuardString(t *testing.T) { 390 s, err := generateSigner() 391 if err != nil { 392 t.Fatal("Couldn't generate a signer") 393 } 394 395 tg, tmpdir := testNewACLGuard(t, s.GetVerifierFromSigner()) 396 defer os.RemoveAll(tmpdir) 397 398 if err := tg.AddRule("0"); err != nil { 399 t.Fatal("Couldn't add a rule that was a single integer as a string:", err) 400 } 401 402 ss := "ACLGuard{\n0\n}" 403 if tg.String() != ss { 404 t.Fatalf("Got the wrong string representation of the ACLGuard: expected '%s', but got '%s'", tg.String(), ss) 405 } 406 } 407 408 func TestACLGuardSignedSubprincipal(t *testing.T) { 409 s, err := generateSigner() 410 if err != nil { 411 t.Fatal("Couldn't generate a signer") 412 } 413 414 tg, tmpdir := testNewACLGuard(t, s.GetVerifierFromSigner()) 415 defer os.RemoveAll(tmpdir) 416 417 p := auth.NewKeyPrin([]byte(`Fake key`)) 418 if err := tg.Authorize(p, "Write", []string{"filename"}); err != nil { 419 t.Fatal("Couldn't authorize a simple operation:", err) 420 } 421 name := tg.Subprincipal().String() 422 k := s.ToPrincipal().String() 423 if name != ".ACLGuard("+k+")" { 424 t.Fatalf("ACL guard has wrong name: %v", name) 425 } 426 } 427 428 func TestACLGuardUnsignedSubprincipal(t *testing.T) { 429 g := NewACLGuard(nil, ACLGuardDetails{}) 430 err := g.Authorize(subj, "read", []string{"somefile"}) 431 if err != nil { 432 t.Fatal(err) 433 } 434 name := g.Subprincipal().String() 435 if name != ".ACLGuard([3ba9dc4681ad463d830d98e4a7c98c4fc909cce061cca19d1c9831ea1d9f5f48])" { 436 t.Fatalf("ACL guard has wrong name: %v", name) 437 } 438 }