diff --git a/src/reflect/type.go b/src/reflect/type.go index f921e4cf..68160c33 100644 --- a/src/reflect/type.go +++ b/src/reflect/type.go @@ -164,8 +164,15 @@ func (t Type) Field(i int) StructField { panic("unimplemented: (reflect.Type).Field()") } +// Bits returns the number of bits that this type uses. It is only valid for +// arithmetic types (integers, floats, and complex numbers). For other types, it +// will panic. func (t Type) Bits() int { - panic("unimplemented: (reflect.Type).Bits()") + kind := t.Kind() + if kind >= Int && kind <= Complex128 { + return int(t.Size()) * 8 + } + panic(TypeError{"Bits"}) } func (t Type) Len() int { @@ -213,3 +220,17 @@ type StructField struct { Name string Type Type } + +// TypeError is the error that is used in a panic when invoking a method on a +// type that is not applicable to that type. +type TypeError struct { + Method string +} + +func (e *TypeError) Error() string { + return "reflect: call of reflect.Type." + e.Method + " on invalid type" +} + +func align(offset uintptr, alignment uintptr) uintptr { + return (offset + alignment - 1) &^ (alignment - 1) +} diff --git a/testdata/reflect.go b/testdata/reflect.go index 80c4bd44..7c8a10d1 100644 --- a/testdata/reflect.go +++ b/testdata/reflect.go @@ -92,18 +92,25 @@ func main() { // test sizes println("\nsizes:") - println("int8", int(reflect.TypeOf(int8(0)).Size())) - println("int16", int(reflect.TypeOf(int16(0)).Size())) - println("int32", int(reflect.TypeOf(int32(0)).Size())) - println("int64", int(reflect.TypeOf(int64(0)).Size())) - println("uint8", int(reflect.TypeOf(uint8(0)).Size())) - println("uint16", int(reflect.TypeOf(uint16(0)).Size())) - println("uint32", int(reflect.TypeOf(uint32(0)).Size())) - println("uint64", int(reflect.TypeOf(uint64(0)).Size())) - println("float32", int(reflect.TypeOf(float32(0)).Size())) - println("float64", int(reflect.TypeOf(float64(0)).Size())) - println("complex64", int(reflect.TypeOf(complex64(0)).Size())) - println("complex128", int(reflect.TypeOf(complex128(0)).Size())) + for _, tc := range []struct { + name string + rt reflect.Type + }{ + {"int8", reflect.TypeOf(int8(0))}, + {"int16", reflect.TypeOf(int16(0))}, + {"int32", reflect.TypeOf(int32(0))}, + {"int64", reflect.TypeOf(int64(0))}, + {"uint8", reflect.TypeOf(uint8(0))}, + {"uint16", reflect.TypeOf(uint16(0))}, + {"uint32", reflect.TypeOf(uint32(0))}, + {"uint64", reflect.TypeOf(uint64(0))}, + {"float32", reflect.TypeOf(float32(0))}, + {"float64", reflect.TypeOf(float64(0))}, + {"complex64", reflect.TypeOf(complex64(0))}, + {"complex128", reflect.TypeOf(complex128(0))}, + } { + println(tc.name, int(tc.rt.Size()), tc.rt.Bits()) + } assertSize(reflect.TypeOf(uintptr(0)).Size() == unsafe.Sizeof(uintptr(0)), "uintptr") assertSize(reflect.TypeOf("").Size() == unsafe.Sizeof(""), "string") assertSize(reflect.TypeOf(new(int)).Size() == unsafe.Sizeof(new(int)), "*int") diff --git a/testdata/reflect.txt b/testdata/reflect.txt index 0d89b6dd..f43a6224 100644 --- a/testdata/reflect.txt +++ b/testdata/reflect.txt @@ -222,15 +222,15 @@ reflect type: struct struct sizes: -int8 1 -int16 2 -int32 4 -int64 8 -uint8 1 -uint16 2 -uint32 4 -uint64 8 -float32 4 -float64 8 -complex64 8 -complex128 16 +int8 1 8 +int16 2 16 +int32 4 32 +int64 8 64 +uint8 1 8 +uint16 2 16 +uint32 4 32 +uint64 8 64 +float32 4 32 +float64 8 64 +complex64 8 64 +complex128 16 128