Skip to content

Commit

Permalink
interp: fix type recursivity detection
Browse files Browse the repository at this point in the history
Fix the logic to detect recursive struct types, which was giving a false positive.
We now use the local type name  as key in tracker map.

A non-regression test case is included (_test/struct49.go).

This completes #1008.
  • Loading branch information
mvertes authored Jan 19, 2021
1 parent 8fa00f8 commit 274eecd
Show file tree
Hide file tree
Showing 2 changed files with 45 additions and 3 deletions.
41 changes: 41 additions & 0 deletions _test/struct59.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
package main

import (
"fmt"
)

type A struct {
B map[string]*B
C map[string]*C
}

type C struct {
D *D
E *E
}

type D struct {
F *F
G []G
}

type E struct {
H []H
F *F
}

type B struct{}
type F struct{}
type G struct{}
type H struct{}

func main() {
conf := &A{
B: make(map[string]*B),
C: make(map[string]*C),
}
fmt.Println(conf)
}

// Output:
// &{map[] map[]}
7 changes: 4 additions & 3 deletions interp/type.go
Original file line number Diff line number Diff line change
Expand Up @@ -1414,7 +1414,7 @@ func (t *itype) refType(defined map[string]*itype, wrapRecursive bool) reflect.T
t.rtype = reflect.TypeOf(new(error)).Elem()
case funcT:
if t.name != "" {
defined[name] = t
defined[name] = t // TODO(marc): make sure that key is name and not t.name.
}
variadic := false
in := make([]reflect.Type, len(t.arg))
Expand All @@ -1435,10 +1435,11 @@ func (t *itype) refType(defined map[string]*itype, wrapRecursive bool) reflect.T
t.rtype = reflect.PtrTo(t.val.refType(defined, wrapRecursive))
case structT:
if t.name != "" {
if defined[name] != nil {
// Check against local t.name and not name to catch recursive type definitions.
if defined[t.name] != nil {
recursive = true
}
defined[name] = t
defined[t.name] = t
}
var fields []reflect.StructField
// TODO(mpl): make Anonymous work for recursive types too. Maybe not worth the
Expand Down

0 comments on commit 274eecd

Please sign in to comment.