diff options
author | frenkel26 <[email protected]> | 2024-05-28 15:09:59 +0300 |
---|---|---|
committer | GitHub <[email protected]> | 2024-05-28 14:09:59 +0200 |
commit | f7c0466f78fe97c578f298de639fd5248cc91ee4 (patch) | |
tree | bd196d5c649f3f15a27e01d7a1d7630cfa40130b | |
parent | 81ce7fb738142361afba119f1f531cf6ffddc6d1 (diff) | |
download | tinygo-f7c0466f78fe97c578f298de639fd5248cc91ee4.tar.gz tinygo-f7c0466f78fe97c578f298de639fd5248cc91ee4.zip |
compiler,reflect: fix NumMethods for Interface type
-rw-r--r-- | compiler/interface.go | 15 | ||||
-rw-r--r-- | compiler/testdata/interface.ll | 2 | ||||
-rw-r--r-- | testdata/reflect.go | 1 | ||||
-rw-r--r-- | testdata/reflect.txt | 5 |
4 files changed, 16 insertions, 7 deletions
diff --git a/compiler/interface.go b/compiler/interface.go index 564e3a414..b6dffd643 100644 --- a/compiler/interface.go +++ b/compiler/interface.go @@ -124,16 +124,19 @@ func (c *compilerContext) pkgPathPtr(pkgpath string) llvm.Value { func (c *compilerContext) getTypeCode(typ types.Type) llvm.Value { ms := c.program.MethodSets.MethodSet(typ) hasMethodSet := ms.Len() != 0 - if _, ok := typ.Underlying().(*types.Interface); ok { + _, isInterface := typ.Underlying().(*types.Interface) + if isInterface { hasMethodSet = false } + // As defined in https://pkg.go.dev/reflect#Type: + // NumMethod returns the number of methods accessible using Method. + // For a non-interface type, it returns the number of exported methods. + // For an interface type, it returns the number of exported and unexported methods. var numMethods int - if hasMethodSet { - for i := 0; i < ms.Len(); i++ { - if ms.At(i).Obj().Exported() { - numMethods++ - } + for i := 0; i < ms.Len(); i++ { + if isInterface || ms.At(i).Obj().Exported() { + numMethods++ } } diff --git a/compiler/testdata/interface.ll b/compiler/testdata/interface.ll index ff3a04d91..801f370d5 100644 --- a/compiler/testdata/interface.ll +++ b/compiler/testdata/interface.ll @@ -9,7 +9,7 @@ target triple = "wasm32-unknown-wasi" @"reflect/types.type:basic:int" = linkonce_odr constant { i8, ptr } { i8 -62, ptr @"reflect/types.type:pointer:basic:int" }, align 4 @"reflect/types.type:pointer:basic:int" = linkonce_odr constant { i8, i16, ptr } { i8 -43, i16 0, ptr @"reflect/types.type:basic:int" }, align 4 @"reflect/types.type:pointer:named:error" = linkonce_odr constant { i8, i16, ptr } { i8 -43, i16 0, ptr @"reflect/types.type:named:error" }, align 4 -@"reflect/types.type:named:error" = linkonce_odr constant { i8, i16, ptr, ptr, ptr, [7 x i8] } { i8 116, i16 0, ptr @"reflect/types.type:pointer:named:error", ptr @"reflect/types.type:interface:{Error:func:{}{basic:string}}", ptr @"reflect/types.type.pkgpath.empty", [7 x i8] c".error\00" }, align 4 +@"reflect/types.type:named:error" = linkonce_odr constant { i8, i16, ptr, ptr, ptr, [7 x i8] } { i8 116, i16 1, ptr @"reflect/types.type:pointer:named:error", ptr @"reflect/types.type:interface:{Error:func:{}{basic:string}}", ptr @"reflect/types.type.pkgpath.empty", [7 x i8] c".error\00" }, align 4 @"reflect/types.type.pkgpath.empty" = linkonce_odr unnamed_addr constant [1 x i8] zeroinitializer, align 1 @"reflect/types.type:interface:{Error:func:{}{basic:string}}" = linkonce_odr constant { i8, ptr } { i8 84, ptr @"reflect/types.type:pointer:interface:{Error:func:{}{basic:string}}" }, align 4 @"reflect/types.type:pointer:interface:{Error:func:{}{basic:string}}" = linkonce_odr constant { i8, i16, ptr } { i8 -43, i16 0, ptr @"reflect/types.type:interface:{Error:func:{}{basic:string}}" }, align 4 diff --git a/testdata/reflect.go b/testdata/reflect.go index 1a92e47ab..595aaa8cf 100644 --- a/testdata/reflect.go +++ b/testdata/reflect.go @@ -456,6 +456,7 @@ func showValue(rv reflect.Value, indent string) { case reflect.Interface: println(indent + " interface") println(indent+" nil:", rv.IsNil()) + println(indent+" NumMethod:", rv.NumMethod()) if !rv.IsNil() { showValue(rv.Elem(), indent+" ") } diff --git a/testdata/reflect.txt b/testdata/reflect.txt index e4a92a5e1..3f1b5a17b 100644 --- a/testdata/reflect.txt +++ b/testdata/reflect.txt @@ -80,6 +80,7 @@ reflect type: ptr reflect type: interface settable=true addrable=true interface nil: true + NumMethod: 1 reflect type: ptr pointer: true int nil: false @@ -240,6 +241,7 @@ reflect type: struct reflect type: interface caninterface=false interface nil: true + NumMethod: 1 reflect type: struct struct: 3 field: 0 a @@ -371,12 +373,14 @@ reflect type: slice comparable=false reflect type: interface settable=true addrable=true interface nil: false + NumMethod: 0 reflect type: int int: 3 indexing: 1 reflect type: interface settable=true addrable=true interface nil: false + NumMethod: 0 reflect type: string string: str 3 reflect type: uint8 @@ -389,6 +393,7 @@ reflect type: slice comparable=false reflect type: interface settable=true addrable=true interface nil: false + NumMethod: 0 reflect type: complex128 complex: (-4.000000e+000+2.500000e+000i) reflect type: ptr |