Skip to content

Commit bca5511

Browse files
authored
coroc: better handle chained function calls (#100)
This fixes some odd expression decomposition I noticed. In the worst case (all functions in the chain may yield), a chain like `time.Now().UTC()` is decomposed to: ```go { _v2 := time.Now _v1 := _v2() _v0 := _v1.UTC _v0() } ``` Although this is technically correct, it can cause issues with serialization because the function types aren't necessarily registered. This PR improves the handling of `ast.CallExpr` + `ast.SelectorExpr` so that we instead get the following (in the worst case): ```go { _v0 := time.Now() _v0.UTC() } ```
2 parents fe62e2e + c9fed4e commit bca5511

File tree

2 files changed

+20
-2
lines changed

2 files changed

+20
-2
lines changed

compiler/desugar.go

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -767,11 +767,15 @@ const (
767767
)
768768

769769
func (d *desugarer) mayYield(n ast.Node) bool {
770-
switch n.(type) {
770+
switch x := n.(type) {
771771
case nil:
772772
return false
773773
case *ast.BasicLit, *ast.FuncLit, *ast.Ident:
774774
return false
775+
case *ast.SelectorExpr:
776+
if _, ok := x.X.(*ast.Ident); ok {
777+
return false
778+
}
775779
case *ast.ArrayType, *ast.ChanType, *ast.FuncType, *ast.InterfaceType, *ast.MapType, *ast.StructType:
776780
return false
777781
}
@@ -820,7 +824,11 @@ func (d *desugarer) decomposeExpression(expr ast.Expr, flags exprFlags) (ast.Exp
820824
continue
821825
}
822826
}
823-
e.Fun = decompose(e.Fun)
827+
if se, ok := e.Fun.(*ast.SelectorExpr); ok && d.mayYield(se.X) {
828+
se.X = decompose(se.X)
829+
} else {
830+
e.Fun = decompose(e.Fun)
831+
}
824832
for i, arg := range e.Args {
825833
e.Args[i] = decompose(arg)
826834
}

compiler/desugar_test.go

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1134,6 +1134,16 @@ defer func() {
11341134
foo(_v0, _v1)
11351135
}()
11361136
}
1137+
`,
1138+
},
1139+
{
1140+
name: "repeated function calls",
1141+
body: "time.Now().UTC()",
1142+
expect: `
1143+
{
1144+
_v0 := time.Now()
1145+
_v0.UTC()
1146+
}
11371147
`,
11381148
},
11391149
} {

0 commit comments

Comments
 (0)