diff --git a/cmp/compare.go b/cmp/compare.go
index 2294579..4fff3fd 100644
--- a/cmp/compare.go
+++ b/cmp/compare.go
@@ -31,6 +31,7 @@
 	"reflect"
 
 	"github.com/google/go-cmp/cmp/internal/diff"
+	"github.com/google/go-cmp/cmp/internal/value"
 )
 
 // BUG: Maps with keys containing NaN values cannot be properly compared due to
@@ -442,7 +443,7 @@
 	step := &mapIndex{pathStep: pathStep{t.Elem()}}
 	s.curPath.push(step)
 	defer s.curPath.pop()
-	for _, k := range sortKeys(append(vx.MapKeys(), vy.MapKeys()...)) {
+	for _, k := range value.SortKeys(append(vx.MapKeys(), vy.MapKeys()...)) {
 		step.key = k
 		vvx := vx.MapIndex(k)
 		vvy := vy.MapIndex(k)
diff --git a/cmp/compare_test.go b/cmp/compare_test.go
index 11c30c2..d7d80d5 100644
--- a/cmp/compare_test.go
+++ b/cmp/compare_test.go
@@ -1438,8 +1438,8 @@
 	-: "southbay2"
 	+: "southbay"
 *{teststructs.Eagle}.Dreamers[1].Animal[0].(teststructs.Goat).Immutable.State:
-	-: 6
-	+: 5
+	-: testprotos.Goat_States(6)
+	+: testprotos.Goat_States(5)
 {teststructs.Eagle}.Slaps[0].Immutable.MildSlap:
 	-: false
 	+: true
@@ -1652,8 +1652,8 @@
 	-: &teststructs.MockTable{state: []string{"a", "c"}}
 	+: &teststructs.MockTable{state: []string{"a", "b", "c"}}
 {teststructs.Dirt}.Discord:
-	-: 554
-	+: 500
+	-: teststructs.DiscordState(554)
+	+: teststructs.DiscordState(500)
 λ({teststructs.Dirt}.Proto):
 	-: "blah"
 	+: "proto"
@@ -1751,10 +1751,10 @@
 	-: 0x04
 	+: 0x03
 {teststructs.Cartel}.poisons[0].poisonType:
-	-: 1
-	+: 5
+	-: testprotos.PoisonType(1)
+	+: testprotos.PoisonType(5)
 {teststructs.Cartel}.poisons[1->?]:
-	-: &teststructs.Poison{poisonType: 2, manufactuer: "acme2"}
+	-: &teststructs.Poison{poisonType: testprotos.PoisonType(2), manufactuer: "acme2"}
 	+: <non-existent>`,
 	}}
 }
diff --git a/cmp/internal/value/format.go b/cmp/internal/value/format.go
new file mode 100644
index 0000000..e26395d
--- /dev/null
+++ b/cmp/internal/value/format.go
@@ -0,0 +1,258 @@
+// Copyright 2017, 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.md file.
+
+package value
+
+import (
+	"fmt"
+	"reflect"
+	"strings"
+	"unicode"
+	"unicode/utf8"
+)
+
+// formatFakePointers controls whether to substitute pointer addresses with nil.
+// This is used for deterministic testing.
+var formatFakePointers = false
+
+var stringerIface = reflect.TypeOf((*fmt.Stringer)(nil)).Elem()
+
+// Format formats the value v as a string.
+//
+// This is similar to fmt.Sprintf("%+v", v) except this:
+//	* Prints the type unless it can be elided
+//	* Avoids printing struct fields that are zero
+//	* Prints a nil-slice as being nil, not empty
+//	* Prints map entries in deterministic order
+func Format(v reflect.Value, useStringer bool) string {
+	return formatAny(v, formatConfig{useStringer, true, true, !formatFakePointers}, nil)
+}
+
+type formatConfig struct {
+	useStringer    bool // Should the String method be used if available?
+	printType      bool // Should we print the type before the value?
+	followPointers bool // Should we recursively follow pointers?
+	realPointers   bool // Should we print the real address of pointers?
+}
+
+func formatAny(v reflect.Value, conf formatConfig, visited map[uintptr]bool) string {
+	// TODO: Should this be a multi-line printout in certain situations?
+
+	if !v.IsValid() {
+		return "<non-existent>"
+	}
+	if conf.useStringer && v.Type().Implements(stringerIface) {
+		if v.Kind() == reflect.Ptr && v.IsNil() {
+			return "<nil>"
+		}
+		return fmt.Sprintf("%q", v.Interface().(fmt.Stringer).String())
+	}
+
+	switch v.Kind() {
+	case reflect.Bool:
+		return formatPrimitive(v.Type(), v.Bool(), conf)
+	case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
+		return formatPrimitive(v.Type(), v.Int(), conf)
+	case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr:
+		if v.Type().PkgPath() == "" || v.Kind() == reflect.Uintptr {
+			// Unnamed uints are usually bytes or words, so use hexadecimal.
+			return formatPrimitive(v.Type(), formatHex(v.Uint()), conf)
+		}
+		return formatPrimitive(v.Type(), v.Uint(), conf)
+	case reflect.Float32, reflect.Float64:
+		return formatPrimitive(v.Type(), v.Float(), conf)
+	case reflect.Complex64, reflect.Complex128:
+		return formatPrimitive(v.Type(), v.Complex(), conf)
+	case reflect.String:
+		return formatPrimitive(v.Type(), fmt.Sprintf("%q", v), conf)
+	case reflect.UnsafePointer, reflect.Chan, reflect.Func:
+		return formatPointer(v, conf)
+	case reflect.Ptr:
+		if v.IsNil() {
+			if conf.printType {
+				return fmt.Sprintf("(%v)(nil)", v.Type())
+			}
+			return "<nil>"
+		}
+		if visited[v.Pointer()] || !conf.followPointers {
+			return formatPointer(v, conf)
+		}
+		visited = insertPointer(visited, v.Pointer())
+		return "&" + formatAny(v.Elem(), conf, visited)
+	case reflect.Interface:
+		if v.IsNil() {
+			if conf.printType {
+				return fmt.Sprintf("%v(nil)", v.Type())
+			}
+			return "<nil>"
+		}
+		return formatAny(v.Elem(), conf, visited)
+	case reflect.Slice:
+		if v.IsNil() {
+			if conf.printType {
+				return fmt.Sprintf("%v(nil)", v.Type())
+			}
+			return "<nil>"
+		}
+		if visited[v.Pointer()] {
+			return formatPointer(v, conf)
+		}
+		visited = insertPointer(visited, v.Pointer())
+		fallthrough
+	case reflect.Array:
+		var ss []string
+		subConf := conf
+		subConf.printType = v.Type().Elem().Kind() == reflect.Interface
+		for i := 0; i < v.Len(); i++ {
+			s := formatAny(v.Index(i), subConf, visited)
+			ss = append(ss, s)
+		}
+		s := fmt.Sprintf("{%s}", strings.Join(ss, ", "))
+		if conf.printType {
+			return v.Type().String() + s
+		}
+		return s
+	case reflect.Map:
+		if v.IsNil() {
+			if conf.printType {
+				return fmt.Sprintf("%v(nil)", v.Type())
+			}
+			return "<nil>"
+		}
+		if visited[v.Pointer()] {
+			return formatPointer(v, conf)
+		}
+		visited = insertPointer(visited, v.Pointer())
+
+		var ss []string
+		subConf := conf
+		subConf.printType = v.Type().Elem().Kind() == reflect.Interface
+		for _, k := range SortKeys(v.MapKeys()) {
+			sk := formatAny(k, formatConfig{realPointers: conf.realPointers}, visited)
+			sv := formatAny(v.MapIndex(k), subConf, visited)
+			ss = append(ss, fmt.Sprintf("%s: %s", sk, sv))
+		}
+		s := fmt.Sprintf("{%s}", strings.Join(ss, ", "))
+		if conf.printType {
+			return v.Type().String() + s
+		}
+		return s
+	case reflect.Struct:
+		var ss []string
+		subConf := conf
+		subConf.printType = true
+		for i := 0; i < v.NumField(); i++ {
+			vv := v.Field(i)
+			if isZero(vv) {
+				continue // Elide zero value fields
+			}
+			name := v.Type().Field(i).Name
+			subConf.useStringer = conf.useStringer && isExported(name)
+			s := formatAny(vv, subConf, visited)
+			ss = append(ss, fmt.Sprintf("%s: %s", name, s))
+		}
+		s := fmt.Sprintf("{%s}", strings.Join(ss, ", "))
+		if conf.printType {
+			return v.Type().String() + s
+		}
+		return s
+	default:
+		panic(fmt.Sprintf("%v kind not handled", v.Kind()))
+	}
+}
+
+func formatPrimitive(t reflect.Type, v interface{}, conf formatConfig) string {
+	if conf.printType && t.PkgPath() != "" {
+		return fmt.Sprintf("%v(%v)", t, v)
+	}
+	return fmt.Sprintf("%v", v)
+}
+
+func formatPointer(v reflect.Value, conf formatConfig) string {
+	p := v.Pointer()
+	if !conf.realPointers {
+		p = 0 // For deterministic printing purposes
+	}
+	s := formatHex(uint64(p))
+	if conf.printType {
+		return fmt.Sprintf("(%v)(%s)", v.Type(), s)
+	}
+	return s
+}
+
+func formatHex(u uint64) string {
+	var f string
+	switch {
+	case u <= 0xff:
+		f = "0x%02x"
+	case u <= 0xffff:
+		f = "0x%04x"
+	case u <= 0xffffff:
+		f = "0x%06x"
+	case u <= 0xffffffff:
+		f = "0x%08x"
+	case u <= 0xffffffffff:
+		f = "0x%010x"
+	case u <= 0xffffffffffff:
+		f = "0x%012x"
+	case u <= 0xffffffffffffff:
+		f = "0x%014x"
+	case u <= 0xffffffffffffffff:
+		f = "0x%016x"
+	}
+	return fmt.Sprintf(f, u)
+}
+
+// insertPointer insert p into m, allocating m if necessary.
+func insertPointer(m map[uintptr]bool, p uintptr) map[uintptr]bool {
+	if m == nil {
+		m = make(map[uintptr]bool)
+	}
+	m[p] = true
+	return m
+}
+
+// isZero reports whether v is the zero value.
+// This does not rely on Interface and so can be used on unexported fields.
+func isZero(v reflect.Value) bool {
+	switch v.Kind() {
+	case reflect.Bool:
+		return v.Bool() == false
+	case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
+		return v.Int() == 0
+	case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr:
+		return v.Uint() == 0
+	case reflect.Float32, reflect.Float64:
+		return v.Float() == 0
+	case reflect.Complex64, reflect.Complex128:
+		return v.Complex() == 0
+	case reflect.String:
+		return v.String() == ""
+	case reflect.UnsafePointer:
+		return v.Pointer() == 0
+	case reflect.Chan, reflect.Func, reflect.Interface, reflect.Ptr, reflect.Map, reflect.Slice:
+		return v.IsNil()
+	case reflect.Array:
+		for i := 0; i < v.Len(); i++ {
+			if !isZero(v.Index(i)) {
+				return false
+			}
+		}
+		return true
+	case reflect.Struct:
+		for i := 0; i < v.NumField(); i++ {
+			if !isZero(v.Field(i)) {
+				return false
+			}
+		}
+		return true
+	}
+	return false
+}
+
+// isExported reports whether the identifier is exported.
+func isExported(id string) bool {
+	r, _ := utf8.DecodeRuneInString(id)
+	return unicode.IsUpper(r)
+}
diff --git a/cmp/internal/value/format_test.go b/cmp/internal/value/format_test.go
new file mode 100644
index 0000000..c44884f
--- /dev/null
+++ b/cmp/internal/value/format_test.go
@@ -0,0 +1,91 @@
+// Copyright 2017, 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.md file.
+
+package value
+
+import (
+	"bytes"
+	"io"
+	"reflect"
+	"testing"
+)
+
+func TestFormat(t *testing.T) {
+	type key struct {
+		a int
+		b string
+		c chan bool
+	}
+
+	tests := []struct {
+		in   interface{}
+		want string
+	}{{
+		in:   []int{},
+		want: "[]int{}",
+	}, {
+		in:   []int(nil),
+		want: "[]int(nil)",
+	}, {
+		in:   []int{1, 2, 3, 4, 5},
+		want: "[]int{1, 2, 3, 4, 5}",
+	}, {
+		in:   []interface{}{1, true, "hello", struct{ A, B int }{1, 2}},
+		want: "[]interface {}{1, true, \"hello\", struct { A int; B int }{A: 1, B: 2}}",
+	}, {
+		in:   []struct{ A, B int }{{1, 2}, {0, 4}, {}},
+		want: "[]struct { A int; B int }{{A: 1, B: 2}, {B: 4}, {}}",
+	}, {
+		in:   map[*int]string{new(int): "hello"},
+		want: "map[*int]string{0x00: \"hello\"}",
+	}, {
+		in:   map[key]string{{}: "hello"},
+		want: "map[value.key]string{{}: \"hello\"}",
+	}, {
+		in:   map[key]string{{a: 5, b: "key", c: make(chan bool)}: "hello"},
+		want: "map[value.key]string{{a: 5, b: \"key\", c: (chan bool)(0x00)}: \"hello\"}",
+	}, {
+		in:   map[io.Reader]string{new(bytes.Reader): "hello"},
+		want: "map[io.Reader]string{0x00: \"hello\"}",
+	}, {
+		in: func() interface{} {
+			var a = []interface{}{nil}
+			a[0] = a
+			return a
+		}(),
+		want: "[]interface {}{([]interface {})(0x00)}",
+	}, {
+		in: func() interface{} {
+			type A *A
+			var a A
+			a = &a
+			return a
+		}(),
+		want: "&(value.A)(0x00)",
+	}, {
+		in: func() interface{} {
+			type A map[*A]A
+			a := make(A)
+			a[&a] = a
+			return a
+		}(),
+		want: "value.A{0x00: 0x00}",
+	}, {
+		in: func() interface{} {
+			var a [2]interface{}
+			a[0] = &a
+			return a
+		}(),
+		want: "[2]interface {}{&[2]interface {}{(*[2]interface {})(0x00), interface {}(nil)}, interface {}(nil)}",
+	}}
+
+	formatFakePointers = true
+	defer func() { formatFakePointers = false }()
+	for i, tt := range tests {
+		got := Format(reflect.ValueOf(tt.in), true)
+		if got != tt.want {
+			t.Errorf("test %d, pretty print:\ngot  %q\nwant %q", i, got, tt.want)
+		}
+	}
+}
diff --git a/cmp/internal/value/sort.go b/cmp/internal/value/sort.go
new file mode 100644
index 0000000..da00896
--- /dev/null
+++ b/cmp/internal/value/sort.go
@@ -0,0 +1,111 @@
+// Copyright 2017, 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.md file.
+
+package value
+
+import (
+	"fmt"
+	"math"
+	"reflect"
+	"sort"
+)
+
+// SortKey sorts a list of map keys, deduplicating keys if necessary.
+// The type of each value must be comparable.
+func SortKeys(vs []reflect.Value) []reflect.Value {
+	if len(vs) == 0 {
+		return vs
+	}
+
+	// Sort the map keys.
+	sort.Sort(valueSorter(vs))
+
+	// Deduplicate keys (fails for NaNs).
+	vs2 := vs[:1]
+	for _, v := range vs[1:] {
+		if v.Interface() != vs2[len(vs2)-1].Interface() {
+			vs2 = append(vs2, v)
+		}
+	}
+	return vs2
+}
+
+// TODO: Use sort.Slice once Google AppEngine is on Go1.8 or above.
+type valueSorter []reflect.Value
+
+func (vs valueSorter) Len() int           { return len(vs) }
+func (vs valueSorter) Less(i, j int) bool { return isLess(vs[i], vs[j]) }
+func (vs valueSorter) Swap(i, j int)      { vs[i], vs[j] = vs[j], vs[i] }
+
+// isLess is a generic function for sorting arbitrary map keys.
+// The inputs must be of the same type and must be comparable.
+func isLess(x, y reflect.Value) bool {
+	switch x.Type().Kind() {
+	case reflect.Bool:
+		return !x.Bool() && y.Bool()
+	case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
+		return x.Int() < y.Int()
+	case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr:
+		return x.Uint() < y.Uint()
+	case reflect.Float32, reflect.Float64:
+		fx, fy := x.Float(), y.Float()
+		return fx < fy || math.IsNaN(fx) && !math.IsNaN(fy)
+	case reflect.Complex64, reflect.Complex128:
+		cx, cy := x.Complex(), y.Complex()
+		rx, ix, ry, iy := real(cx), imag(cx), real(cy), imag(cy)
+		if rx == ry || (math.IsNaN(rx) && math.IsNaN(ry)) {
+			return ix < iy || math.IsNaN(ix) && !math.IsNaN(iy)
+		}
+		return rx < ry || math.IsNaN(rx) && !math.IsNaN(ry)
+	case reflect.Ptr, reflect.UnsafePointer, reflect.Chan:
+		return x.Pointer() < y.Pointer()
+	case reflect.String:
+		return x.String() < y.String()
+	case reflect.Array:
+		for i := 0; i < x.Len(); i++ {
+			if isLess(x.Index(i), y.Index(i)) {
+				return true
+			}
+			if isLess(y.Index(i), x.Index(i)) {
+				return false
+			}
+		}
+		return false
+	case reflect.Struct:
+		for i := 0; i < x.NumField(); i++ {
+			if isLess(x.Field(i), y.Field(i)) {
+				return true
+			}
+			if isLess(y.Field(i), x.Field(i)) {
+				return false
+			}
+		}
+		return false
+	case reflect.Interface:
+		vx, vy := x.Elem(), y.Elem()
+		if !vx.IsValid() || !vy.IsValid() {
+			return !vx.IsValid() && vy.IsValid()
+		}
+		tx, ty := vx.Type(), vy.Type()
+		if tx == ty {
+			return isLess(x.Elem(), y.Elem())
+		}
+		if tx.Kind() != ty.Kind() {
+			return vx.Kind() < vy.Kind()
+		}
+		if tx.String() != ty.String() {
+			return tx.String() < ty.String()
+		}
+		if tx.PkgPath() != ty.PkgPath() {
+			return tx.PkgPath() < ty.PkgPath()
+		}
+		// This can happen in rare situations, so we fallback to just comparing
+		// the unique pointer for a reflect.Type. This guarantees deterministic
+		// ordering within a program, but it is obviously not stable.
+		return reflect.ValueOf(vx.Type()).Pointer() < reflect.ValueOf(vy.Type()).Pointer()
+	default:
+		// Must be Func, Map, or Slice; which are not comparable.
+		panic(fmt.Sprintf("%T is not comparable", x.Type()))
+	}
+}
diff --git a/cmp/reporter_test.go b/cmp/internal/value/sort_test.go
similarity index 60%
rename from cmp/reporter_test.go
rename to cmp/internal/value/sort_test.go
index 7310077..d3f254b 100644
--- a/cmp/reporter_test.go
+++ b/cmp/internal/value/sort_test.go
@@ -2,93 +2,17 @@
 // Use of this source code is governed by a BSD-style
 // license that can be found in the LICENSE.md file.
 
-package cmp
+package value_test
 
 import (
-	"bytes"
-	"io"
 	"math"
 	"reflect"
 	"testing"
+
+	"github.com/google/go-cmp/cmp"
+	"github.com/google/go-cmp/cmp/internal/value"
 )
 
-func TestFormatAny(t *testing.T) {
-	type key struct {
-		a int
-		b string
-		c chan bool
-	}
-
-	tests := []struct {
-		in   interface{}
-		want string
-	}{{
-		in:   []int{},
-		want: "[]int{}",
-	}, {
-		in:   []int(nil),
-		want: "[]int(nil)",
-	}, {
-		in:   []int{1, 2, 3, 4, 5},
-		want: "[]int{1, 2, 3, 4, 5}",
-	}, {
-		in:   []interface{}{1, true, "hello", struct{ A, B int }{1, 2}},
-		want: "[]interface {}{1, true, \"hello\", struct { A int; B int }{A: 1, B: 2}}",
-	}, {
-		in:   []struct{ A, B int }{{1, 2}, {0, 4}, {}},
-		want: "[]struct { A int; B int }{{A: 1, B: 2}, {B: 4}, {}}",
-	}, {
-		in:   map[*int]string{new(int): "hello"},
-		want: "map[*int]string{0x00: \"hello\"}",
-	}, {
-		in:   map[key]string{{}: "hello"},
-		want: "map[cmp.key]string{{}: \"hello\"}",
-	}, {
-		in:   map[key]string{{a: 5, b: "key", c: make(chan bool)}: "hello"},
-		want: "map[cmp.key]string{{a: 5, b: \"key\", c: (chan bool)(0x00)}: \"hello\"}",
-	}, {
-		in:   map[io.Reader]string{new(bytes.Reader): "hello"},
-		want: "map[io.Reader]string{0x00: \"hello\"}",
-	}, {
-		in: func() interface{} {
-			var a = []interface{}{nil}
-			a[0] = a
-			return a
-		}(),
-		want: "[]interface {}{([]interface {})(0x00)}",
-	}, {
-		in: func() interface{} {
-			type A *A
-			var a A
-			a = &a
-			return a
-		}(),
-		want: "&(cmp.A)(0x00)",
-	}, {
-		in: func() interface{} {
-			type A map[*A]A
-			a := make(A)
-			a[&a] = a
-			return a
-		}(),
-		want: "cmp.A{0x00: 0x00}",
-	}, {
-		in: func() interface{} {
-			var a [2]interface{}
-			a[0] = &a
-			return a
-		}(),
-		want: "[2]interface {}{&[2]interface {}{(*[2]interface {})(0x00), interface {}(nil)}, interface {}(nil)}",
-	}}
-
-	for i, tt := range tests {
-		got := formatAny(reflect.ValueOf(tt.in), formatConfig{true, true, true, false}, nil)
-		if got != tt.want {
-			t.Errorf("test %d, pretty print:\ngot  %q\nwant %q", i, got, tt.want)
-		}
-	}
-}
-
 func TestSortKeys(t *testing.T) {
 	type (
 		MyString string
@@ -101,14 +25,14 @@
 		EmptyStruct struct{}
 	)
 
-	opts := []Option{
-		Comparer(func(x, y float64) bool {
+	opts := []cmp.Option{
+		cmp.Comparer(func(x, y float64) bool {
 			if math.IsNaN(x) && math.IsNaN(y) {
 				return true
 			}
 			return x == y
 		}),
-		Comparer(func(x, y complex128) bool {
+		cmp.Comparer(func(x, y complex128) bool {
 			rx, ix, ry, iy := real(x), imag(x), real(y), imag(y)
 			if math.IsNaN(rx) && math.IsNaN(ry) {
 				rx, ry = 0, 0
@@ -118,11 +42,11 @@
 			}
 			return rx == ry && ix == iy
 		}),
-		Comparer(func(x, y chan bool) bool { return true }),
-		Comparer(func(x, y chan int) bool { return true }),
-		Comparer(func(x, y chan float64) bool { return true }),
-		Comparer(func(x, y chan interface{}) bool { return true }),
-		Comparer(func(x, y *int) bool { return true }),
+		cmp.Comparer(func(x, y chan bool) bool { return true }),
+		cmp.Comparer(func(x, y chan int) bool { return true }),
+		cmp.Comparer(func(x, y chan float64) bool { return true }),
+		cmp.Comparer(func(x, y chan interface{}) bool { return true }),
+		cmp.Comparer(func(x, y *int) bool { return true }),
 	}
 
 	tests := []struct {
@@ -188,7 +112,8 @@
 			[2]int{2, 3}, [2]int{2, 4}, [2]int{4, 0}, MyArray([2]int{2, 4}),
 			make(chan bool), make(chan bool), make(chan int), make(chan interface{}),
 			new(int), new(int),
-			MyString("abc"), MyString("abcd"), MyString("abcde"), "abc", "abcd", "abcde", "bar", "foo",
+			"abc", "abcd", "abcde", "bar", "foo",
+			MyString("abc"), MyString("abcd"), MyString("abcde"),
 			EmptyStruct{},
 			MyStruct{"alpha", [2]int{3, 3}, make(chan float64)},
 			MyStruct{"bravo", [2]int{2, 3}, make(chan float64)},
@@ -217,11 +142,11 @@
 	for i, tt := range tests {
 		keys := append(reflect.ValueOf(tt.in).MapKeys(), reflect.ValueOf(tt.in).MapKeys()...)
 		var got []interface{}
-		for _, k := range sortKeys(keys) {
+		for _, k := range value.SortKeys(keys) {
 			got = append(got, k.Interface())
 		}
-		if !Equal(got, tt.want, opts...) {
-			t.Errorf("test %d, output mismatch:\ngot  %#v\nwant %#v", i, got, tt.want)
+		if d := cmp.Diff(tt.want, got, opts...); d != "" {
+			t.Errorf("test %d, output mismatch (-want +got):\n%s", i, d)
 		}
 	}
 }
diff --git a/cmp/reporter.go b/cmp/reporter.go
index 3f3454b..faebc05 100644
--- a/cmp/reporter.go
+++ b/cmp/reporter.go
@@ -6,14 +6,11 @@
 
 import (
 	"fmt"
-	"math"
 	"reflect"
-	"sort"
 	"strings"
-)
 
-// TODO: Can we leave the interface for a reporter here in the cmp package
-// and somehow extract the implementation of defaultReporter into cmp/report?
+	"github.com/google/go-cmp/cmp/internal/value"
+)
 
 type defaultReporter struct {
 	Option
@@ -34,12 +31,12 @@
 	const maxLines = 256
 	r.ndiffs++
 	if r.nbytes < maxBytes && r.nlines < maxLines {
-		sx := prettyPrint(x, true)
-		sy := prettyPrint(y, true)
+		sx := value.Format(x, true)
+		sy := value.Format(y, true)
 		if sx == sy {
 			// Stringer is not helpful, so rely on more exact formatting.
-			sx = prettyPrint(x, false)
-			sy = prettyPrint(y, false)
+			sx = value.Format(x, false)
+			sy = value.Format(y, false)
 		}
 		s := fmt.Sprintf("%#v:\n\t-: %s\n\t+: %s\n", p, sx, sy)
 		r.diffs = append(r.diffs, s)
@@ -55,327 +52,3 @@
 	}
 	return fmt.Sprintf("%s... %d more differences ...", s, len(r.diffs)-r.ndiffs)
 }
-
-var stringerIface = reflect.TypeOf((*fmt.Stringer)(nil)).Elem()
-
-func prettyPrint(v reflect.Value, useStringer bool) string {
-	return formatAny(v, formatConfig{useStringer, true, true, true}, nil)
-}
-
-type formatConfig struct {
-	useStringer    bool // Should the String method be used if available?
-	printType      bool // Should we print the type before the value?
-	followPointers bool // Should we recursively follow pointers?
-	realPointers   bool // Should we print the real address of pointers?
-}
-
-// formatAny prints the value v in a pretty formatted manner.
-// This is similar to fmt.Sprintf("%+v", v) except this:
-//	* Prints the type unless it can be elided.
-//	* Avoids printing struct fields that are zero.
-//	* Prints a nil-slice as being nil, not empty.
-//	* Prints map entries in deterministic order.
-func formatAny(v reflect.Value, conf formatConfig, visited map[uintptr]bool) string {
-	// TODO: Should this be a multi-line printout in certain situations?
-
-	if !v.IsValid() {
-		return "<non-existent>"
-	}
-	if conf.useStringer && v.Type().Implements(stringerIface) {
-		if v.Kind() == reflect.Ptr && v.IsNil() {
-			return "<nil>"
-		}
-		return fmt.Sprintf("%q", v.Interface().(fmt.Stringer).String())
-	}
-
-	switch v.Kind() {
-	case reflect.Bool:
-		return fmt.Sprint(v.Bool())
-	case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
-		return fmt.Sprint(v.Int())
-	case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr:
-		if v.Type().PkgPath() == "" || v.Kind() == reflect.Uintptr {
-			return formatHex(v.Uint()) // Unnamed uints are usually bytes or words
-		}
-		return fmt.Sprint(v.Uint()) // Named uints are usually enumerations
-	case reflect.Float32, reflect.Float64:
-		return fmt.Sprint(v.Float())
-	case reflect.Complex64, reflect.Complex128:
-		return fmt.Sprint(v.Complex())
-	case reflect.String:
-		return fmt.Sprintf("%q", v)
-	case reflect.UnsafePointer, reflect.Chan, reflect.Func:
-		return formatPointer(v, conf)
-	case reflect.Ptr:
-		if v.IsNil() {
-			if conf.printType {
-				return fmt.Sprintf("(%v)(nil)", v.Type())
-			}
-			return "<nil>"
-		}
-		if visited[v.Pointer()] || !conf.followPointers {
-			return formatPointer(v, conf)
-		}
-		visited = insertPointer(visited, v.Pointer())
-		return "&" + formatAny(v.Elem(), conf, visited)
-	case reflect.Interface:
-		if v.IsNil() {
-			if conf.printType {
-				return fmt.Sprintf("%v(nil)", v.Type())
-			}
-			return "<nil>"
-		}
-		return formatAny(v.Elem(), conf, visited)
-	case reflect.Slice:
-		if v.IsNil() {
-			if conf.printType {
-				return fmt.Sprintf("%v(nil)", v.Type())
-			}
-			return "<nil>"
-		}
-		if visited[v.Pointer()] {
-			return formatPointer(v, conf)
-		}
-		visited = insertPointer(visited, v.Pointer())
-		fallthrough
-	case reflect.Array:
-		var ss []string
-		subConf := conf
-		subConf.printType = v.Type().Elem().Kind() == reflect.Interface
-		for i := 0; i < v.Len(); i++ {
-			s := formatAny(v.Index(i), subConf, visited)
-			ss = append(ss, s)
-		}
-		s := fmt.Sprintf("{%s}", strings.Join(ss, ", "))
-		if conf.printType {
-			return v.Type().String() + s
-		}
-		return s
-	case reflect.Map:
-		if v.IsNil() {
-			if conf.printType {
-				return fmt.Sprintf("%v(nil)", v.Type())
-			}
-			return "<nil>"
-		}
-		if visited[v.Pointer()] {
-			return formatPointer(v, conf)
-		}
-		visited = insertPointer(visited, v.Pointer())
-
-		var ss []string
-		subConf := conf
-		subConf.printType = v.Type().Elem().Kind() == reflect.Interface
-		for _, k := range sortKeys(v.MapKeys()) {
-			sk := formatAny(k, formatConfig{realPointers: conf.realPointers}, visited)
-			sv := formatAny(v.MapIndex(k), subConf, visited)
-			ss = append(ss, fmt.Sprintf("%s: %s", sk, sv))
-		}
-		s := fmt.Sprintf("{%s}", strings.Join(ss, ", "))
-		if conf.printType {
-			return v.Type().String() + s
-		}
-		return s
-	case reflect.Struct:
-		var ss []string
-		subConf := conf
-		subConf.printType = true
-		for i := 0; i < v.NumField(); i++ {
-			vv := v.Field(i)
-			if isZero(vv) {
-				continue // Elide zero value fields
-			}
-			name := v.Type().Field(i).Name
-			subConf.useStringer = conf.useStringer && isExported(name)
-			s := formatAny(vv, subConf, visited)
-			ss = append(ss, fmt.Sprintf("%s: %s", name, s))
-		}
-		s := fmt.Sprintf("{%s}", strings.Join(ss, ", "))
-		if conf.printType {
-			return v.Type().String() + s
-		}
-		return s
-	default:
-		panic(fmt.Sprintf("%v kind not handled", v.Kind()))
-	}
-}
-
-func formatPointer(v reflect.Value, conf formatConfig) string {
-	p := v.Pointer()
-	if !conf.realPointers {
-		p = 0 // For deterministic printing purposes
-	}
-	s := formatHex(uint64(p))
-	if conf.printType {
-		return fmt.Sprintf("(%v)(%s)", v.Type(), s)
-	}
-	return s
-}
-
-func formatHex(u uint64) string {
-	var f string
-	switch {
-	case u <= 0xff:
-		f = "0x%02x"
-	case u <= 0xffff:
-		f = "0x%04x"
-	case u <= 0xffffff:
-		f = "0x%06x"
-	case u <= 0xffffffff:
-		f = "0x%08x"
-	case u <= 0xffffffffff:
-		f = "0x%010x"
-	case u <= 0xffffffffffff:
-		f = "0x%012x"
-	case u <= 0xffffffffffffff:
-		f = "0x%014x"
-	case u <= 0xffffffffffffffff:
-		f = "0x%016x"
-	}
-	return fmt.Sprintf(f, u)
-}
-
-// insertPointer insert p into m, allocating m if necessary.
-func insertPointer(m map[uintptr]bool, p uintptr) map[uintptr]bool {
-	if m == nil {
-		m = make(map[uintptr]bool)
-	}
-	m[p] = true
-	return m
-}
-
-// isZero reports whether v is the zero value.
-// This does not rely on Interface and so can be used on unexported fields.
-func isZero(v reflect.Value) bool {
-	switch v.Kind() {
-	case reflect.Bool:
-		return v.Bool() == false
-	case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
-		return v.Int() == 0
-	case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr:
-		return v.Uint() == 0
-	case reflect.Float32, reflect.Float64:
-		return v.Float() == 0
-	case reflect.Complex64, reflect.Complex128:
-		return v.Complex() == 0
-	case reflect.String:
-		return v.String() == ""
-	case reflect.UnsafePointer:
-		return v.Pointer() == 0
-	case reflect.Chan, reflect.Func, reflect.Interface, reflect.Ptr, reflect.Map, reflect.Slice:
-		return v.IsNil()
-	case reflect.Array:
-		for i := 0; i < v.Len(); i++ {
-			if !isZero(v.Index(i)) {
-				return false
-			}
-		}
-		return true
-	case reflect.Struct:
-		for i := 0; i < v.NumField(); i++ {
-			if !isZero(v.Field(i)) {
-				return false
-			}
-		}
-		return true
-	}
-	return false
-}
-
-// isLess is a generic function for sorting arbitrary map keys.
-// The inputs must be of the same type and must be comparable.
-func isLess(x, y reflect.Value) bool {
-	switch x.Type().Kind() {
-	case reflect.Bool:
-		return !x.Bool() && y.Bool()
-	case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
-		return x.Int() < y.Int()
-	case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr:
-		return x.Uint() < y.Uint()
-	case reflect.Float32, reflect.Float64:
-		fx, fy := x.Float(), y.Float()
-		return fx < fy || math.IsNaN(fx) && !math.IsNaN(fy)
-	case reflect.Complex64, reflect.Complex128:
-		cx, cy := x.Complex(), y.Complex()
-		rx, ix, ry, iy := real(cx), imag(cx), real(cy), imag(cy)
-		if rx == ry || (math.IsNaN(rx) && math.IsNaN(ry)) {
-			return ix < iy || math.IsNaN(ix) && !math.IsNaN(iy)
-		}
-		return rx < ry || math.IsNaN(rx) && !math.IsNaN(ry)
-	case reflect.Ptr, reflect.UnsafePointer, reflect.Chan:
-		return x.Pointer() < y.Pointer()
-	case reflect.String:
-		return x.String() < y.String()
-	case reflect.Array:
-		for i := 0; i < x.Len(); i++ {
-			if isLess(x.Index(i), y.Index(i)) {
-				return true
-			}
-			if isLess(y.Index(i), x.Index(i)) {
-				return false
-			}
-		}
-		return false
-	case reflect.Struct:
-		for i := 0; i < x.NumField(); i++ {
-			if isLess(x.Field(i), y.Field(i)) {
-				return true
-			}
-			if isLess(y.Field(i), x.Field(i)) {
-				return false
-			}
-		}
-		return false
-	case reflect.Interface:
-		vx, vy := x.Elem(), y.Elem()
-		if !vx.IsValid() || !vy.IsValid() {
-			return !vx.IsValid() && vy.IsValid()
-		}
-		tx, ty := vx.Type(), vy.Type()
-		if tx == ty {
-			return isLess(x.Elem(), y.Elem())
-		}
-		if tx.Kind() != ty.Kind() {
-			return vx.Kind() < vy.Kind()
-		}
-		if tx.String() != ty.String() {
-			return tx.String() < ty.String()
-		}
-		if tx.PkgPath() != ty.PkgPath() {
-			return tx.PkgPath() < ty.PkgPath()
-		}
-		// This can happen in rare situations, so we fallback to just comparing
-		// the unique pointer for a reflect.Type. This guarantees deterministic
-		// ordering within a program, but it is obviously not stable.
-		return reflect.ValueOf(vx.Type()).Pointer() < reflect.ValueOf(vy.Type()).Pointer()
-	default:
-		// Must be Func, Map, or Slice; which are not comparable.
-		panic(fmt.Sprintf("%T is not comparable", x.Type()))
-	}
-}
-
-// sortKey sorts a list of map keys, deduplicating keys if necessary.
-func sortKeys(vs []reflect.Value) []reflect.Value {
-	if len(vs) == 0 {
-		return vs
-	}
-
-	// Sort the map keys.
-	sort.Sort(valueSorter(vs))
-
-	// Deduplicate keys (fails for NaNs).
-	vs2 := vs[:1]
-	for _, v := range vs[1:] {
-		if v.Interface() != vs2[len(vs2)-1].Interface() {
-			vs2 = append(vs2, v)
-		}
-	}
-	return vs2
-}
-
-// TODO: Use sort.Slice once Google AppEngine is on Go1.8 or above.
-type valueSorter []reflect.Value
-
-func (vs valueSorter) Len() int           { return len(vs) }
-func (vs valueSorter) Less(i, j int) bool { return isLess(vs[i], vs[j]) }
-func (vs valueSorter) Swap(i, j int)      { vs[i], vs[j] = vs[j], vs[i] }
