diff --git a/cmd/genbindings/clang2il.go b/cmd/genbindings/clang2il.go index 5a6214e2..341bd19b 100644 --- a/cmd/genbindings/clang2il.go +++ b/cmd/genbindings/clang2il.go @@ -437,7 +437,7 @@ func parseTypeString(typeString string) (CppParameter, []CppParameter, error) { } // Parameters are separated by commas and nesting can not be possible - params := strings.Split(inner, `,`) + params := tokenizeMultipleParameters(inner) // strings.Split(inner, `,`) ret := make([]CppParameter, 0, len(params)) for _, p := range params { @@ -456,6 +456,31 @@ func parseTypeString(typeString string) (CppParameter, []CppParameter, error) { return returnType, ret, nil } +func tokenizeMultipleParameters(p string) []string { + // Tokenize into top-level strings + templateDepth := 0 + tokens := []string{} + wip := "" + p = strings.TrimSpace(p) + for _, c := range p { + if c == '<' { + wip += string(c) + templateDepth++ + } else if c == '>' { + wip += string(c) + templateDepth-- + } else if c == ',' && templateDepth == 0 { + tokens = append(tokens, wip) + wip = "" + } else { + wip += string(c) + } + } + + tokens = append(tokens, wip) + return tokens +} + func parseSingleTypeString(p string) CppParameter { tokens := strings.Split(strings.TrimSpace(p), " ") diff --git a/cmd/genbindings/clang2il_test.go b/cmd/genbindings/clang2il_test.go index 6c2d32f2..b6c61027 100644 --- a/cmd/genbindings/clang2il_test.go +++ b/cmd/genbindings/clang2il_test.go @@ -10,6 +10,7 @@ func TestParseTypeString(t *testing.T) { input string expectReturn CppParameter expectParams []CppParameter + expectErr bool } cases := []testCase{ @@ -20,20 +21,40 @@ func TestParseTypeString(t *testing.T) { CppParameter{ParameterType: "bool"}, }, }, + testCase{ + input: "bool (QList>, QString)", + /* + expectReturn: CppParameter{ParameterType: "bool"}, + expectParams: []CppParameter{ + CppParameter{ParameterType: "QList>"}, + CppParameter{ParameterType: "QString"}, + }, + */ + expectErr: true, + }, } for _, tc := range cases { r, p, err := parseTypeString(tc.input) - if err != nil { - t.Errorf("Test %q got error %v", tc.input, err) - continue - } - if !reflect.DeepEqual(r, tc.expectReturn) { - t.Errorf("Test %q got return=%#v, expected=%#v", tc.input, r, tc.expectReturn) - } - if !reflect.DeepEqual(p, tc.expectParams) { - t.Errorf("Test %q got return=%#v, expected=%#v", tc.input, r, tc.expectReturn) + if tc.expectErr { + if err == nil { + t.Errorf("Test %q got error=nil but it was expected to fail", tc.input) + continue + } + + } else { + if err != nil { + t.Errorf("Test %q got error %v", tc.input, err) + continue + } + + if !reflect.DeepEqual(r, tc.expectReturn) { + t.Errorf("Test %q\n-got return=%#v\n-expected =%#v", tc.input, r, tc.expectReturn) + } + if !reflect.DeepEqual(p, tc.expectParams) { + t.Errorf("Test %q\n-got params=%#v\n-expected =%#v", tc.input, p, tc.expectParams) + } } } }