github.com/keybase/client/go@v0.0.0-20241007131713-f10651d043c8/libkb/merkle_client.go (about) 1 // Copyright 2015 Keybase, Inc. All rights reserved. Use of 2 // this source code is governed by the included BSD license. 3 4 package libkb 5 6 import ( 7 "crypto/sha256" 8 "crypto/sha512" 9 "crypto/subtle" 10 "encoding/hex" 11 "encoding/json" 12 "errors" 13 "fmt" 14 "math" 15 "strings" 16 "sync" 17 "time" 18 19 chat1 "github.com/keybase/client/go/protocol/chat1" 20 keybase1 "github.com/keybase/client/go/protocol/keybase1" 21 jsonw "github.com/keybase/go-jsonw" 22 ) 23 24 const ( 25 NodeHashLenLong = sha512.Size // = 64 26 NodeHashLenShort = sha256.Size // = 32 27 ) 28 29 type NodeHash interface { 30 Check(s string) bool // Check if the node hashes to this string 31 String() string 32 bytes() []byte 33 IsNil() bool 34 Eq(h NodeHash) bool 35 } 36 37 type NodeHashShort [NodeHashLenShort]byte 38 type NodeHashLong [NodeHashLenLong]byte 39 40 // NodeHashAny incorporates either a short (256-bit) or a long (512-bit) hash. 41 // It's unfortunate we need it, but I didn't see any other way to use the 42 // Go json marshal/unmarshal system where the hashes might be either short 43 // or long. Our hacky solution is to have a union-type struct that supports 44 // both, and just to unmarshal into the relevant field. Note this 45 // type also fits ths NodeHash interface. 46 type NodeHashAny struct { 47 s *NodeHashShort 48 l *NodeHashLong 49 } 50 51 var _ NodeHash = NodeHashShort{} 52 var _ NodeHash = NodeHashLong{} 53 var _ NodeHash = NodeHashAny{} 54 55 func (h1 NodeHashShort) Check(s string) bool { 56 h2 := sha256.Sum256([]byte(s)) 57 return subtle.ConstantTimeCompare(h1[:], h2[:]) == 1 58 } 59 60 func (h1 NodeHashShort) String() string { 61 return hex.EncodeToString(h1[:]) 62 } 63 64 func (h1 NodeHashShort) bytes() []byte { 65 return h1[:] 66 } 67 68 func (h1 NodeHashShort) IsNil() bool { 69 return false 70 } 71 72 func (h1 NodeHashShort) Eq(h2 NodeHash) bool { 73 return subtle.ConstantTimeCompare(h1.bytes(), h2.bytes()) == 1 74 } 75 76 func (h1 NodeHashShort) ExportToHashMeta() keybase1.HashMeta { 77 return keybase1.HashMeta(h1.bytes()) 78 } 79 80 func (h1 NodeHashLong) Check(s string) bool { 81 h2 := sha512.Sum512([]byte(s)) 82 return subtle.ConstantTimeCompare(h1[:], h2[:]) == 1 83 } 84 85 func (h1 NodeHashLong) String() string { 86 return hex.EncodeToString(h1[:]) 87 } 88 89 func (h1 NodeHashLong) bytes() []byte { 90 return h1[:] 91 } 92 93 func (h1 NodeHashLong) IsNil() bool { 94 return false 95 } 96 97 func (h1 NodeHashLong) Eq(h2 NodeHash) bool { 98 return subtle.ConstantTimeCompare(h1.bytes(), h2.bytes()) == 1 99 } 100 101 func hashEq(h1 NodeHash, h2 NodeHash) bool { 102 b1 := h1.bytes() 103 b2 := h2.bytes() 104 return subtle.ConstantTimeCompare(b1, b2) == 1 105 } 106 107 func (h NodeHashAny) Check(s string) bool { 108 switch { 109 case h.s != nil: 110 return h.s.Check(s) 111 case h.l != nil: 112 return h.l.Check(s) 113 default: 114 return false 115 } 116 } 117 118 func (h NodeHashAny) String() string { 119 switch { 120 case h.s != nil: 121 return h.s.String() 122 case h.l != nil: 123 return h.l.String() 124 default: 125 return "" 126 } 127 } 128 129 func (h NodeHashAny) bytes() []byte { 130 switch { 131 case h.s != nil: 132 return h.s.bytes() 133 case h.l != nil: 134 return h.l.bytes() 135 default: 136 return nil 137 } 138 } 139 140 func (h NodeHashAny) Eq(h2 NodeHash) bool { 141 return subtle.ConstantTimeCompare(h.bytes(), h2.bytes()) == 1 142 } 143 144 func (h *NodeHashAny) UnmarshalJSON(b []byte) error { 145 s := keybase1.Unquote(b) 146 147 // empty strings are OK, to mean no hash available 148 if len(s) == 0 { 149 return nil 150 } 151 152 g, err := NodeHashFromHex(s) 153 if err != nil { 154 return err 155 } 156 switch g := g.(type) { 157 case NodeHashShort: 158 h.s = &g 159 case NodeHashLong: 160 h.l = &g 161 default: 162 return errors.New("unknown hash type") 163 } 164 return nil 165 } 166 167 func (h NodeHashAny) IsNil() bool { 168 return h.s == nil && h.l == nil 169 } 170 171 func (h1 *NodeHashShort) UnmarshalJSON(b []byte) error { 172 s := keybase1.Unquote(b) 173 // empty strings are OK, to mean no hash available 174 if len(s) == 0 { 175 return nil 176 } 177 g, err := NodeHashFromHex(s) 178 if err != nil { 179 return err 180 } 181 if ret, ok := g.(NodeHashShort); ok { 182 *h1 = ret 183 return nil 184 } 185 return errors.New("bad SHA256 hash") 186 } 187 188 func (h1 *NodeHashLong) UnmarshalJSON(b []byte) error { 189 s := keybase1.Unquote(b) 190 // empty strings are OK, to mean no hash available 191 if len(s) == 0 { 192 return nil 193 } 194 g, err := NodeHashFromHex(s) 195 if err != nil { 196 return err 197 } 198 if ret, ok := g.(NodeHashLong); ok { 199 *h1 = ret 200 return nil 201 } 202 return errors.New("bad SHA512hash") 203 } 204 205 func (h *NodeHashAny) MarshalJSON() ([]byte, error) { 206 s := h.String() 207 if len(s) == 0 { 208 return nil, nil 209 } 210 return keybase1.Quote(s), nil 211 } 212 213 type MerkleClientInterface interface { 214 CanExamineHistoricalRoot(m MetaContext, q keybase1.Seqno) bool 215 FetchRootFromServerByMinSeqno(m MetaContext, lowerBound keybase1.Seqno) (mr *MerkleRoot, err error) 216 FetchRootFromServer(m MetaContext, freshness time.Duration) (mr *MerkleRoot, err error) 217 FirstExaminableHistoricalRoot(m MetaContext) *keybase1.Seqno 218 FirstMainRootWithHiddenRootHash(m MetaContext) (s keybase1.Seqno, err error) 219 LastRoot(m MetaContext) *MerkleRoot 220 LastRootToSigJSON(m MetaContext) (ret *jsonw.Wrapper, err error) 221 LookupLeafAtHashMeta(m MetaContext, leafID keybase1.UserOrTeamID, hm keybase1.HashMeta) (leaf *MerkleGenericLeaf, err error) 222 LookupLeafAtSeqno(m MetaContext, leafID keybase1.UserOrTeamID, s keybase1.Seqno) (leaf *MerkleGenericLeaf, root *MerkleRoot, err error) 223 LookupLeafAtSeqnoForAudit(m MetaContext, leafID keybase1.UserOrTeamID, s keybase1.Seqno, processHiddenRespFunc ProcessHiddenRespFunc) (leaf *MerkleGenericLeaf, root *MerkleRoot, hiddenResp *MerkleHiddenResponse, err error) 224 LookupRootAtSeqno(m MetaContext, s keybase1.Seqno) (root *MerkleRoot, err error) 225 LookupTeam(m MetaContext, teamID keybase1.TeamID) (leaf *MerkleTeamLeaf, err error) 226 LookupTeamWithHidden(m MetaContext, teamID keybase1.TeamID, processHiddenRespFunc ProcessHiddenRespFunc) (leaf *MerkleTeamLeaf, hiddenResp *MerkleHiddenResponse, lastMerkleRoot *MerkleRoot, err error) 227 LookupUser(m MetaContext, q HTTPArgs, sigHints *SigHints, opts MerkleOpts) (u *MerkleUserLeaf, err error) 228 } 229 230 type MerkleClient struct { 231 Contextified 232 233 // protects whole object 234 // 235 // Warning: Never grab the latestRootLock while holding this lock, as the 236 // opposite happens and so you might introduce deadlocks. 237 sync.RWMutex 238 239 keyring *SpecialKeyRing 240 241 // The most recently-available root 242 lastRoot *MerkleRoot 243 244 // The first node we saw that has skip pointers; not used in production 245 firstSkip *keybase1.Seqno 246 247 // The first merkle root that contains the root of the hidden merkle tree 248 firstRootWithHidden keybase1.Seqno 249 250 // latestRootLock ensures that only one API call to fetch the latest merkle 251 // root is in flight at a time. These calls are expensive and would almost 252 // always get the same answer when concurrent. 253 // 254 // Warning: it is ok, to grab the object Lock while holding this one, but do 255 // not ever go the other way around, or you are risking deadlocks. 256 latestRootLock sync.Mutex 257 } 258 259 var _ MerkleClientInterface = (*MerkleClient)(nil) 260 261 type MerkleRoot struct { 262 sigs *jsonw.Wrapper 263 payload MerkleRootPayload 264 fetched time.Time 265 } 266 267 func (mr MerkleRoot) HashMeta() keybase1.HashMeta { 268 return mr.ShortHash().ExportToHashMeta() 269 } 270 271 func (mr MerkleRoot) IsNil() bool { 272 return mr == MerkleRoot{} 273 } 274 275 type SkipSequence []MerkleRootPayload 276 277 type MerkleTriple struct { 278 Seqno keybase1.Seqno `json:"seqno"` 279 LinkID LinkID `json:"id"` 280 SigID keybase1.SigIDBase `json:"sigid,omitempty"` 281 } 282 283 type MerkleUserLeaf struct { 284 public *MerkleTriple 285 private *MerkleTriple 286 idVersion int64 287 username string 288 uid keybase1.UID 289 eldest keybase1.KID // may be empty 290 resets *MerkleResets 291 } 292 293 type MerkleTeamLeaf struct { 294 TeamID keybase1.TeamID 295 Public *MerkleTriple 296 Private *MerkleTriple 297 } 298 299 type MerkleGenericLeaf struct { 300 LeafID keybase1.UserOrTeamID 301 Public *MerkleTriple 302 Private *MerkleTriple 303 304 // if the leaf is a User leaf, we'll have extra information here, like 305 // reset chain and eldest key. On a team leaf, this will be nil. 306 userExtras *MerkleUserLeaf 307 } 308 309 func (l MerkleTeamLeaf) MerkleGenericLeaf() *MerkleGenericLeaf { 310 return &MerkleGenericLeaf{ 311 LeafID: l.TeamID.AsUserOrTeam(), 312 Public: l.Public, 313 Private: l.Private, 314 } 315 } 316 317 func (mul MerkleUserLeaf) MerkleGenericLeaf() *MerkleGenericLeaf { 318 return &MerkleGenericLeaf{ 319 LeafID: mul.uid.AsUserOrTeam(), 320 Public: mul.public, 321 Private: mul.private, 322 userExtras: &mul, 323 } 324 } 325 326 func (l MerkleGenericLeaf) PartialClone() MerkleGenericLeaf { 327 ret := MerkleGenericLeaf{LeafID: l.LeafID} 328 if l.Public != nil { 329 tmp := *l.Public 330 ret.Public = &tmp 331 } 332 if l.Private != nil { 333 tmp := *l.Private 334 ret.Private = &tmp 335 } 336 return ret 337 } 338 339 type PathSteps []*PathStep 340 341 type merkleUserInfoT struct { 342 uid keybase1.UID 343 uidPath PathSteps 344 idVersion int64 345 username string 346 usernameCased string 347 unverifiedResetChain unverifiedResetChain 348 } 349 350 type VerificationPath struct { 351 Contextified 352 root *MerkleRoot 353 path PathSteps 354 } 355 356 type MerkleRootPayload struct { 357 packed string 358 unpacked *MerkleRootPayloadUnpacked 359 } 360 361 func (mrp MerkleRootPayload) shortHash() NodeHashShort { 362 return sha256.Sum256([]byte(mrp.packed)) 363 } 364 365 func (mrp MerkleRootPayload) hasSkips() bool { 366 return len(mrp.unpacked.Body.Skips) > 0 367 } 368 369 type MerkleRootPayloadUnpacked struct { 370 Body struct { 371 Kbfs struct { 372 Private struct { 373 Root keybase1.KBFSRootHash `json:"root"` 374 Version *keybase1.Seqno `json:"version"` 375 } `json:"private"` 376 Public struct { 377 Root keybase1.KBFSRootHash `json:"root"` 378 Version *keybase1.Seqno `json:"version"` 379 } `json:"public"` 380 PrivateTeam struct { 381 Root keybase1.KBFSRootHash `json:"root"` 382 Version *keybase1.Seqno `json:"version"` 383 } `json:"privateteam"` 384 } `json:"kbfs"` 385 LegacyUIDRoot NodeHashShort `json:"legacy_uid_root"` 386 Prev NodeHashLong `json:"prev"` 387 Root NodeHashLong `json:"root"` 388 Seqno keybase1.Seqno `json:"seqno"` 389 Skips SkipTable `json:"skips"` 390 Txid string `json:"txid"` 391 Type string `json:"type"` 392 Version int `json:"version"` 393 PvlHash string `json:"pvl_hash"` 394 ProofServicesHash string `json:"proof_services_hash"` 395 ExternalURLHash string `json:"external_urls_hash"` 396 BlindMerkleRootHash string `json:"blind_merkle_root_hash"` 397 } `json:"body"` 398 Ctime int64 `json:"ctime"` 399 Tag string `json:"tag"` 400 } 401 402 type SkipTable map[keybase1.Seqno]NodeHashAny 403 404 type PathStep struct { 405 prefix string 406 node string // The JSON-stringified version of the node (to be unpacked lazily) 407 } 408 409 func (mt MerkleTriple) Eq(mt2 MerkleTriple) bool { 410 return mt.Seqno == mt2.Seqno && mt.LinkID.Eq(mt2.LinkID) && mt.SigID.Eq(mt2.SigID) 411 } 412 413 func (mul MerkleUserLeaf) Public() *MerkleTriple { 414 return mul.public 415 } 416 417 func NodeHashFromHex(s string) (NodeHash, error) { 418 switch hex.DecodedLen(len(s)) { 419 case NodeHashLenLong: 420 var buf NodeHashLong 421 err := DecodeHexFixed(buf[:], []byte(s)) 422 if err != nil { 423 return nil, err 424 } 425 return buf, err 426 case NodeHashLenShort: 427 var buf NodeHashShort 428 err := DecodeHexFixed(buf[:], []byte(s)) 429 if err != nil { 430 return nil, err 431 } 432 return buf, err 433 default: 434 return nil, fmt.Errorf("Bad NodeHash; wrong length: %d", len(s)) 435 } 436 } 437 438 func GetNodeHash(w *jsonw.Wrapper) (NodeHash, error) { 439 s, err := w.GetString() 440 if err != nil { 441 return nil, err 442 } 443 ret, err := NodeHashFromHex(s) 444 return ret, err 445 } 446 447 func GetNodeHashVoid(w *jsonw.Wrapper, nhp *NodeHash, errp *error) { 448 nh, err := GetNodeHash(w) 449 if err != nil { 450 *errp = err 451 } else { 452 *nhp = nh 453 } 454 } 455 456 func computeSetBitsBigEndian(x uint) []uint { 457 if x == 0 { 458 return nil 459 } else if x == 1 { 460 return []uint{1} 461 } 462 // Allocate maximum array size necessary 463 high := int(math.Ceil(math.Log2(float64(x)))) 464 ret := make([]uint, 0, high) 465 for i, bit := 0, uint(1); i <= high; i, bit = i+1, bit*2 { 466 if x&bit != 0 { 467 ret = append(ret, bit) 468 } 469 } 470 return ret 471 } 472 473 func computeLogPatternMerkleSkips(startSeqno keybase1.Seqno, endSeqno keybase1.Seqno) (ret []uint, err error) { 474 if endSeqno < startSeqno { 475 return ret, fmt.Errorf("got startSeqno > endSeqno (%d > %d) in merkle skip sequence", startSeqno, endSeqno) 476 } 477 if endSeqno == startSeqno { 478 return ret, nil 479 } 480 end := uint(endSeqno) 481 start := uint(startSeqno) 482 diff := end - start 483 skips := computeSetBitsBigEndian(diff) 484 curr := end 485 // Ignore first set bit 486 for i := len(skips) - 1; i > 0; i-- { 487 curr -= skips[i] 488 ret = append(ret, curr) 489 } 490 return ret, nil 491 } 492 493 func NewMerkleClient(g *GlobalContext) *MerkleClient { 494 return &MerkleClient{ 495 keyring: NewSpecialKeyRing(g.Env.GetMerkleKIDs(), g), 496 lastRoot: nil, 497 Contextified: NewContextified(g), 498 } 499 } 500 501 func (mc *MerkleClient) init(m MetaContext) error { 502 err := mc.loadRoot(m) 503 return err 504 } 505 506 func merkleHeadKey() DbKey { 507 // DBMerkleRoot was once used to store specific roots with Key: fmt.Sprintf("%d", int) 508 return DbKey{ 509 Typ: DBMerkleRoot, 510 Key: "HEAD", 511 } 512 } 513 514 func (mc *MerkleClient) dbGet(m MetaContext, k DbKey) (ret *MerkleRoot, err error) { 515 defer m.VTrace(VLog1, fmt.Sprintf("MerkleClient#dbGet(%+v)", k), &err)() 516 curr, err := m.G().LocalDb.Get(k) 517 if err != nil { 518 return nil, err 519 } 520 if curr == nil { 521 m.VLogf(VLog1, "| MerkleClient#dbGet(%+v) found not results", k) 522 return nil, nil 523 } 524 525 mr, err := NewMerkleRootFromJSON(curr, MerkleOpts{}) 526 if err != nil { 527 return nil, err 528 } 529 return mr, err 530 } 531 532 func (mc *MerkleClient) loadRoot(m MetaContext) (err error) { 533 defer m.VTrace(VLog1, "MerkleClient#loadRoot()", &err)() 534 var mr *MerkleRoot 535 mr, err = mc.dbGet(m, merkleHeadKey()) 536 if mr == nil || err != nil { 537 return err 538 } 539 mc.Lock() 540 mc.lastRoot = mr 541 mc.Unlock() 542 return nil 543 } 544 545 func (mr *MerkleRoot) HasSkips() bool { 546 return mr.payload.hasSkips() 547 } 548 549 func (mr *MerkleRoot) ToJSON() (jw *jsonw.Wrapper) { 550 ret := jsonw.NewDictionary() 551 _ = ret.SetKey("sigs", mr.sigs) 552 _ = ret.SetKey("payload_json", jsonw.NewString(mr.payload.packed)) 553 _ = ret.SetKey("fetched_ns", jsonw.NewInt64(mr.fetched.UnixNano())) 554 return ret 555 } 556 557 func (mr MerkleRoot) ShortHash() NodeHashShort { 558 return mr.payload.shortHash() 559 } 560 561 func NewMerkleRootPayloadFromJSONString(s string) (ret MerkleRootPayload, err error) { 562 ret = MerkleRootPayload{packed: s} 563 err = json.Unmarshal([]byte(s), &ret.unpacked) 564 if err != nil { 565 return ret, err 566 } 567 return ret, nil 568 } 569 570 func NewMerkleRootFromJSON(jw *jsonw.Wrapper, opts MerkleOpts) (ret *MerkleRoot, err error) { 571 var sigs *jsonw.Wrapper 572 var payloadJSONString string 573 var mrp MerkleRootPayload 574 575 if !opts.noSigCheck { 576 if sigs, err = jw.AtKey("sigs").ToDictionary(); err != nil { 577 return nil, err 578 } 579 } 580 581 if payloadJSONString, err = jw.AtKey("payload_json").GetString(); err != nil { 582 return nil, err 583 } 584 585 if mrp, err = NewMerkleRootPayloadFromJSONString(payloadJSONString); err != nil { 586 return nil, err 587 } 588 589 ret = &MerkleRoot{ 590 sigs: sigs, 591 payload: mrp, 592 fetched: time.Time{}, 593 } 594 595 fetchedNs, err := jw.AtKey("fetched_ns").GetInt64() 596 if err == nil { 597 ret.fetched = time.Unix(0, fetchedNs) 598 } 599 600 return ret, nil 601 } 602 603 func importPathFromJSON(jw *jsonw.Wrapper) (out []*PathStep, err error) { 604 if jw.IsNil() { 605 return 606 } 607 608 var path *jsonw.Wrapper 609 if path, err = jw.ToArray(); err != nil { 610 return 611 } 612 613 var l int 614 if l, err = path.Len(); err != nil { 615 return 616 } 617 618 for i := 0; i < l; i++ { 619 var step *PathStep 620 if step, err = pathStepFromJSON(path.AtIndex(i)); err != nil { 621 return 622 } 623 out = append(out, step) 624 } 625 return 626 } 627 628 // FetchRootFromServerByMinSeqno returns the latest root this client knows 629 // about. If the seqno of the latest root is smaller than the lowerBound 630 // argument, a new api call is made to the server. However, if the server 631 // returns a root at a seqno smaller than lowerBound, no errors are raised. 632 func (mc *MerkleClient) FetchRootFromServerByMinSeqno(m MetaContext, lowerBound keybase1.Seqno) (mr *MerkleRoot, err error) { 633 defer m.VTrace(VLog0, "MerkleClient#FetchRootFromServerByMinSeqno", &err)() 634 635 checkFreshness := func() (ok bool, root *MerkleRoot) { 636 root = mc.LastRoot(m) 637 if root != nil && *root.Seqno() >= lowerBound { 638 m.VLogf(VLog0, "seqno=%d, and was current enough, so returning non-nil previously fetched root", *root.Seqno()) 639 return true, root 640 } 641 return false, root 642 } 643 644 if ok, root := checkFreshness(); ok { 645 return root, nil 646 } 647 648 mc.latestRootLock.Lock() 649 defer mc.latestRootLock.Unlock() 650 // by the time we got the lock, the root might have been updated to a recent enough one, so check again 651 ok, root := checkFreshness() 652 if ok { 653 return root, nil 654 } 655 656 return mc.fetchAndStoreRootFromServerLocked(m, root) 657 } 658 659 // FetchRootFromServer fetches a root from the server. If the last-fetched root was fetched within 660 // freshness ago, then OK to return the last-fetched root. Otherwise refetch. Similarly, if the freshness 661 // passed is 0, then always refresh. 662 func (mc *MerkleClient) FetchRootFromServer(m MetaContext, freshness time.Duration) (mr *MerkleRoot, err error) { 663 defer m.VTrace(VLog0, "MerkleClient#FetchRootFromServer", &err)() 664 665 now := m.G().Clock().Now() 666 667 checkFreshness := func() (ok bool, root *MerkleRoot) { 668 root = mc.LastRoot(m) 669 if root != nil && freshness > 0 && now.Sub(root.fetched) < freshness { 670 m.VLogf(VLog0, "freshness=%s, and was current enough, so returning non-nil previously fetched root", freshness) 671 return true, root 672 } 673 return false, root 674 } 675 676 if ok, root := checkFreshness(); ok { 677 return root, nil 678 } 679 680 mc.latestRootLock.Lock() 681 defer mc.latestRootLock.Unlock() 682 // by the time we got the lock, the root might have been updated to a recent enough one, so check again 683 ok, root := checkFreshness() 684 if ok { 685 return root, nil 686 } 687 688 return mc.fetchAndStoreRootFromServerLocked(m, root) 689 } 690 691 func (mc *MerkleClient) fetchAndStoreRootFromServerLocked(m MetaContext, lastRoot *MerkleRoot) (mr *MerkleRoot, err error) { 692 defer m.VTrace(VLog0, "MerkleClient#fetchRootFromServerLocked", &err)() 693 var ss SkipSequence 694 var apiRes *APIRes 695 var opts MerkleOpts 696 697 mr, ss, apiRes, err = mc.lookupRootAndSkipSequence(m, lastRoot, opts) 698 if err != nil { 699 return nil, err 700 } 701 702 if mr == nil { 703 // The server indicated that last root is the most recent one: updating 704 // the fetch time and skipping verification 705 lastRoot.fetched = m.G().Clock().Now() 706 mc.Lock() 707 defer mc.Unlock() 708 mc.storeRoot(m, lastRoot) 709 return lastRoot, nil 710 } 711 712 if err = mc.verifySkipSequenceAndRoot(m, ss, mr, lastRoot, apiRes, opts); err != nil { 713 return nil, err 714 } 715 716 mc.Lock() 717 defer mc.Unlock() 718 mc.storeRoot(m, mr) 719 720 return mr, nil 721 } 722 723 // if both mr and err are nil, this indicates the server did not send a new root 724 // as lastRoot was the most recent one. 725 func (mc *MerkleClient) lookupRootAndSkipSequence(m MetaContext, lastRoot *MerkleRoot, opts MerkleOpts) (mr *MerkleRoot, ss SkipSequence, apiRes *APIRes, err error) { 726 727 // c=1 invokes server-side compression 728 q := HTTPArgs{ 729 "c": B{true}, 730 } 731 732 // Get back a series of skips from the last merkle root we had to the new 733 // one we're getting back, and hold the server to it. 734 lastSeqno := lastRoot.Seqno() 735 if lastSeqno != nil { 736 q.Add("last", I{int(*lastSeqno)}) 737 // If the last root known to the server has seqno last, we do not need 738 // to receive it again. 739 q.Add("skip_last", B{true}) 740 } 741 742 apiRes, err = m.G().API.Get(m, APIArg{ 743 Endpoint: "merkle/root", 744 SessionType: APISessionTypeNONE, 745 Args: q, 746 AppStatusCodes: []int{SCOk}, 747 }) 748 749 if err != nil { 750 return nil, nil, nil, err 751 } 752 753 seqno, err := apiRes.Body.AtKey("seqno").GetInt64() 754 if err != nil { 755 return nil, nil, nil, fmt.Errorf("merkle/root response does not contain seqno: %v", err) 756 } 757 if lastSeqno != nil && *lastSeqno == keybase1.Seqno(seqno) { 758 // here we can ignore the rest of the server response (the server 759 // should not send it anyways), as lastRoot is still the most recent 760 // root 761 m.Debug("The server indicated that the root at seqno %v (which we have) is the most recent, shortcircuiting the root parsing and validation.", seqno) 762 return nil, nil, nil, nil 763 } 764 765 mr, err = readRootFromAPIRes(m, apiRes.Body, opts) 766 if err != nil { 767 return nil, nil, nil, err 768 } 769 ss, err = mc.readSkipSequenceFromAPIRes(m, apiRes, mr, lastRoot) 770 if err != nil { 771 return nil, nil, nil, err 772 } 773 return mr, ss, apiRes, err 774 } 775 776 func (mc *MerkleClient) lookupLeafAndPathUser(m MetaContext, q HTTPArgs, sigHints *SigHints, root *MerkleRoot, opts MerkleOpts) (vp *VerificationPath, userInfo *merkleUserInfoT, apiRes *APIRes, err error) { 777 opts.isUser = true 778 vp, apiRes, err = mc.lookupLeafAndPath(m, q, root, sigHints, opts) 779 if err != nil { 780 return nil, nil, nil, err 781 } 782 783 if sigHints != nil { 784 if err = sigHints.RefreshWith(m, apiRes.Body.AtKey("sigs")); err != nil { 785 return nil, nil, nil, err 786 } 787 } 788 789 userInfo, err = mc.readUserFromAPIRes(m, apiRes) 790 if err != nil { 791 return nil, nil, nil, err 792 } 793 794 return vp, userInfo, apiRes, nil 795 } 796 797 func (mc *MerkleClient) lookupLeafAndPath(m MetaContext, q HTTPArgs, root *MerkleRoot, sigHints *SigHints, opts MerkleOpts) (vp *VerificationPath, res *APIRes, err error) { 798 apiRes, root, err := mc.lookupLeafAndPathHelper(m, q, sigHints, root, opts) 799 if err != nil { 800 return nil, nil, err 801 } 802 803 vp, err = mc.readPathFromAPIRes(m, apiRes, opts) 804 if err != nil { 805 return nil, nil, err 806 } 807 vp.root = root 808 809 return vp, apiRes, nil 810 } 811 812 // `MerkleOpts.isUser` is true for loading a user and false for loading a team. 813 func (mc *MerkleClient) lookupLeafAndPathHelper(m MetaContext, q HTTPArgs, sigHints *SigHints, root *MerkleRoot, opts MerkleOpts) (apiRes *APIRes, newRoot *MerkleRoot, err error) { 814 defer m.VTrace(VLog1, "MerkleClient#lookupLeafAndPathHelper", &err)() 815 816 for i := 0; i < 5; i++ { 817 apiRes, rootRefreshNeeded, err := mc.lookupLeafAndPathHelperOnce(m, q, sigHints, root, opts) 818 if err != nil { 819 return nil, nil, err 820 } 821 if !rootRefreshNeeded { 822 return apiRes, root, err 823 } 824 825 m.Debug("Server suggested a root refresh is necessary") 826 root, err = mc.FetchRootFromServer(m, 0) 827 if err != nil { 828 return nil, nil, err 829 } 830 } 831 832 return nil, nil, fmt.Errorf("Too many server requests to refresh the merkle root") 833 } 834 835 // `isUser` is true for loading a user and false for loading a team. 836 func (mc *MerkleClient) lookupLeafAndPathHelperOnce(m MetaContext, q HTTPArgs, sigHints *SigHints, root *MerkleRoot, opts MerkleOpts) (apiRes *APIRes, rootRefreshNeeded bool, err error) { 837 defer m.VTrace(VLog1, "MerkleClient#lookupLeafAndPathHelperOnce", &err)() 838 839 if !opts.NoServerPolling { 840 // Poll for 10s and ask for a race-free state. 841 w := 10 * int(CITimeMultiplier(mc.G())) 842 q.Add("poll", I{w}) 843 } 844 845 q.Add("c", B{true}) 846 if opts.isUser { 847 q.Add("load_deleted", B{true}) 848 q.Add("load_reset_chain", B{true}) 849 } 850 851 // Add the local db sigHints version 852 if sigHints != nil { 853 q.Add("sig_hints_low", I{sigHints.version}) 854 } 855 856 // Get back a path from the leaf to the current merkle root. The root itself 857 // is not included. 858 tail := root.Seqno() 859 if tail != nil { 860 q.Add("tail", I{int(*tail)}) 861 } 862 863 apiRes, err = m.G().API.Get(m, APIArg{ 864 Endpoint: "merkle/path", 865 SessionType: APISessionTypeOPTIONAL, 866 Args: q, 867 AppStatusCodes: []int{SCOk, SCNotFound, SCDeleted, SCMerkleUpdateRoot}, 868 }) 869 870 if err != nil { 871 return nil, false, err 872 } 873 874 switch apiRes.AppStatus.Code { 875 case SCMerkleUpdateRoot: 876 // Server indicated that a refetch of the root is needed 877 return nil, true, nil 878 case SCOk: 879 err = assertRespSeqnoPrecedesCurrentRoot(apiRes, root) 880 if err != nil { 881 return nil, false, err 882 } 883 // TRIAGE-2068 884 case SCNotFound: 885 return nil, false, NotFoundError{} 886 case SCDeleted: 887 return nil, false, UserDeletedError{} 888 } 889 return apiRes, false, nil 890 } 891 892 func assertRespSeqnoPrecedesCurrentRoot(apiRes *APIRes, root *MerkleRoot) error { 893 resSeqno, err := apiRes.Body.AtKey("root").AtKey("seqno").GetInt64() 894 if err != nil { 895 return err 896 } 897 if keybase1.Seqno(resSeqno) > *root.Seqno() { 898 // The server should have returned SCMerkleUpdateRoot instead 899 return MerkleClientError{m: fmt.Sprintf("The server unexpectedly returned root (%v) ahead of the last one we know about (%v) instead of asking to update", keybase1.Seqno(resSeqno), *root.Seqno())} 900 } 901 return nil 902 } 903 904 func readSkipSequenceFromStringList(v []string) (ret SkipSequence, err error) { 905 for _, s := range v { 906 var p MerkleRootPayload 907 if p, err = NewMerkleRootPayloadFromJSONString(s); err != nil { 908 return nil, err 909 } 910 ret = append(ret, p) 911 } 912 return ret, nil 913 } 914 915 func (mc *MerkleClient) readAndCheckRootFromAPIRes(m MetaContext, apiRes *APIRes, currentRoot *MerkleRoot, opts MerkleOpts) (newRoot *MerkleRoot, err error) { 916 newRoot, err = readRootFromAPIRes(m, apiRes.Body.AtKey("root"), opts) 917 if err != nil { 918 return nil, err 919 } 920 ss, err := mc.readSkipSequenceFromAPIRes(m, apiRes, newRoot, currentRoot) 921 if err != nil { 922 return nil, err 923 } 924 err = mc.verifySkipSequenceAndRoot(m, ss, newRoot, currentRoot, apiRes, opts) 925 if err != nil { 926 return nil, err 927 } 928 return newRoot, nil 929 } 930 931 func readRootFromAPIRes(m MetaContext, jw *jsonw.Wrapper, opts MerkleOpts) (*MerkleRoot, error) { 932 ret, err := NewMerkleRootFromJSON(jw, opts) 933 if err != nil { 934 return nil, err 935 } 936 if chk := GetMerkleCheckpoint(m); chk != nil && *ret.Seqno() < *chk.Seqno() { 937 msg := fmt.Sprintf("got unexpected early root %d < %d", *ret.Seqno(), *chk.Seqno()) 938 m.Error("checkpoint failure: %s", msg) 939 return nil, NewClientMerkleFailedCheckpointError(msg) 940 } 941 ret.fetched = m.G().Clock().Now() 942 return ret, nil 943 } 944 945 // readSkipSequenceFromAPIRes returns a SkipSequence. We construct the sequence by starting with the 946 // most recent merkle root, adding the "skip" pointers returned by the server, and finally bookending 947 // with the merkle root we last fetched from the DB. In verifySkipSequence, we walk over this Sequence 948 // to make sure that it obeys proper construction. 949 func (mc *MerkleClient) readSkipSequenceFromAPIRes(m MetaContext, res *APIRes, thisRoot *MerkleRoot, lastRoot *MerkleRoot) (ret SkipSequence, err error) { 950 defer m.VTrace(VLog1, "MerkleClient#readSkipSequenceFromAPIRes", &err)() 951 if lastRoot == nil { 952 m.VLogf(VLog0, "| lastRoot==nil") 953 return nil, nil 954 } 955 if !thisRoot.HasSkips() { 956 m.VLogf(VLog0, "| thisRoot has no skips") 957 return nil, nil 958 } 959 skips := res.Body.AtKey("skips") 960 961 if skips.IsNil() { 962 m.VLogf(VLog1, "| skip list from API server is nil") 963 return nil, nil 964 } 965 966 var v []string 967 if err = skips.UnmarshalAgain(&v); err != nil { 968 m.VLogf(VLog0, "| failed to unmarshal skip list as a list of strings") 969 return nil, err 970 } 971 972 ret, err = readSkipSequenceFromStringList(v) 973 if err != nil { 974 return nil, err 975 } 976 977 // Create the skip sequence by bookending the list the server replies with 978 // with: (1) the most recent root, sent back in this reply; and (2) our last 979 // root, which we read out of cache (in memory or on disk). HOWEVER, in the 980 // case of lookup up historical roots, the ordering might be reversed. So 981 // we swap in that case. 982 983 left, right := thisRoot.payload, lastRoot.payload 984 if left.seqno() < right.seqno() { 985 left, right = right, left 986 } 987 988 ret = append(SkipSequence{left}, ret...) 989 ret = append(ret, right) 990 991 return ret, nil 992 } 993 994 func (mc *MerkleClient) readUserFromAPIRes(m MetaContext, res *APIRes) (userInfo *merkleUserInfoT, err error) { 995 userInfo = &merkleUserInfoT{} 996 997 userInfo.uid, err = GetUID(res.Body.AtKey("uid")) 998 if err != nil { 999 return nil, err 1000 } 1001 1002 // We don't trust this version, but it's useful to tell us if there 1003 // are new versions unsigned data, like basics, and maybe uploaded 1004 // keys 1005 userInfo.idVersion, err = res.Body.AtKey("id_version").GetInt64() 1006 if err != nil { 1007 return nil, err 1008 } 1009 1010 userInfo.uidPath, err = importPathFromJSON(res.Body.AtKey("uid_proof_path")) 1011 if err != nil { 1012 return nil, err 1013 } 1014 1015 userInfo.username, err = res.Body.AtKey("username").GetString() 1016 if err != nil { 1017 return nil, err 1018 } 1019 userInfo.usernameCased, _ = res.Body.AtKey("username_cased").GetString() 1020 1021 userInfo.unverifiedResetChain, err = importResetChainFromServer(m, res.Body.AtKey("reset_chain")) 1022 if err != nil { 1023 return nil, err 1024 } 1025 1026 return userInfo, nil 1027 } 1028 1029 func (mc *MerkleClient) readPathFromAPIRes(m MetaContext, res *APIRes, opts MerkleOpts) (vp *VerificationPath, err error) { 1030 defer m.VTrace(VLog1, "MerkleClient#readPathFromAPIRes", &err)() 1031 1032 vp = &VerificationPath{ 1033 Contextified: NewContextified(mc.G()), 1034 } 1035 1036 vp.path, err = importPathFromJSON(res.Body.AtKey("path")) 1037 if err != nil { 1038 return nil, err 1039 } 1040 1041 return vp, nil 1042 } 1043 1044 func pathStepFromJSON(jw *jsonw.Wrapper) (ps *PathStep, err error) { 1045 1046 var prefix string 1047 pw := jw.AtKey("prefix") 1048 if !pw.IsNil() { 1049 var s string 1050 if s, err = pw.GetString(); err != nil { 1051 return 1052 } 1053 prefix = s 1054 } 1055 node, err := jw.AtKey("node").AtKey("val").GetString() 1056 if err != nil { 1057 return 1058 } 1059 ps = &PathStep{prefix, node} 1060 return 1061 } 1062 1063 func (mc *MerkleClient) LastRoot(m MetaContext) *MerkleRoot { 1064 mc.RLock() 1065 defer mc.RUnlock() 1066 if mc.lastRoot == nil { 1067 return nil 1068 } 1069 ret := mc.lastRoot 1070 chk := GetMerkleCheckpoint(m) 1071 if chk != nil && *ret.Seqno() < *chk.Seqno() { 1072 ret = chk 1073 } 1074 return ret.ShallowCopy() 1075 } 1076 1077 func (mr MerkleRoot) ExportToAVDL(g *GlobalContext) keybase1.MerkleRootAndTime { 1078 hashMeta := mr.ShortHash() 1079 return keybase1.MerkleRootAndTime{ 1080 Root: keybase1.MerkleRootV2{ 1081 Seqno: mr.payload.unpacked.Body.Seqno, 1082 HashMeta: hashMeta[:], 1083 }, 1084 UpdateTime: keybase1.TimeFromSeconds(mr.payload.unpacked.Ctime), 1085 FetchTime: keybase1.ToTime(mr.fetched), 1086 } 1087 } 1088 1089 // storeRoot stores the root in the db and mem. 1090 // Must be called from under a lock. 1091 func (mc *MerkleClient) storeRoot(m MetaContext, root *MerkleRoot) { 1092 m.VLogf(VLog0, "storing merkle root: %d", *root.Seqno()) 1093 err := mc.G().LocalDb.Put(merkleHeadKey(), nil, root.ToJSON()) 1094 if err != nil { 1095 m.Error("Cannot commit Merkle root to local DB: %s", err) 1096 } else { 1097 mc.lastRoot = root 1098 } 1099 } 1100 1101 func (mc *MerkleClient) firstExaminableHistoricalRootProd(m MetaContext) *keybase1.Seqno { 1102 chk := GetMerkleCheckpoint(m) 1103 var ret *keybase1.Seqno 1104 if chk != nil { 1105 ret = chk.Seqno() 1106 } 1107 if ret == nil || FirstProdMerkleSeqnoWithSkips > *ret { 1108 ret = &FirstProdMerkleSeqnoWithSkips 1109 } 1110 return ret 1111 } 1112 1113 func (mc *MerkleClient) FirstExaminableHistoricalRoot(m MetaContext) *keybase1.Seqno { 1114 1115 if mc.G().Env.GetRunMode() == ProductionRunMode { 1116 return mc.firstExaminableHistoricalRootProd(m) 1117 } 1118 1119 ret := mc.getFirstSkip() 1120 if ret != nil { 1121 return ret 1122 } 1123 1124 ret = mc.getFirstSkipFromServer(m) 1125 return ret 1126 } 1127 1128 func (mc *MerkleClient) getFirstSkip() *keybase1.Seqno { 1129 mc.RLock() 1130 defer mc.RUnlock() 1131 return mc.firstSkip 1132 } 1133 1134 type firstSkipRaw struct { 1135 Status AppStatus `json:"status"` 1136 Seqno keybase1.Seqno `json:"seqno"` 1137 } 1138 1139 func (r *firstSkipRaw) GetAppStatus() *AppStatus { 1140 return &r.Status 1141 } 1142 1143 func (mc *MerkleClient) getFirstSkipFromServer(m MetaContext) *keybase1.Seqno { 1144 1145 var raw firstSkipRaw 1146 err := m.G().API.GetDecode(m, APIArg{ 1147 Endpoint: "merkle/first_root_with_skips", 1148 SessionType: APISessionTypeNONE, 1149 AppStatusCodes: []int{SCOk}, 1150 }, &raw) 1151 1152 if err != nil { 1153 m.Debug("failed to fetch first skip from server: %v", err) 1154 return nil 1155 } 1156 1157 m.Debug("Got back seqno=%v as first merkle root with skips", raw.Seqno) 1158 1159 mc.Lock() 1160 mc.firstSkip = &raw.Seqno 1161 mc.Unlock() 1162 1163 return &raw.Seqno 1164 } 1165 1166 func (mc *MerkleClient) firstMainRootWithHiddenRootHashProd(m MetaContext) (s keybase1.Seqno) { 1167 return FirstProdMerkleSeqnoWithHiddenRootHash 1168 } 1169 1170 func (mc *MerkleClient) FirstMainRootWithHiddenRootHash(m MetaContext) (s keybase1.Seqno, err error) { 1171 if mc.G().Env.GetRunMode() == ProductionRunMode { 1172 return mc.firstMainRootWithHiddenRootHashProd(m), nil 1173 } 1174 1175 s = mc.getFirstMainRootWithHiddenRootHash() 1176 if s != 0 { 1177 return s, nil 1178 } 1179 1180 return mc.getFirstMainRootWithHiddenRootHashFromServer(m) 1181 } 1182 1183 func (mc *MerkleClient) getFirstMainRootWithHiddenRootHash() keybase1.Seqno { 1184 mc.RLock() 1185 defer mc.RUnlock() 1186 return mc.firstRootWithHidden 1187 } 1188 1189 type firstHiddenSeqnoRaw struct { 1190 Status AppStatus `json:"status"` 1191 Seqno keybase1.Seqno `json:"seqno"` 1192 } 1193 1194 func (r *firstHiddenSeqnoRaw) GetAppStatus() *AppStatus { 1195 return &r.Status 1196 } 1197 1198 func (mc *MerkleClient) getFirstMainRootWithHiddenRootHashFromServer(m MetaContext) (s keybase1.Seqno, err error) { 1199 1200 var raw firstHiddenSeqnoRaw 1201 err = m.G().API.GetDecode(m, APIArg{ 1202 Endpoint: "merkle/first_root_with_hidden", 1203 SessionType: APISessionTypeNONE, 1204 AppStatusCodes: []int{SCOk}, 1205 }, &raw) 1206 1207 if err != nil { 1208 m.Debug("failed to fetch first main root with hidden from server: %v", err) 1209 return 0, fmt.Errorf("failed to fetch first main root with hidden from server: %v", err) 1210 } 1211 1212 m.Debug("Got back seqno=%v as first merkle root with hidden root hash", raw.Seqno) 1213 1214 mc.Lock() 1215 mc.firstRootWithHidden = raw.Seqno 1216 mc.Unlock() 1217 1218 return raw.Seqno, nil 1219 } 1220 1221 func (mc *MerkleClient) findValidKIDAndSig(root *MerkleRoot) (keybase1.KID, string, error) { 1222 if v, err := root.sigs.Keys(); err == nil { 1223 for _, s := range v { 1224 kid := keybase1.KIDFromString(s) 1225 if !mc.keyring.IsValidKID(kid) { 1226 continue 1227 } else if sig, err := root.sigs.AtKey(s).AtKey("sig").GetString(); err == nil { 1228 return kid, sig, nil 1229 } 1230 } 1231 } 1232 var nilKID keybase1.KID 1233 return nilKID, "", MerkleClientError{"no known verifying key", merkleErrorNoKnownKey} 1234 } 1235 1236 func (mc *MerkleClient) verifySkipSequence(m MetaContext, ss SkipSequence, thisRoot *MerkleRoot, lastRoot *MerkleRoot, opts MerkleOpts) (err error) { 1237 defer m.VTrace(VLog1, "MerkleClient#verifySkipSequence", &err)() 1238 1239 var left, right keybase1.Seqno 1240 if thisRoot.Seqno() != nil { 1241 left = *thisRoot.Seqno() 1242 } 1243 if lastRoot.Seqno() != nil { 1244 right = *lastRoot.Seqno() 1245 } 1246 1247 // In historical queries (for which we fetch old roots), we check the skip 1248 // sequence in the opposite direction. 1249 if opts.historical { 1250 left, right = right, left 1251 } 1252 1253 // In this case, the server did not return a skip sequence. It's OK if 1254 // the last known root is too old. It's not OK if the last known root is 1255 // from after the server starting providing skip pointers. 1256 if ss == nil { 1257 m.VLogf(VLog1, "| nil SkipSequence") 1258 fss := mc.FirstExaminableHistoricalRoot(m) 1259 if lastRoot == nil { 1260 m.VLogf(VLog1, "| lastRoot==nil, so OK") 1261 return nil 1262 } 1263 if fss == nil { 1264 m.VLogf(VLog1, "| no known root with skips, so OK") 1265 return nil 1266 } 1267 if *fss > right { 1268 m.VLogf(VLog1, "| right marker (%d) is from before first known root with skips (%d), so OK", int(right), int(*fss)) 1269 return nil 1270 } 1271 if *fss > left { 1272 m.VLogf(VLog1, "| left marker (%d) is from before first known root with skips (%d), so OK", int(left), int(*fss)) 1273 return nil 1274 } 1275 if thisRoot != nil && *lastRoot.Seqno() == *thisRoot.Seqno() { 1276 m.VLogf(VLog1, "| thisRoot is the same as lastRoot (%d), so OK", int(*lastRoot.Seqno())) 1277 return nil 1278 } 1279 return MerkleClientError{fmt.Sprintf("Expected a skip sequence with last=%d", int(*lastRoot.Seqno())), merkleErrorNoSkipSequence} 1280 } 1281 1282 if left == right { 1283 m.VLogf(VLog1, "| No change since last check (seqno %d)", *thisRoot.Seqno()) 1284 return nil 1285 } 1286 return ss.verify(m, left, right) 1287 } 1288 1289 // verify verifies the raw "Skip Sequence" ss. ss contains a list of MerkleRootPayloads beginning 1290 // with the most recently returned root, and ending with the last root that we fetched. So for instance, 1291 // it might contain: [ 100, 84, 82, 81 ] in that case that we last fetched Seqno=81 and the server is 1292 // currently at Seqno=100. 1293 func (ss SkipSequence) verify(m MetaContext, thisRoot keybase1.Seqno, lastRoot keybase1.Seqno) (err error) { 1294 defer m.VTrace(VLog1, "SkipSequence#verify", &err)() 1295 1296 expectedSkips, err := computeLogPatternMerkleSkips(lastRoot, thisRoot) 1297 if err != nil { 1298 return MerkleClientError{fmt.Sprintf("Failed to compute expected skip pattern: %s", err), merkleErrorWrongSkipSequence} 1299 } 1300 // Don't check bookends that were added by client 1301 if len(expectedSkips)+2 != len(ss) { 1302 return MerkleClientError{fmt.Sprintf("Wrong number of skips: expected %d, got %d.", len(expectedSkips)+2, len(ss)), merkleErrorWrongSkipSequence} 1303 } 1304 1305 for index := 1; index < len(ss)-1; index++ { 1306 root := ss[index].seqno() 1307 if keybase1.Seqno(expectedSkips[index-1]) != root { 1308 return MerkleClientError{fmt.Sprintf("Unexpected skip index: expected %d, got %d.", expectedSkips[index-1], root), merkleErrorWrongSkipSequence} 1309 } 1310 } 1311 1312 const maxClockDriftSeconds int64 = 5 * 60 1313 var totalDrift int64 1314 1315 for index := 0; index < len(ss)-1; index++ { 1316 nextIndex := index + 1 1317 thisRoot, prevRoot := ss[index].seqno(), ss[nextIndex].seqno() 1318 m.VLogf(VLog1, "| Checking skip %d->%d", thisRoot, prevRoot) 1319 1320 // Next compare the skip pointer in this merkle root against the hash of the previous 1321 // root in the merkle root sequence. They must be equal. 1322 hash := ss[index].skipToSeqno(prevRoot) 1323 if hash == nil || hash.IsNil() { 1324 return MerkleClientError{fmt.Sprintf("Skip missing at %d->%d", thisRoot, prevRoot), merkleErrorSkipMissing} 1325 } 1326 if !hashEq(hash, ss[nextIndex].shortHash()) { 1327 m.VLogf(VLog0, "| Failure in hashes: %s != %s", hash.String(), ss[nextIndex].shortHash().String()) 1328 return MerkleClientError{fmt.Sprintf("Skip pointer mismatch at %d->%d", thisRoot, prevRoot), merkleErrorSkipHashMismatch} 1329 } 1330 1331 // Check that ctimes in the sequence are nearly strictly ordered; we have to make sure we can handle slight 1332 // clock jitters since the server might need to rewind time due to leap seconds or NTP issues. 1333 // We'll allow at most 5 minutes of "time-travel" between 2 updates, and no more than 5minutes of time travel 1334 // across the whole sequence 1335 thisCTime, prevCTime := ss[index].ctime(), ss[nextIndex].ctime() 1336 if prevCTime > thisCTime { 1337 drift := prevCTime - thisCTime 1338 if drift > maxClockDriftSeconds { 1339 return MerkleClientError{ 1340 fmt.Sprintf("Out of order ctimes: %d at %d should not have come before %d at %d (even with %ds tolerance)", thisRoot, thisCTime, prevRoot, prevCTime, maxClockDriftSeconds), 1341 merkleErrorOutOfOrderCtime, 1342 } 1343 } 1344 totalDrift += drift 1345 } 1346 } 1347 1348 if totalDrift > maxClockDriftSeconds { 1349 return MerkleClientError{ 1350 fmt.Sprintf("Too much clock drift detected (%ds) in skip sequence", totalDrift), 1351 merkleErrorTooMuchClockDrift, 1352 } 1353 1354 } 1355 1356 return nil 1357 } 1358 1359 func (mc *MerkleClient) verifyRootHelper(m MetaContext, newRoot *MerkleRoot, currentRoot *MerkleRoot, opts MerkleOpts) (err error) { 1360 defer m.VTrace(VLog1, fmt.Sprintf("merkleClient#verifyRootHelper(root=%d, cached=%v, opts=%+v)", int(*newRoot.Seqno()), currentRoot.Seqno() == nil, opts), &err)() 1361 1362 // First make sure it's not a rollback. If we're doing an historical lookup, it's 1363 // actual OK. 1364 if !opts.historical && currentRoot != nil && *currentRoot.Seqno() > *newRoot.Seqno() { 1365 return fmt.Errorf("Server rolled back Merkle tree: %d > %d", *currentRoot.Seqno(), *newRoot.Seqno()) 1366 } 1367 1368 if currentRoot != nil && currentRoot.ShortHash() == newRoot.ShortHash() { 1369 // the new root is the same as the old one, no need to check it again 1370 return nil 1371 } 1372 1373 kid, sig, err := mc.findValidKIDAndSig(newRoot) 1374 if err != nil { 1375 return err 1376 } 1377 m.VLogf(VLog1, "+ Merkle: using KID=%s for verifying server sig", kid) 1378 1379 key, err := mc.keyring.Load(m, kid) 1380 if err != nil { 1381 return err 1382 } 1383 1384 if key == nil { 1385 return MerkleClientError{"no known verifying key", merkleErrorNoKnownKey} 1386 } 1387 1388 // Actually run the PGP verification over the signature 1389 _, err = key.VerifyString(mc.G().Log, sig, []byte(newRoot.payload.packed)) 1390 if err != nil { 1391 return err 1392 } 1393 1394 skips := newRoot.payload.unpacked.Body.Skips 1395 if err := verifyRootSkips(*newRoot.Seqno(), skips); err != nil { 1396 return err 1397 } 1398 1399 m.VLogf(VLog1, "- Merkle: server sig verified") 1400 1401 return nil 1402 } 1403 1404 func verifyRootSkips(rootSeqno keybase1.Seqno, skips SkipTable) error { 1405 expectedSkips := computeExpectedRootSkips(uint(rootSeqno)) 1406 if len(expectedSkips) != len(skips) { 1407 return MerkleClientError{fmt.Sprintf("Root check: wrong number of skips: expected %d, got %d.", len(expectedSkips), len(skips)), merkleErrorWrongRootSkips} 1408 } 1409 for _, expectedSkip := range expectedSkips { 1410 seqno := keybase1.Seqno(expectedSkip) 1411 _, ok := skips[seqno] 1412 if !ok { 1413 return MerkleClientError{fmt.Sprintf("Root check: unexpected skip index: wanted %d, but did not exist.", seqno), merkleErrorWrongRootSkips} 1414 } 1415 } 1416 return nil 1417 } 1418 1419 func computeExpectedRootSkips(start uint) []uint { 1420 if start <= 1 { 1421 return nil 1422 } 1423 high := int(math.Ceil(math.Log2(float64(start)))) 1424 ret := make([]uint, high) 1425 for i, skip := 0, uint(1); i < high; i, skip = i+1, skip*2 { 1426 ret[i] = start - skip 1427 } 1428 return ret 1429 } 1430 1431 func parseTriple(jw *jsonw.Wrapper) (*MerkleTriple, error) { 1432 if jw.IsNil() { 1433 return nil, nil 1434 } 1435 1436 l, err := jw.Len() 1437 if err != nil { 1438 return nil, err 1439 } 1440 if l == 0 { 1441 return nil, nil 1442 } 1443 if l == 1 { 1444 return nil, fmt.Errorf("Bad merkle 'triple', with < 2 values") 1445 } 1446 if l > 3 { 1447 return nil, fmt.Errorf("Bad merkle triple, with > 3 values") 1448 } 1449 seqno, err := jw.AtIndex(0).GetInt64() 1450 if err != nil { 1451 return nil, err 1452 } 1453 li, err := GetLinkID(jw.AtIndex(1)) 1454 if err != nil { 1455 return nil, err 1456 } 1457 1458 var si keybase1.SigIDBase 1459 if l == 3 { 1460 si, err = GetSigIDBase(jw.AtIndex(2)) 1461 if err != nil { 1462 return nil, err 1463 } 1464 } 1465 1466 return &MerkleTriple{keybase1.Seqno(seqno), li, si}, nil 1467 1468 } 1469 1470 func parseV1(jw *jsonw.Wrapper) (user *MerkleUserLeaf, err error) { 1471 var t *MerkleTriple 1472 if t, err = parseTriple(jw); err == nil { 1473 user = &MerkleUserLeaf{ 1474 public: t, 1475 private: nil, 1476 } 1477 } 1478 return 1479 } 1480 func parseV2(jw *jsonw.Wrapper) (*MerkleUserLeaf, error) { 1481 user := MerkleUserLeaf{} 1482 1483 l, err := jw.Len() 1484 if err != nil { 1485 return nil, err 1486 } 1487 if l < 2 { 1488 return nil, fmt.Errorf("No public chain.") 1489 } 1490 1491 user.public, err = parseTriple(jw.AtIndex(1)) 1492 if err != nil { 1493 return nil, err 1494 } 1495 1496 if l >= 3 { 1497 user.private, err = parseTriple(jw.AtIndex(2)) 1498 if err != nil { 1499 return nil, err 1500 } 1501 } 1502 1503 if l >= 4 && !jw.AtIndex(3).IsNil() { 1504 eldest, err := GetKID(jw.AtIndex(3)) 1505 if err != nil { 1506 return nil, err 1507 } 1508 user.eldest = eldest 1509 } 1510 1511 if l >= 5 { 1512 user.resets, err = parseV2LeafResetChainTail(jw.AtIndex(4)) 1513 if err != nil { 1514 return nil, err 1515 } 1516 } 1517 1518 return &user, nil 1519 } 1520 1521 func parseMerkleUserLeaf(m MetaContext, jw *jsonw.Wrapper, g *GlobalContext) (user *MerkleUserLeaf, err error) { 1522 m.VLogf(VLog1, "+ ParsingMerkleUserLeaf") 1523 1524 if jw == nil { 1525 m.VLogf(VLog0, "| empty leaf found; user wasn't in tree") 1526 user = &MerkleUserLeaf{} 1527 return 1528 } 1529 1530 l, err := jw.Len() 1531 if err != nil { 1532 return 1533 } 1534 if l < 2 { 1535 err = fmt.Errorf("Expected an array of length 2 or more") 1536 return 1537 } 1538 1539 v, err := jw.AtIndex(0).GetInt() 1540 1541 if err != nil { 1542 return 1543 } 1544 1545 // We messed up and didn't version the initial leafs of the tree 1546 if _, e2 := jw.AtIndex(1).GetString(); e2 == nil { 1547 v = 1 1548 } 1549 1550 switch v { 1551 case 1: 1552 user, err = parseV1(jw) 1553 case 2: 1554 user, err = parseV2(jw) 1555 default: 1556 err = fmt.Errorf("Unexpected version: %d", v) 1557 } 1558 1559 m.VLogf(VLog1, "- ParsingMerkleUserLeaf -> %v", ErrToOk(err)) 1560 return 1561 } 1562 1563 func parseMerkleTeamLeaf(m MetaContext, jw *jsonw.Wrapper, g *GlobalContext) (leaf *MerkleTeamLeaf, err error) { 1564 m.VLogf(VLog1, "+ ParsingMerkleTeamLeaf") 1565 1566 if jw == nil { 1567 m.VLogf(VLog0, "| empty leaf found; team wasn't in tree") 1568 leaf = &MerkleTeamLeaf{} 1569 return 1570 } 1571 1572 l, err := jw.Len() 1573 if err != nil { 1574 return 1575 } 1576 // length should be 4, but only use the first 3, and allow larger for forward compatibility. 1577 if l < 3 { 1578 err = fmt.Errorf("Expected an array of length >=3 but got %v", l) 1579 return 1580 } 1581 1582 v, err := jw.AtIndex(0).GetInt() 1583 if err != nil { 1584 return 1585 } 1586 if v != 2 { 1587 err = fmt.Errorf("Expected version 2 but got %v", v) 1588 return 1589 } 1590 1591 public, err := parseTriple(jw.AtIndex(1)) 1592 if err != nil { 1593 return 1594 } 1595 1596 private, err := parseTriple(jw.AtIndex(2)) 1597 if err != nil { 1598 return 1599 } 1600 1601 m.VLogf(VLog1, "- ParsingMerkleTeamLeaf -> %v", ErrToOk(err)) 1602 return &MerkleTeamLeaf{ 1603 // TeamID is filled in by the caller 1604 Public: public, 1605 Private: private, 1606 }, err 1607 } 1608 1609 func (vp *VerificationPath) verifyUsername(m MetaContext, userInfo merkleUserInfoT) (username string, err error) { 1610 if CheckUIDAgainstUsername(userInfo.uid, userInfo.username) == nil { 1611 m.VLogf(VLog1, "| Username %s mapped to %s via direct hash", userInfo.username, userInfo.uid) 1612 username = userInfo.username 1613 return 1614 } 1615 1616 m.VLogf(VLog1, "| Failed to map Username %s -> UID %s via direct hash", userInfo.username, userInfo.uid) 1617 1618 if userInfo.usernameCased != userInfo.username && strings.ToLower(userInfo.usernameCased) == userInfo.username { 1619 m.VLogf(VLog1, "| Checking cased username difference: %s v %s", userInfo.username, userInfo.usernameCased) 1620 if checkUIDAgainstCasedUsername(userInfo.uid, userInfo.usernameCased) == nil { 1621 m.VLogf(VLog1, "| Username %s mapped to %s via direct hash (w/ username casing)", userInfo.usernameCased, userInfo.uid) 1622 username = userInfo.username 1623 return 1624 } 1625 } 1626 1627 hsh := sha256.Sum256([]byte(strings.ToLower(userInfo.username))) 1628 hshS := hex.EncodeToString(hsh[:]) 1629 var leaf *jsonw.Wrapper 1630 1631 if vp.root.LegacyUIDRootHash() == nil { 1632 err = MerkleClientError{"no legacy UID root hash found in root", merkleErrorNoLegacyUIDRoot} 1633 return 1634 } 1635 1636 if leaf, err = userInfo.uidPath.VerifyPath(vp.root.LegacyUIDRootHash(), hshS); err != nil { 1637 return 1638 } 1639 1640 var uid2 keybase1.UID 1641 if uid2, err = GetUID(leaf); err != nil { 1642 return 1643 } 1644 if userInfo.uid.NotEqual(uid2) { 1645 err = UIDMismatchError{fmt.Sprintf("UID %s != %s via merkle tree", uid2, userInfo.uid)} 1646 return 1647 } 1648 1649 m.VLogf(VLog1, "| Username %s mapped to %s via Merkle lookup", userInfo.username, userInfo.uid) 1650 username = userInfo.username 1651 1652 return 1653 } 1654 1655 func (vp *VerificationPath) verifyUser(m MetaContext, uid keybase1.UID) (user *MerkleUserLeaf, err error) { 1656 curr := vp.root.RootHash() 1657 1658 var leaf *jsonw.Wrapper 1659 leaf, err = vp.path.VerifyPath(curr, uid.String()) 1660 1661 if leaf != nil && err == nil { 1662 if leaf, err = leaf.ToArray(); err != nil { 1663 msg := fmt.Sprintf("Didn't find a leaf for user in tree: %s", err) 1664 err = MerklePathNotFoundError{uid.String(), msg} 1665 } 1666 } 1667 1668 if err == nil { 1669 // noop 1670 } else if _, ok := err.(MerklePathNotFoundError); ok { 1671 m.VLogf(VLog0, fmt.Sprintf("In checking Merkle tree: %s", err)) 1672 } else { 1673 return 1674 } 1675 1676 user, err = parseMerkleUserLeaf(m, leaf, vp.G()) 1677 if user != nil { 1678 user.uid = uid 1679 } 1680 return 1681 } 1682 1683 func (vp *VerificationPath) verifyTeam(m MetaContext, teamID keybase1.TeamID) (teamLeaf *MerkleTeamLeaf, err error) { 1684 curr := vp.root.RootHash() 1685 1686 var leaf *jsonw.Wrapper 1687 leaf, err = vp.path.VerifyPath(curr, teamID.String()) 1688 1689 if leaf != nil && err == nil { 1690 if leaf, err = leaf.ToArray(); err != nil { 1691 msg := fmt.Sprintf("Didn't find a leaf for team in tree: %s", err) 1692 err = MerklePathNotFoundError{teamID.String(), msg} 1693 } 1694 } 1695 1696 if err == nil { 1697 // noop 1698 } else if _, ok := err.(MerklePathNotFoundError); ok { 1699 m.VLogf(VLog0, fmt.Sprintf("In checking Merkle tree: %s", err)) 1700 } else { 1701 return 1702 } 1703 1704 teamLeaf, err = parseMerkleTeamLeaf(m, leaf, vp.G()) 1705 if teamLeaf != nil { 1706 teamLeaf.TeamID = teamID 1707 } 1708 return 1709 } 1710 1711 func (path PathSteps) VerifyPath(curr NodeHash, uidS string) (juser *jsonw.Wrapper, err error) { 1712 1713 bpath := uidS 1714 lastTyp := 0 1715 1716 for i, step := range path { 1717 payload := step.node 1718 if !curr.Check(payload) { 1719 err = fmt.Errorf("Hash mismatch at level=%d", i) 1720 break 1721 } 1722 1723 var jw *jsonw.Wrapper 1724 jw, err = jsonw.Unmarshal([]byte(payload)) 1725 if err != nil { 1726 err = fmt.Errorf("Can't parse JSON at level=%d: %s", i, err) 1727 break 1728 } 1729 1730 plen := len(step.prefix) 1731 if plen > len(bpath) { 1732 err = fmt.Errorf("Path prefix longer than identifier: %v > %v", plen, len(bpath)) 1733 return nil, err 1734 } 1735 if plen > 0 && bpath[:plen] != step.prefix { 1736 err = fmt.Errorf("Path mismatch at level %d: %s != %s", i, bpath[:plen], step.prefix) 1737 break 1738 } 1739 1740 lastTyp, err = jw.AtKey("type").GetInt() 1741 if err != nil { 1742 err = fmt.Errorf("At level %d, failed to get a valid 'type'", i) 1743 break 1744 } 1745 1746 if lastTyp == MerkleTreeNode { 1747 if plen == 0 { 1748 err = fmt.Errorf("Empty prefix len at level=%d", i) 1749 return 1750 } 1751 curr, err = GetNodeHash(jw.AtKey("tab").AtKey(step.prefix)) 1752 if err != nil { 1753 err = MerklePathNotFoundError{uidS, err.Error()} 1754 break 1755 } 1756 juser = nil 1757 } else { 1758 juser = jw.AtKey("tab").AtKey(uidS) 1759 } 1760 } 1761 1762 if err == nil && juser == nil { 1763 err = MerklePathNotFoundError{uidS, "tree path didn't end in a leaf"} 1764 } 1765 return 1766 } 1767 1768 func (mc *MerkleClient) verifySkipSequenceAndRoot(m MetaContext, ss SkipSequence, curr *MerkleRoot, prev *MerkleRoot, apiRes *APIRes, opts MerkleOpts) (err error) { 1769 1770 defer func() { 1771 if err != nil { 1772 m.VLogf(VLog0, "| Full APIRes was: %s", apiRes.Body.MarshalToDebug()) 1773 } 1774 }() 1775 1776 // It's important to check the merkle skip sequence before verifying the root. 1777 if err = mc.verifySkipSequence(m, ss, curr, prev, opts); err != nil { 1778 return err 1779 } 1780 if opts.noSigCheck { 1781 m.VLogf(VLog0, "| noSigCheck wanted, so skipping out") 1782 return nil 1783 } 1784 return mc.verifyRootHelper(m, curr, prev, opts) 1785 } 1786 1787 func (mc *MerkleClient) LookupUser(m MetaContext, q HTTPArgs, sigHints *SigHints, opts MerkleOpts) (u *MerkleUserLeaf, err error) { 1788 1789 m.VLogf(VLog0, "+ MerkleClient.LookupUser(%v)", q) 1790 1791 if err = mc.init(m); err != nil { 1792 return nil, err 1793 } 1794 1795 root, err := mc.FetchRootFromServer(m, DefaultMerkleRootFreshness) 1796 if err != nil { 1797 return nil, err 1798 } 1799 1800 path, userInfo, _, err := mc.lookupLeafAndPathUser(m, q, sigHints, root, opts) 1801 if err != nil { 1802 return nil, err 1803 } 1804 // spot check that the user-specific path attributes were filled 1805 if userInfo.uid.IsNil() { 1806 return nil, fmt.Errorf("verification path has nil UID") 1807 } 1808 1809 if u, err = path.verifyUser(m, userInfo.uid); err != nil { 1810 return nil, err 1811 } 1812 1813 if u.username, err = path.verifyUsername(m, *userInfo); err != nil { 1814 return nil, err 1815 } 1816 1817 if err = u.resets.verifyAndLoad(m, userInfo.unverifiedResetChain); err != nil { 1818 return nil, err 1819 } 1820 1821 u.idVersion = userInfo.idVersion 1822 1823 m.VLogf(VLog0, "- MerkleClient.LookupUser(%v) -> OK", q) 1824 return u, nil 1825 } 1826 1827 func (vp *VerificationPath) verifyUserOrTeam(m MetaContext, id keybase1.UserOrTeamID) (leaf *MerkleGenericLeaf, err error) { 1828 1829 if id.IsUser() { 1830 user, err := vp.verifyUser(m, id.AsUserOrBust()) 1831 if err != nil { 1832 return nil, err 1833 } 1834 return user.MerkleGenericLeaf(), nil 1835 } 1836 1837 if id.IsTeamOrSubteam() { 1838 team, err := vp.verifyTeam(m, id.AsTeamOrBust()) 1839 if err != nil { 1840 return nil, err 1841 } 1842 return team.MerkleGenericLeaf(), nil 1843 } 1844 1845 return nil, errors.New("id was neither a user or a team") 1846 } 1847 1848 func (mc *MerkleClient) LookupLeafAtHashMeta(m MetaContext, leafID keybase1.UserOrTeamID, hm keybase1.HashMeta) (leaf *MerkleGenericLeaf, err error) { 1849 m.VLogf(VLog0, "+ MerkleClient.LookupLeafAtHashMeta(%v)", leafID) 1850 paramer := func(a *HTTPArgs) { 1851 a.Add("start_hash_meta", S{Val: hm.String()}) 1852 } 1853 checker := func(path *VerificationPath) error { 1854 if !path.root.HashMeta().Eq(hm) { 1855 return MerkleClientError{"hash meta failed to match", merkleErrorHashMeta} 1856 } 1857 return nil 1858 } 1859 leaf, _, _, err = mc.lookupLeafHistorical(m, leafID, paramer, checker, MerkleOpts{}, nil) 1860 return leaf, err 1861 } 1862 1863 func (mc *MerkleClient) checkHistoricalSeqno(s keybase1.Seqno) error { 1864 if mc.G().Env.GetRunMode() == ProductionRunMode && s < FirstProdMerkleSeqnoWithSigs { 1865 return MerkleClientError{fmt.Sprintf("cannot load seqno=%d; must load at %d or higher", s, FirstProdMerkleSeqnoWithSigs), merkleErrorAncientSeqno} 1866 } 1867 return nil 1868 } 1869 1870 type MerkleOpts struct { 1871 // All used internally 1872 noSigCheck bool 1873 historical bool 1874 isUser bool 1875 1876 // Used externally 1877 NoServerPolling bool 1878 } 1879 1880 func (mc *MerkleClient) LookupLeafAtSeqno(m MetaContext, leafID keybase1.UserOrTeamID, s keybase1.Seqno) (leaf *MerkleGenericLeaf, root *MerkleRoot, err error) { 1881 leaf, root, _, err = mc.lookupLeafAtSeqno(m, leafID, s, MerkleOpts{}, nil /* processHiddenResponseFunc */) 1882 return leaf, root, err 1883 } 1884 1885 func (mc *MerkleClient) LookupLeafAtSeqnoForAudit(m MetaContext, leafID keybase1.UserOrTeamID, s keybase1.Seqno, processHiddenResponseFunc ProcessHiddenRespFunc) (leaf *MerkleGenericLeaf, root *MerkleRoot, hiddenResp *MerkleHiddenResponse, err error) { 1886 return mc.lookupLeafAtSeqno(m, leafID, s, MerkleOpts{noSigCheck: true}, processHiddenResponseFunc) 1887 } 1888 1889 func (mc *MerkleClient) lookupLeafAtSeqno(m MetaContext, leafID keybase1.UserOrTeamID, s keybase1.Seqno, opts MerkleOpts, processHiddenResponseFunc ProcessHiddenRespFunc) (leaf *MerkleGenericLeaf, root *MerkleRoot, hiddenResp *MerkleHiddenResponse, err error) { 1890 m.VLogf(VLog0, "+ MerkleClient.lookupLeafAtSeqno(%v,%v,%v)", leafID, s, opts) 1891 if err = mc.checkHistoricalSeqno(s); err != nil { 1892 return nil, nil, nil, err 1893 } 1894 paramer := func(a *HTTPArgs) { 1895 a.Add("start_seqno", I{Val: int(s)}) 1896 if opts.noSigCheck { 1897 a.Add("no_root_sigs", B{Val: true}) 1898 } 1899 } 1900 // Since we are looking up a leaf at a specific seqno, ensure we have root 1901 // at least as recent as that seqno. 1902 _, err = mc.FetchRootFromServerByMinSeqno(m, s) 1903 if err != nil { 1904 return nil, nil, nil, err 1905 } 1906 1907 checker := func(path *VerificationPath) error { 1908 if path.root.Seqno() == nil { 1909 return MerkleClientError{"no such seqno was found", merkleErrorNotFound} 1910 } 1911 if *path.root.Seqno() != s { 1912 return MerkleClientError{"seqno mismatch", merkleErrorBadSeqno} 1913 } 1914 return nil 1915 } 1916 return mc.lookupLeafHistorical(m, leafID, paramer, checker, opts, processHiddenResponseFunc) 1917 } 1918 1919 func (mc *MerkleClient) LookupRootAtSeqno(m MetaContext, s keybase1.Seqno) (root *MerkleRoot, err error) { 1920 defer m.VTrace(VLog0, fmt.Sprintf("LookupRootAtSeqno(%d)", s), &err)() 1921 _, root, err = mc.LookupLeafAtSeqno(m, keybase1.UserOrTeamID(""), s) 1922 return root, err 1923 } 1924 1925 func (mc *MerkleClient) lookupLeafHistorical(m MetaContext, leafID keybase1.UserOrTeamID, paramer func(*HTTPArgs), checker func(*VerificationPath) error, opts MerkleOpts, processHiddenResponseFunc ProcessHiddenRespFunc) (leaf *MerkleGenericLeaf, root *MerkleRoot, hiddenResp *MerkleHiddenResponse, err error) { 1926 opts.historical = true 1927 1928 var path *VerificationPath 1929 var apiRes *APIRes 1930 1931 if err = mc.init(m); err != nil { 1932 return nil, nil, nil, err 1933 } 1934 1935 // The most current root we got. This might be slightly out of date, but all 1936 // we really care is that it points back to another historical root, which 1937 // should be before currentRoot. If it's not, we'll refresh currentRoot in 1938 // the process. 1939 currentRoot := mc.LastRoot(m) 1940 1941 q := NewHTTPArgs() 1942 if leafID.IsNil() { 1943 q.Add("no_leaf", B{Val: true}) 1944 } else { 1945 q.Add("leaf_id", S{Val: leafID.String()}) 1946 } 1947 paramer(&q) 1948 1949 if apiRes, currentRoot, err = mc.lookupLeafAndPathHelper(m, q, nil, currentRoot, opts); err != nil { 1950 return nil, nil, nil, err 1951 } 1952 1953 path, err = mc.readPathFromAPIRes(m, apiRes, opts) 1954 if err != nil { 1955 return nil, nil, nil, err 1956 } 1957 resSeqno, err := apiRes.Body.AtKey("root").AtKey("seqno").GetInt64() 1958 if err != nil { 1959 return nil, nil, nil, err 1960 } 1961 if keybase1.Seqno(resSeqno) == *currentRoot.Seqno() { 1962 path.root = currentRoot 1963 } else { 1964 path.root, err = mc.readAndCheckRootFromAPIRes(m, apiRes, currentRoot, opts) 1965 if err != nil { 1966 return nil, nil, nil, err 1967 } 1968 } 1969 1970 if err = checker(path); err != nil { 1971 return nil, nil, nil, err 1972 } 1973 1974 if !leafID.IsNil() { 1975 leaf, err = path.verifyUserOrTeam(m, leafID) 1976 if err != nil { 1977 return nil, nil, nil, err 1978 } 1979 1980 if processHiddenResponseFunc != nil { 1981 hiddenResp, err = processHiddenResponseFunc(m, leafID.AsTeamOrBust(), apiRes, path.root.BlindMerkleRootHash()) 1982 if err != nil { 1983 return nil, nil, nil, err 1984 } 1985 } 1986 } 1987 1988 return leaf, path.root, hiddenResp, nil 1989 } 1990 1991 func (mc *MerkleClient) LookupTeamWithHidden(m MetaContext, teamID keybase1.TeamID, processHiddenRespFunc ProcessHiddenRespFunc) (leaf *MerkleTeamLeaf, hiddenResp *MerkleHiddenResponse, lastMerkleRoot *MerkleRoot, err error) { 1992 // Copied from LookupUser. These methods should be kept relatively in sync. 1993 return mc.lookupTeam(m, teamID, processHiddenRespFunc) 1994 } 1995 1996 func (mc *MerkleClient) LookupTeam(m MetaContext, teamID keybase1.TeamID) (leaf *MerkleTeamLeaf, err error) { 1997 // Copied from LookupUser. These methods should be kept relatively in sync. 1998 leaf, _, _, err = mc.lookupTeam(m, teamID, nil) 1999 return leaf, err 2000 } 2001 2002 type MerkleHiddenResponseType uint8 2003 2004 const ( 2005 // the server did not include any hidden chain data 2006 MerkleHiddenResponseTypeNONE MerkleHiddenResponseType = 1 2007 2008 // Removed (not serving proofs anymore) 2009 // the server provided a proof of absence (or inclusion with an empty leaf) for 2010 // the requested key 2011 // MerkleHiddenResponseTypeABSENCEPROOF MerkleHiddenResponseType = 2 2012 2013 // the server provided a valid inclusion or exclusion proof for the returned leaf in the tree 2014 // (however, we are currently not providing a proof) 2015 MerkleHiddenResponseTypeOK MerkleHiddenResponseType = 3 2016 2017 // All hidden checks should be skipped as the feature flag is off 2018 MerkleHiddenResponseTypeFLAGOFF MerkleHiddenResponseType = 127 2019 ) 2020 2021 type MerkleHiddenResponse struct { 2022 RespType MerkleHiddenResponseType `json:"resp_type"` 2023 UncommittedSeqno keybase1.Seqno `json:"uncommitted_seqno"` 2024 } 2025 2026 func (m *MerkleHiddenResponse) GetUncommittedSeqno() keybase1.Seqno { 2027 if m == nil { 2028 return 0 2029 } 2030 return m.UncommittedSeqno 2031 } 2032 2033 type ProcessHiddenRespFunc func(m MetaContext, teamID keybase1.TeamID, apiRes *APIRes, blindRootHash string) (*MerkleHiddenResponse, error) 2034 2035 func (mc *MerkleClient) lookupTeam(m MetaContext, teamID keybase1.TeamID, processHiddenResponseFunc ProcessHiddenRespFunc) (leaf *MerkleTeamLeaf, hiddenResp *MerkleHiddenResponse, lastMerkleRoot *MerkleRoot, err error) { 2036 2037 m.VLogf(VLog0, "+ MerkleClient.LookupTeam(%v)", teamID) 2038 2039 var path *VerificationPath 2040 var apiRes *APIRes 2041 var opts MerkleOpts 2042 2043 if err = mc.init(m); err != nil { 2044 return nil, nil, nil, err 2045 } 2046 2047 root, err := mc.FetchRootFromServer(m, DefaultMerkleRootFreshness) 2048 if err != nil { 2049 return nil, nil, nil, err 2050 } 2051 q := NewHTTPArgs() 2052 q.Add("leaf_id", S{Val: teamID.String()}) 2053 2054 if path, apiRes, err = mc.lookupLeafAndPath(m, q, root, nil, opts); err != nil { 2055 return nil, nil, nil, err 2056 } 2057 2058 if leaf, err = path.verifyTeam(m, teamID); err != nil { 2059 return nil, nil, nil, err 2060 } 2061 2062 if processHiddenResponseFunc != nil { 2063 hiddenResp, err = processHiddenResponseFunc(m, teamID, apiRes, path.root.BlindMerkleRootHash()) 2064 if err != nil { 2065 return nil, nil, nil, err 2066 } 2067 } 2068 2069 m.VLogf(VLog0, "- MerkleClient.LookupTeam(%v) -> OK", teamID) 2070 return leaf, hiddenResp, path.root, err 2071 } 2072 2073 func (mr *MerkleRoot) ToSigJSON() (ret *jsonw.Wrapper) { 2074 2075 ret = jsonw.NewDictionary() 2076 _ = ret.SetKey("seqno", jsonw.NewInt(int(*mr.Seqno()))) 2077 _ = ret.SetKey("ctime", jsonw.NewInt64(mr.Ctime())) 2078 _ = ret.SetKey("hash", jsonw.NewString(mr.RootHash().String())) 2079 _ = ret.SetKey("hash_meta", jsonw.NewString(mr.ShortHash().String())) 2080 2081 return 2082 } 2083 2084 func (mr *MerkleRoot) ToInfo() chat1.MerkleRoot { 2085 return chat1.MerkleRoot{ 2086 Seqno: int64(*mr.Seqno()), 2087 Hash: mr.RootHash().bytes(), 2088 } 2089 } 2090 2091 func (mr *MerkleRoot) ToMerkleRootV2() keybase1.MerkleRootV2 { 2092 return keybase1.MerkleRootV2{ 2093 Seqno: *mr.Seqno(), 2094 HashMeta: mr.HashMeta(), 2095 } 2096 } 2097 2098 func (mc *MerkleClient) LastRootToSigJSON(m MetaContext) (ret *jsonw.Wrapper, err error) { 2099 // Lazy-init, only when needed. 2100 if err = mc.init(m); err == nil { 2101 mc.RLock() 2102 if mc.lastRoot != nil { 2103 ret = mc.lastRoot.ToSigJSON() 2104 } 2105 mc.RUnlock() 2106 } 2107 return 2108 } 2109 2110 func (mul *MerkleUserLeaf) MatchUser(u *User, uid keybase1.UID, nun NormalizedUsername) (err error) { 2111 if mul.username != u.GetName() { 2112 err = MerkleClashError{fmt.Sprintf("vs loaded object: username %s != %s", mul.username, u.GetName())} 2113 } else if mul.uid.NotEqual(u.GetUID()) { 2114 err = MerkleClientError{fmt.Sprintf("vs loaded object: UID %s != %s", mul.uid, u.GetUID()), merkleErrorUIDMismatch} 2115 } else if !nun.IsNil() && !NewNormalizedUsername(mul.username).Eq(nun) { 2116 err = MerkleClashError{fmt.Sprintf("vs given arg: username %s != %s", mul.username, nun)} 2117 } else if uid.NotEqual(mul.uid) { 2118 err = MerkleClashError{fmt.Sprintf("vs given arg: UID %s != %s", uid, mul.uid)} 2119 } 2120 return 2121 } 2122 2123 func (mt MerkleTriple) Less(mt2 MerkleTriple) bool { 2124 return mt.Seqno < mt2.Seqno 2125 } 2126 2127 func GetMerkleTriple(jw *jsonw.Wrapper) (ret *MerkleTriple, err error) { 2128 var tmp MerkleTriple 2129 if err = jw.UnmarshalAgain(&tmp); err != nil { 2130 ret = &tmp 2131 } 2132 return ret, err 2133 } 2134 2135 func (mr MerkleRoot) ShallowCopy() *MerkleRoot { 2136 return &mr 2137 } 2138 2139 func (mr *MerkleRoot) Seqno() *keybase1.Seqno { 2140 if mr == nil { 2141 return nil 2142 } 2143 tmp := mr.payload.seqno() 2144 return &tmp 2145 } 2146 2147 func (mr *MerkleRoot) RootHash() NodeHash { 2148 if mr == nil { 2149 return nil 2150 } 2151 return mr.payload.rootHash() 2152 } 2153 2154 func (mr *MerkleRoot) LegacyUIDRootHash() NodeHash { 2155 if mr == nil { 2156 return nil 2157 } 2158 return mr.payload.legacyUIDRootHash() 2159 } 2160 2161 func (mr *MerkleRoot) PvlHash() string { 2162 if mr == nil { 2163 return "" 2164 } 2165 return mr.payload.pvlHash() 2166 } 2167 2168 func (mr *MerkleRoot) ProofServicesHash() string { 2169 if mr == nil { 2170 return "" 2171 } 2172 return mr.payload.proofServicesHash() 2173 } 2174 2175 func (mr *MerkleRoot) ExternalURLHash() string { 2176 if mr == nil { 2177 return "" 2178 } 2179 return mr.payload.externalURLHash() 2180 } 2181 2182 func (mr *MerkleRoot) BlindMerkleRootHash() string { 2183 if mr == nil { 2184 return "" 2185 } 2186 return mr.payload.blindMerkleRootHash() 2187 } 2188 2189 func (mr *MerkleRoot) SkipToSeqno(s keybase1.Seqno) NodeHash { 2190 if mr == nil { 2191 return nil 2192 } 2193 return mr.payload.skipToSeqno(s) 2194 } 2195 2196 func (mr *MerkleRoot) Ctime() int64 { 2197 if mr == nil { 2198 return 0 2199 } 2200 return mr.payload.ctime() 2201 } 2202 2203 func (mr *MerkleRoot) Fetched() time.Time { 2204 if mr == nil { 2205 return time.Time{} 2206 } 2207 return mr.fetched 2208 } 2209 2210 func (mr *MerkleRoot) KBFSPrivate() (keybase1.KBFSRootHash, *keybase1.Seqno) { 2211 if mr == nil { 2212 return nil, nil 2213 } 2214 return mr.payload.kbfsPrivate() 2215 } 2216 2217 func (mr *MerkleRoot) KBFSPublic() (keybase1.KBFSRootHash, *keybase1.Seqno) { 2218 if mr == nil { 2219 return nil, nil 2220 } 2221 return mr.payload.kbfsPublic() 2222 } 2223 2224 func (mr *MerkleRoot) KBFSPrivateTeam() (keybase1.KBFSRootHash, *keybase1.Seqno) { 2225 if mr == nil { 2226 return nil, nil 2227 } 2228 return mr.payload.kbfsPrivateTeam() 2229 } 2230 2231 func (mrp MerkleRootPayload) skipToSeqno(s keybase1.Seqno) NodeHash { 2232 if mrp.unpacked.Body.Skips == nil { 2233 return nil 2234 } 2235 return mrp.unpacked.Body.Skips[s] 2236 } 2237 2238 func (mrp MerkleRootPayload) seqno() keybase1.Seqno { return mrp.unpacked.Body.Seqno } 2239 func (mrp MerkleRootPayload) rootHash() NodeHash { return mrp.unpacked.Body.Root } 2240 func (mrp MerkleRootPayload) legacyUIDRootHash() NodeHash { return mrp.unpacked.Body.LegacyUIDRoot } 2241 func (mrp MerkleRootPayload) pvlHash() string { return mrp.unpacked.Body.PvlHash } 2242 func (mrp MerkleRootPayload) proofServicesHash() string { return mrp.unpacked.Body.ProofServicesHash } 2243 func (mrp MerkleRootPayload) externalURLHash() string { return mrp.unpacked.Body.ExternalURLHash } 2244 func (mrp MerkleRootPayload) blindMerkleRootHash() string { 2245 return mrp.unpacked.Body.BlindMerkleRootHash 2246 } 2247 func (mrp MerkleRootPayload) ctime() int64 { return mrp.unpacked.Ctime } 2248 func (mrp MerkleRootPayload) kbfsPrivate() (keybase1.KBFSRootHash, *keybase1.Seqno) { 2249 return mrp.unpacked.Body.Kbfs.Private.Root, mrp.unpacked.Body.Kbfs.Private.Version 2250 } 2251 func (mrp MerkleRootPayload) kbfsPublic() (keybase1.KBFSRootHash, *keybase1.Seqno) { 2252 return mrp.unpacked.Body.Kbfs.Public.Root, mrp.unpacked.Body.Kbfs.Public.Version 2253 } 2254 func (mrp MerkleRootPayload) kbfsPrivateTeam() (keybase1.KBFSRootHash, *keybase1.Seqno) { 2255 return mrp.unpacked.Body.Kbfs.PrivateTeam.Root, mrp.unpacked.Body.Kbfs.PrivateTeam.Version 2256 } 2257 2258 func (mc *MerkleClient) CanExamineHistoricalRoot(m MetaContext, q keybase1.Seqno) bool { 2259 chk := mc.FirstExaminableHistoricalRoot(m) 2260 if chk == nil { 2261 return true 2262 } 2263 return q >= *chk 2264 }