1
0
mirror of https://github.com/golang/go synced 2024-11-12 10:00:25 -07:00

fix up %p

- use an interface {Get()}
- implement Get for maps, slices
- for slices, retrieves the address of the end of the array, which will give the
	same value for every slice of the same array.

R=rsc
CC=golang-dev
https://golang.org/cl/179129
This commit is contained in:
Rob Pike 2009-12-23 07:34:17 +11:00
parent d488c4b4ac
commit 148ee9c009
2 changed files with 19 additions and 4 deletions

View File

@ -136,6 +136,12 @@ type GoStringer interface {
GoString() string GoString() string
} }
// getter is implemented by any value that has a Get() method,
// which means the object contains a pointer. Used by %p.
type getter interface {
Get() uintptr
}
const allocSize = 32 const allocSize = 32
type pp struct { type pp struct {
@ -803,12 +809,9 @@ func (p *pp) doprintf(format string, v *reflect.StructValue) {
// pointer, including addresses of reference types. // pointer, including addresses of reference types.
case 'p': case 'p':
switch v := field.(type) { switch v := field.(type) {
case *reflect.PtrValue: case getter:
p.fmt.fmt_s("0x") p.fmt.fmt_s("0x")
p.fmt.fmt_uX64(uint64(v.Get())) p.fmt.fmt_uX64(uint64(v.Get()))
case *reflect.ChanValue, *reflect.MapValue, *reflect.SliceValue:
p.fmt.fmt_s("0x")
p.fmt.fmt_uX64(uint64(field.Addr()))
default: default:
goto badtype goto badtype
} }

View File

@ -567,6 +567,14 @@ func (v *SliceValue) Set(x *SliceValue) {
// Set sets v to the value x. // Set sets v to the value x.
func (v *SliceValue) SetValue(x Value) { v.Set(x.(*SliceValue)) } func (v *SliceValue) SetValue(x Value) { v.Set(x.(*SliceValue)) }
// Get returns the uintptr address of the v.Cap()'th element. This gives
// the same result for all slices of the same array.
// It is mainly useful for printing.
func (v *SliceValue) Get() uintptr {
typ := v.typ.(*SliceType)
return uintptr(v.addr()) + uintptr(v.Cap())*typ.Elem().Size()
}
// Slice returns a sub-slice of the slice v. // Slice returns a sub-slice of the slice v.
func (v *SliceValue) Slice(beg, end int) *SliceValue { func (v *SliceValue) Slice(beg, end int) *SliceValue {
cap := v.Cap() cap := v.Cap()
@ -970,6 +978,10 @@ func (v *MapValue) Set(x *MapValue) {
// Set sets v to the value x. // Set sets v to the value x.
func (v *MapValue) SetValue(x Value) { v.Set(x.(*MapValue)) } func (v *MapValue) SetValue(x Value) { v.Set(x.(*MapValue)) }
// Get returns the uintptr value of v.
// It is mainly useful for printing.
func (v *MapValue) Get() uintptr { return *(*uintptr)(v.addr) }
// implemented in ../pkg/runtime/reflect.cgo // implemented in ../pkg/runtime/reflect.cgo
func mapaccess(m, key, val *byte) bool func mapaccess(m, key, val *byte) bool
func mapassign(m, key, val *byte) func mapassign(m, key, val *byte)