.gitignore added
[dotfiles/.git] / .config / coc / extensions / coc-go-data / tools / pkg / mod / github.com / google / go-cmp@v0.5.4 / cmp / report_references.go
diff --git a/.config/coc/extensions/coc-go-data/tools/pkg/mod/github.com/google/go-cmp@v0.5.4/cmp/report_references.go b/.config/coc/extensions/coc-go-data/tools/pkg/mod/github.com/google/go-cmp@v0.5.4/cmp/report_references.go
new file mode 100644 (file)
index 0000000..be31b33
--- /dev/null
@@ -0,0 +1,264 @@
+// Copyright 2020, The Go 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 cmp
+
+import (
+       "fmt"
+       "reflect"
+       "strings"
+
+       "github.com/google/go-cmp/cmp/internal/flags"
+       "github.com/google/go-cmp/cmp/internal/value"
+)
+
+const (
+       pointerDelimPrefix = "⟪"
+       pointerDelimSuffix = "⟫"
+)
+
+// formatPointer prints the address of the pointer.
+func formatPointer(p value.Pointer, withDelims bool) string {
+       v := p.Uintptr()
+       if flags.Deterministic {
+               v = 0xdeadf00f // Only used for stable testing purposes
+       }
+       if withDelims {
+               return pointerDelimPrefix + formatHex(uint64(v)) + pointerDelimSuffix
+       }
+       return formatHex(uint64(v))
+}
+
+// pointerReferences is a stack of pointers visited so far.
+type pointerReferences [][2]value.Pointer
+
+func (ps *pointerReferences) PushPair(vx, vy reflect.Value, d diffMode, deref bool) (pp [2]value.Pointer) {
+       if deref && vx.IsValid() {
+               vx = vx.Addr()
+       }
+       if deref && vy.IsValid() {
+               vy = vy.Addr()
+       }
+       switch d {
+       case diffUnknown, diffIdentical:
+               pp = [2]value.Pointer{value.PointerOf(vx), value.PointerOf(vy)}
+       case diffRemoved:
+               pp = [2]value.Pointer{value.PointerOf(vx), value.Pointer{}}
+       case diffInserted:
+               pp = [2]value.Pointer{value.Pointer{}, value.PointerOf(vy)}
+       }
+       *ps = append(*ps, pp)
+       return pp
+}
+
+func (ps *pointerReferences) Push(v reflect.Value) (p value.Pointer, seen bool) {
+       p = value.PointerOf(v)
+       for _, pp := range *ps {
+               if p == pp[0] || p == pp[1] {
+                       return p, true
+               }
+       }
+       *ps = append(*ps, [2]value.Pointer{p, p})
+       return p, false
+}
+
+func (ps *pointerReferences) Pop() {
+       *ps = (*ps)[:len(*ps)-1]
+}
+
+// trunkReferences is metadata for a textNode indicating that the sub-tree
+// represents the value for either pointer in a pair of references.
+type trunkReferences struct{ pp [2]value.Pointer }
+
+// trunkReference is metadata for a textNode indicating that the sub-tree
+// represents the value for the given pointer reference.
+type trunkReference struct{ p value.Pointer }
+
+// leafReference is metadata for a textNode indicating that the value is
+// truncated as it refers to another part of the tree (i.e., a trunk).
+type leafReference struct{ p value.Pointer }
+
+func wrapTrunkReferences(pp [2]value.Pointer, s textNode) textNode {
+       switch {
+       case pp[0].IsNil():
+               return &textWrap{Value: s, Metadata: trunkReference{pp[1]}}
+       case pp[1].IsNil():
+               return &textWrap{Value: s, Metadata: trunkReference{pp[0]}}
+       case pp[0] == pp[1]:
+               return &textWrap{Value: s, Metadata: trunkReference{pp[0]}}
+       default:
+               return &textWrap{Value: s, Metadata: trunkReferences{pp}}
+       }
+}
+func wrapTrunkReference(p value.Pointer, printAddress bool, s textNode) textNode {
+       var prefix string
+       if printAddress {
+               prefix = formatPointer(p, true)
+       }
+       return &textWrap{Prefix: prefix, Value: s, Metadata: trunkReference{p}}
+}
+func makeLeafReference(p value.Pointer, printAddress bool) textNode {
+       out := &textWrap{Prefix: "(", Value: textEllipsis, Suffix: ")"}
+       var prefix string
+       if printAddress {
+               prefix = formatPointer(p, true)
+       }
+       return &textWrap{Prefix: prefix, Value: out, Metadata: leafReference{p}}
+}
+
+// resolveReferences walks the textNode tree searching for any leaf reference
+// metadata and resolves each against the corresponding trunk references.
+// Since pointer addresses in memory are not particularly readable to the user,
+// it replaces each pointer value with an arbitrary and unique reference ID.
+func resolveReferences(s textNode) {
+       var walkNodes func(textNode, func(textNode))
+       walkNodes = func(s textNode, f func(textNode)) {
+               f(s)
+               switch s := s.(type) {
+               case *textWrap:
+                       walkNodes(s.Value, f)
+               case textList:
+                       for _, r := range s {
+                               walkNodes(r.Value, f)
+                       }
+               }
+       }
+
+       // Collect all trunks and leaves with reference metadata.
+       var trunks, leaves []*textWrap
+       walkNodes(s, func(s textNode) {
+               if s, ok := s.(*textWrap); ok {
+                       switch s.Metadata.(type) {
+                       case leafReference:
+                               leaves = append(leaves, s)
+                       case trunkReference, trunkReferences:
+                               trunks = append(trunks, s)
+                       }
+               }
+       })
+
+       // No leaf references to resolve.
+       if len(leaves) == 0 {
+               return
+       }
+
+       // Collect the set of all leaf references to resolve.
+       leafPtrs := make(map[value.Pointer]bool)
+       for _, leaf := range leaves {
+               leafPtrs[leaf.Metadata.(leafReference).p] = true
+       }
+
+       // Collect the set of trunk pointers that are always paired together.
+       // This allows us to assign a single ID to both pointers for brevity.
+       // If a pointer in a pair ever occurs by itself or as a different pair,
+       // then the pair is broken.
+       pairedTrunkPtrs := make(map[value.Pointer]value.Pointer)
+       unpair := func(p value.Pointer) {
+               if !pairedTrunkPtrs[p].IsNil() {
+                       pairedTrunkPtrs[pairedTrunkPtrs[p]] = value.Pointer{} // invalidate other half
+               }
+               pairedTrunkPtrs[p] = value.Pointer{} // invalidate this half
+       }
+       for _, trunk := range trunks {
+               switch p := trunk.Metadata.(type) {
+               case trunkReference:
+                       unpair(p.p) // standalone pointer cannot be part of a pair
+               case trunkReferences:
+                       p0, ok0 := pairedTrunkPtrs[p.pp[0]]
+                       p1, ok1 := pairedTrunkPtrs[p.pp[1]]
+                       switch {
+                       case !ok0 && !ok1:
+                               // Register the newly seen pair.
+                               pairedTrunkPtrs[p.pp[0]] = p.pp[1]
+                               pairedTrunkPtrs[p.pp[1]] = p.pp[0]
+                       case ok0 && ok1 && p0 == p.pp[1] && p1 == p.pp[0]:
+                               // Exact pair already seen; do nothing.
+                       default:
+                               // Pair conflicts with some other pair; break all pairs.
+                               unpair(p.pp[0])
+                               unpair(p.pp[1])
+                       }
+               }
+       }
+
+       // Correlate each pointer referenced by leaves to a unique identifier,
+       // and print the IDs for each trunk that matches those pointers.
+       var nextID uint
+       ptrIDs := make(map[value.Pointer]uint)
+       newID := func() uint {
+               id := nextID
+               nextID++
+               return id
+       }
+       for _, trunk := range trunks {
+               switch p := trunk.Metadata.(type) {
+               case trunkReference:
+                       if print := leafPtrs[p.p]; print {
+                               id, ok := ptrIDs[p.p]
+                               if !ok {
+                                       id = newID()
+                                       ptrIDs[p.p] = id
+                               }
+                               trunk.Prefix = updateReferencePrefix(trunk.Prefix, formatReference(id))
+                       }
+               case trunkReferences:
+                       print0 := leafPtrs[p.pp[0]]
+                       print1 := leafPtrs[p.pp[1]]
+                       if print0 || print1 {
+                               id0, ok0 := ptrIDs[p.pp[0]]
+                               id1, ok1 := ptrIDs[p.pp[1]]
+                               isPair := pairedTrunkPtrs[p.pp[0]] == p.pp[1] && pairedTrunkPtrs[p.pp[1]] == p.pp[0]
+                               if isPair {
+                                       var id uint
+                                       assert(ok0 == ok1) // must be seen together or not at all
+                                       if ok0 {
+                                               assert(id0 == id1) // must have the same ID
+                                               id = id0
+                                       } else {
+                                               id = newID()
+                                               ptrIDs[p.pp[0]] = id
+                                               ptrIDs[p.pp[1]] = id
+                                       }
+                                       trunk.Prefix = updateReferencePrefix(trunk.Prefix, formatReference(id))
+                               } else {
+                                       if print0 && !ok0 {
+                                               id0 = newID()
+                                               ptrIDs[p.pp[0]] = id0
+                                       }
+                                       if print1 && !ok1 {
+                                               id1 = newID()
+                                               ptrIDs[p.pp[1]] = id1
+                                       }
+                                       switch {
+                                       case print0 && print1:
+                                               trunk.Prefix = updateReferencePrefix(trunk.Prefix, formatReference(id0)+","+formatReference(id1))
+                                       case print0:
+                                               trunk.Prefix = updateReferencePrefix(trunk.Prefix, formatReference(id0))
+                                       case print1:
+                                               trunk.Prefix = updateReferencePrefix(trunk.Prefix, formatReference(id1))
+                                       }
+                               }
+                       }
+               }
+       }
+
+       // Update all leaf references with the unique identifier.
+       for _, leaf := range leaves {
+               if id, ok := ptrIDs[leaf.Metadata.(leafReference).p]; ok {
+                       leaf.Prefix = updateReferencePrefix(leaf.Prefix, formatReference(id))
+               }
+       }
+}
+
+func formatReference(id uint) string {
+       return fmt.Sprintf("ref#%d", id)
+}
+
+func updateReferencePrefix(prefix, ref string) string {
+       if prefix == "" {
+               return pointerDelimPrefix + ref + pointerDelimSuffix
+       }
+       suffix := strings.TrimPrefix(prefix, pointerDelimPrefix)
+       return pointerDelimPrefix + ref + ": " + suffix
+}