From c780003d448d9329d9670a4a49b41540b2707b3a Mon Sep 17 00:00:00 2001 From: James Strachan Date: Thu, 25 May 2023 10:44:44 -0700 Subject: [PATCH] avoid using "C.enum_" expressions in the generated go code if the C header file uses C enums then we can generate go code of the form `C.enum_` which doesn't compile; so using somethign simpler like `uint32` fixes it this workaround works great for me on a project I'm using c-for-go on. I wonder if we need some configuration to enable this behaviour? --- generator/gen_bindings.go | 3 ++- generator/gen_callbacks.go | 9 +++++---- generator/gen_typedef.go | 9 +++++---- translator/ast_walker.go | 3 ++- translator/translator.go | 5 +++-- utils/helpers.go | 13 +++++++++++++ 6 files changed, 30 insertions(+), 12 deletions(-) create mode 100644 utils/helpers.go diff --git a/generator/gen_bindings.go b/generator/gen_bindings.go index 1749b98..adebf63 100644 --- a/generator/gen_bindings.go +++ b/generator/gen_bindings.go @@ -3,6 +3,7 @@ package generator import ( "bytes" "fmt" + "github.com/xlab/c-for-go/utils" "io" "strings" @@ -1033,7 +1034,7 @@ func (gen *Generator) writeFunctionBody(wr io.Writer, decl *tl.CDecl) { if spec.Return != nil { fmt.Fprint(wr, "__ret := ") } - fmt.Fprintf(wr, "C.%s", decl.Name) + fmt.Fprintf(wr, utils.CTypeString(decl.Name)) writeStartParams(wr) for i := range spec.Params { fmt.Fprint(wr, from[i].Name) diff --git a/generator/gen_callbacks.go b/generator/gen_callbacks.go index 658ff53..9e4bae5 100644 --- a/generator/gen_callbacks.go +++ b/generator/gen_callbacks.go @@ -3,6 +3,7 @@ package generator import ( "bytes" "fmt" + "github.com/xlab/c-for-go/utils" "io" "strings" @@ -78,8 +79,8 @@ func (gen *Generator) getCallbackHelpers(goFuncName, cFuncName string, spec tl.C if %sFunc == nil { %sFunc = x } - return (*%s)(C.%s), nil - }`, cbGoName, cbGoName, cgoSpec, cbCName) + return (*%s)(%s), nil + }`, cbGoName, cbGoName, cgoSpec, utils.CTypeString(cbCName)) helpers = append(helpers, &Helper{ Name: fmt.Sprintf("%s.PassRef", goFuncName), Source: buf.String(), @@ -95,8 +96,8 @@ func (gen *Generator) getCallbackHelpers(goFuncName, cFuncName string, spec tl.C if %sFunc == nil { %sFunc = x } - return (%s)(C.%s), nil - }`, cbGoName, cbGoName, cgoSpec, cbCName) + return (%s)(%s), nil + }`, cbGoName, cbGoName, cgoSpec, utils.CTypeString(cbCName)) helpers = append(helpers, &Helper{ Name: fmt.Sprintf("%s.PassValue", goFuncName), Source: buf.String(), diff --git a/generator/gen_typedef.go b/generator/gen_typedef.go index 4722d6b..d70e396 100644 --- a/generator/gen_typedef.go +++ b/generator/gen_typedef.go @@ -2,10 +2,10 @@ package generator import ( "fmt" + tl "github.com/xlab/c-for-go/translator" + "github.com/xlab/c-for-go/utils" "io" "path/filepath" - - tl "github.com/xlab/c-for-go/translator" ) func (gen *Generator) writeTypeTypedef(wr io.Writer, decl *tl.CDecl, seenNames map[string]bool) { @@ -107,7 +107,8 @@ func (gen *Generator) writeStructTypedef(wr io.Writer, decl *tl.CDecl, raw bool, // opaque struct fmt.Fprintf(wr, "// %s as declared in %s\n", goName, filepath.ToSlash(gen.tr.SrcLocation(tl.TargetType, cName, decl.Position))) - fmt.Fprintf(wr, "type %s C.%s", goName, decl.Spec.CGoName()) + cgoName := decl.Spec.CGoName() + fmt.Fprintf(wr, "type %s %s", goName, utils.CTypeString(cgoName)) writeSpace(wr, 1) for _, helper := range gen.getRawStructHelpers(goName, cName, decl.Spec) { gen.submitHelper(helper) @@ -139,7 +140,7 @@ func (gen *Generator) writeUnionTypedef(wr io.Writer, decl *tl.CDecl) { if typeName := string(goName); typeName != typeRef { fmt.Fprintf(wr, "// %s as declared in %s\n", goName, filepath.ToSlash(gen.tr.SrcLocation(tl.TargetType, cName, decl.Position))) - fmt.Fprintf(wr, "const sizeof%s = unsafe.Sizeof(C.%s{})\n", goName, decl.Spec.CGoName()) + fmt.Fprintf(wr, "const sizeof%s = unsafe.Sizeof(%s{})\n", goName, utils.CTypeString(decl.Spec.CGoName())) fmt.Fprintf(wr, "type %s [sizeof%s]byte\n", goName, goName) writeSpace(wr, 1) return diff --git a/translator/ast_walker.go b/translator/ast_walker.go index f47702d..275f85e 100644 --- a/translator/ast_walker.go +++ b/translator/ast_walker.go @@ -2,6 +2,7 @@ package translator import ( "fmt" + "github.com/xlab/c-for-go/utils" "strings" "modernc.org/cc/v4" @@ -129,7 +130,7 @@ func (t *Translator) enumSpec(base *CTypeSpec, typ cc.Type) *CEnumSpec { } switch { case t.constRules[ConstEnum] == ConstCGOAlias: - m.Expression = fmt.Sprintf("C.%s", name) + m.Expression = utils.CTypeString(name) case t.constRules[ConstEnum] == ConstExpand: enTokens := cc.NodeTokens(en.ConstantExpression) srcParts := make([]string, 0, len(enTokens)) diff --git a/translator/translator.go b/translator/translator.go index a5df3e3..90632ac 100644 --- a/translator/translator.go +++ b/translator/translator.go @@ -3,6 +3,7 @@ package translator import ( "bytes" "fmt" + "github.com/xlab/c-for-go/utils" "regexp" "sort" "strings" @@ -881,7 +882,7 @@ func (t *Translator) TranslateSpec(spec CType, tips ...Tip) GoTypeSpec { if base := spec.GetBase(); len(base) > 0 { wrapper.Raw = string(t.TransformName(TargetType, base)) } else if cgoName := spec.CGoName(); len(cgoName) > 0 { - wrapper.Raw = "C." + cgoName + wrapper.Raw = utils.CTypeString(cgoName) } return wrapper } @@ -919,7 +920,7 @@ func (t *Translator) CGoSpec(spec CType, asArg bool) CGoSpec { } } } - cgo.Base = "C." + spec.CGoName() + cgo.Base = utils.CTypeString(spec.CGoName()) return cgo } diff --git a/utils/helpers.go b/utils/helpers.go new file mode 100644 index 0000000..6285e92 --- /dev/null +++ b/utils/helpers.go @@ -0,0 +1,13 @@ +package utils + +import ( + "fmt" + "strings" +) + +func CTypeString(name string) string { + if strings.HasPrefix(name, "enum") { + return "uint32" + } + return fmt.Sprintf("C.%s", name) +}