genbindings: move all large int constants to a 64-bit only build file

This commit is contained in:
mappu 2024-12-30 18:42:05 +13:00
parent 12618a309c
commit dba031643c
2 changed files with 54 additions and 6 deletions

View File

@ -5,8 +5,10 @@ import (
"fmt"
"go/format"
"log"
"math"
"path"
"sort"
"strconv"
"strings"
)
@ -643,7 +645,7 @@ func (gfs *goFileState) emitCabiToGo(assignExpr string, rt CppParameter, rvalue
}
func emitGo(src *CppParsedHeader, headerName string, packageName string) (string, error) {
func emitGo(src *CppParsedHeader, headerName string, packageName string) (string, string, error) {
ret := strings.Builder{}
ret.WriteString(`package ` + path.Base(packageName) + `
@ -664,6 +666,8 @@ import "C"
currentPackageName: packageName,
}
var bigints []string
// Check if short-named enums are allowed.
// We only allow short names if there are no conflicts anywhere in the whole
// file. This doesn't fully defend against cross-file conflicts but those
@ -716,13 +720,41 @@ import "C"
if len(e.Entries) > 0 {
ret.WriteString("const (\n")
var smallvalues []string
for _, ee := range e.Entries {
ret.WriteString(titleCase(cabiClassName(goEnumShortName+"::"+ee.EntryName)) + " " + goEnumName + " = " + ee.EntryValue + "\n")
isBigInt := false
if e.UnderlyingType.IntType() {
// Int-type enums need special handling in case of 64-bit
// overflow, that would prevent using miqt on 32-bit platforms
entryValueI64, err := strconv.ParseInt(ee.EntryValue, 10, 64)
if err != nil {
panic("Enum " + ee.EntryName + " has non-parseable integer value")
}
if entryValueI64 > math.MaxInt32 || entryValueI64 < math.MinInt32 {
isBigInt = true
}
}
enumConstDeclaration := titleCase(cabiClassName(goEnumShortName+"::"+ee.EntryName)) + " " + goEnumName + " = " + ee.EntryValue
if isBigInt {
bigints = append(bigints, "const "+enumConstDeclaration+"\n")
} else {
smallvalues = append(smallvalues, enumConstDeclaration+"\n")
}
}
if len(smallvalues) > 0 {
ret.WriteString("const (\n")
ret.WriteString(strings.Join(smallvalues, ""))
ret.WriteString("\n)\n\n")
}
ret.WriteString("\n)\n\n")
}
}
@ -1085,5 +1117,14 @@ import "C"
formattedSrc = []byte(goSrc)
}
return string(formattedSrc), nil
// Determine if we need to produce a _64bit.go file
bigintSrc := ""
if len(bigints) > 0 {
bigintSrc = `//go:build !386 && !arm
// +build !386,!arm
package ` + path.Base(packageName) + "\n\n" + strings.Join(bigints, "") + "\n"
}
return string(formattedSrc), bigintSrc, nil
}

View File

@ -222,7 +222,7 @@ func generate(packageName string, srcDirs []string, allowHeaderFn func(string) b
counter++
}
goSrc, err := emitGo(parsed, filepath.Base(parsed.Filename), packageName)
goSrc, go64Src, err := emitGo(parsed, filepath.Base(parsed.Filename), packageName)
if err != nil {
panic(err)
}
@ -232,6 +232,13 @@ func generate(packageName string, srcDirs []string, allowHeaderFn func(string) b
panic(err)
}
if len(go64Src) > 0 {
err = os.WriteFile(outputName+"_64bit.go", []byte(go64Src), 0644)
if err != nil {
panic(err)
}
}
bindingCppSrc, err := emitBindingCpp(parsed, filepath.Base(parsed.Filename))
if err != nil {
panic(err)