From bdf873ed8fac3aa70a6f831e0e491d4a89f62ce6 Mon Sep 17 00:00:00 2001 From: Elias Naur Date: Fri, 16 Sep 2016 19:19:01 +0200 Subject: [PATCH] bind,cmd: accept Java API in bound packages Accept Java API interface types as arguments and return values from bound Go package functions and methods. Also, allow Go structs to extend Java classes and implement Java interfaces as well as override and implement methods. This is the third and final part of the implementation of the golang/go#16876 proposal. Fixes golang/go#16876 Change-Id: I6951dd87235553ce09abe5117a39a503466163c0 Reviewed-on: https://go-review.googlesource.com/28597 Reviewed-by: David Crawshaw --- bind/bind_test.go | 5 +- bind/gen.go | 47 ++- bind/gengo.go | 19 +- bind/genjava.go | 484 +++++++++++++++++++---- bind/genobjc.go | 15 +- bind/java/ClassesTest.java | 56 +++ bind/java/Seq.java | 35 +- bind/java/seq.h | 2 + bind/java/seq_android.c.support | 48 ++- bind/testdata/basictypes.java.c.golden | 14 +- bind/testdata/classes.go | 46 +++ bind/testdata/classes.go.golden | 463 ++++++++++++++++++++++ bind/testdata/classes.java.c.golden | 252 ++++++++++++ bind/testdata/classes.java.golden | 144 +++++++ bind/testdata/classes.java.h.golden | 72 ++++ bind/testdata/customprefix.java.c.golden | 2 +- bind/testdata/ignore.go.golden | 6 + bind/testdata/ignore.java.c.golden | 8 +- bind/testdata/ignore.java.golden | 6 +- bind/testdata/interfaces.java.c.golden | 60 +-- bind/testdata/interfaces.java.golden | 16 +- bind/testdata/issue10788.go.golden | 5 + bind/testdata/issue10788.java.c.golden | 12 +- bind/testdata/issue10788.java.golden | 6 +- bind/testdata/issue12328.go.golden | 5 + bind/testdata/issue12328.java.golden | 4 +- bind/testdata/issue12403.java.c.golden | 12 +- bind/testdata/issue12403.java.golden | 2 +- bind/testdata/java.java.c.golden | 4 +- bind/testdata/java.java.golden | 8 +- bind/testdata/keywords.java.c.golden | 318 +++++++-------- bind/testdata/keywords.java.golden | 2 +- bind/testdata/structs.go.golden | 10 + bind/testdata/structs.java.c.golden | 26 +- bind/testdata/structs.java.golden | 10 +- bind/testdata/try.java.c.golden | 2 +- bind/testdata/vars.go.golden | 5 + bind/testdata/vars.java.golden | 6 +- bind/testpkg/javapkg/classes.go | 147 +++++++ bind/types.go | 18 + cmd/gobind/gen.go | 2 +- cmd/gomobile/bind.go | 2 +- 42 files changed, 2036 insertions(+), 370 deletions(-) create mode 100644 bind/testdata/classes.go create mode 100644 bind/testdata/classes.go.golden create mode 100644 bind/testdata/classes.java.c.golden create mode 100644 bind/testdata/classes.java.golden create mode 100644 bind/testdata/classes.java.h.golden create mode 100644 bind/testpkg/javapkg/classes.go diff --git a/bind/bind_test.go b/bind/bind_test.go index d5fd0c5..df52cc1 100644 --- a/bind/bind_test.go +++ b/bind/bind_test.go @@ -44,6 +44,7 @@ var tests = []string{ var javaTests = []string{ "testdata/java.go", + "testdata/classes.go", } var fset = token.NewFileSet() @@ -232,7 +233,7 @@ func TestGenJava(t *testing.T) { Pkg: pkg, }, } - g.Init() + g.Init(classes) testCases := []struct { suffix string gen func() error @@ -364,7 +365,7 @@ func TestCustomPrefix(t *testing.T) { Pkg: pkg, }, } - g.Init() + g.Init(nil) testCases := []struct { golden string gen func(w io.Writer) error diff --git a/bind/gen.go b/bind/gen.go index 64a8b3c..7d4ad65 100644 --- a/bind/gen.go +++ b/bind/gen.go @@ -53,6 +53,23 @@ func (list ErrorList) Error() string { return buf.String() } +// interfaceInfo comes from Init and collects the auxillary information +// needed to generate bindings for an exported Go interface in a bound +// package. +type interfaceInfo struct { + obj *types.TypeName + t *types.Interface + summary ifaceSummary +} + +// structInfo comes from Init and collects the auxillary information +// needed to generate bindings for an exported Go struct in a bound +// package. +type structInfo struct { + obj *types.TypeName + t *types.Struct +} + // Generator contains the common Go package information // needed for the specific Go, Java, ObjC generators. // @@ -66,7 +83,7 @@ type Generator struct { Pkg *types.Package err ErrorList - // fields set by Init. + // fields set by init. pkgName string pkgPrefix string funcs []*types.Func @@ -158,11 +175,29 @@ func (g *Generator) Init() { } } -func (_ *Generator) toCFlag(v bool) int { - if v { - return 1 +// constructorType returns the type T for a function on the form +// +// func NewT(...) *T +func (g *Generator) constructorType(f *types.Func) *types.TypeName { + sig := f.Type().(*types.Signature) + res := sig.Results() + if res.Len() != 1 { + return nil } - return 0 + rt := res.At(0).Type() + pt, ok := rt.(*types.Pointer) + if !ok { + return nil + } + nt, ok := pt.Elem().(*types.Named) + if !ok { + return nil + } + obj := nt.Obj() + if !strings.HasPrefix(f.Name(), "New"+obj.Name()) { + return nil + } + return obj } func toCFlag(v bool) int { @@ -298,7 +333,7 @@ func (g *Generator) isSigSupported(t types.Type) bool { // isSupported returns whether the generators can handle the type. func (g *Generator) isSupported(t types.Type) bool { - if isErrorType(t) { + if isErrorType(t) || isJavaType(t) { return true } switch t := t.(type) { diff --git a/bind/gengo.go b/bind/gengo.go index b4200f3..ec26ffc 100644 --- a/bind/gengo.go +++ b/bind/gengo.go @@ -223,6 +223,13 @@ func (g *goGen) genStruct(obj *types.TypeName, T *types.Struct) { g.Outdent() g.Printf("}\n\n") } + // Export constructor for ObjC and Java default no-arg constructors + g.Printf("//export new_%s_%s\n", g.Pkg.Name(), obj.Name()) + g.Printf("func new_%s_%s() C.int32_t {\n", g.Pkg.Name(), obj.Name()) + g.Indent() + g.Printf("return C.int32_t(_seq.ToRefNum(new(%s%s)))\n", g.pkgName(g.Pkg), obj.Name()) + g.Outdent() + g.Printf("}\n") } func (g *goGen) genVar(o *types.Var) { @@ -399,9 +406,10 @@ func (g *goGen) genRead(toVar, fromVar string, typ types.Type, mode varMode) { if iface, ok := t.Underlying().(*types.Interface); ok { hasProxy = makeIfaceSummary(iface).implementable } + isJava := isJavaType(t) o := t.Obj() oPkg := o.Pkg() - if !isErrorType(t) && !g.validPkg(oPkg) { + if !isErrorType(t) && !g.validPkg(oPkg) && !isJava { g.errorf("type %s is defined in %s, which is not bound", t, oPkg) return } @@ -412,7 +420,12 @@ func (g *goGen) genRead(toVar, fromVar string, typ types.Type, mode varMode) { g.Printf(" %s = %s_ref.Get().(%s%s)\n", toVar, toVar, g.pkgName(oPkg), o.Name()) if hasProxy { g.Printf(" } else { // foreign object \n") - g.Printf(" %s = (*proxy%s_%s)(%s_ref)\n", toVar, pkgPrefix(oPkg), o.Name(), toVar) + if isJava { + clsName := flattenName(classNameFor(t)) + g.Printf(" %s = (*proxy_class_%s)(%s_ref)\n", toVar, clsName, toVar) + } else { + g.Printf(" %s = (*proxy%s_%s)(%s_ref)\n", toVar, pkgPrefix(oPkg), o.Name(), toVar) + } } g.Printf(" }\n") g.Printf("}\n") @@ -434,7 +447,7 @@ func (g *goGen) typeString(typ types.Type) string { return types.TypeString(typ, types.RelativeTo(pkg)) } oPkg := obj.Pkg() - if !g.validPkg(oPkg) { + if !g.validPkg(oPkg) && !isJavaType(t) { g.errorf("type %s is defined in %s, which is not bound", t, oPkg) return "TODO" } diff --git a/bind/genjava.go b/bind/genjava.go index 9653563..9e3ab62 100644 --- a/bind/genjava.go +++ b/bind/genjava.go @@ -10,6 +10,8 @@ import ( "go/types" "math" "strings" + + "golang.org/x/mobile/internal/importers/java" ) // TODO(crawshaw): disallow basic android java type names in exported symbols. @@ -21,6 +23,78 @@ type JavaGen struct { JavaPkg string *Generator + + jstructs map[*types.TypeName]*javaClassInfo + clsMap map[string]*java.Class +} + +type javaClassInfo struct { + // The Java class this class extends. + extends *java.Class + // All Java classes and interfaces this class extends and implements. + supers []*java.Class + methods map[string]*java.Func + // Does the extended class include a noarg constructor + hasNoargCon bool + // Constructors for the type, on the form + // func New(...) *Type + cons []*types.Func +} + +// Init intializes the embedded Generator and initializes the Java class information +// needed to generate structs that extend Java classes and interfaces. +func (g *JavaGen) Init(classes []*java.Class) { + g.Generator.Init() + g.clsMap = make(map[string]*java.Class) + for _, cls := range classes { + g.clsMap[cls.Name] = cls + } + g.jstructs = make(map[*types.TypeName]*javaClassInfo) + for _, s := range g.structs { + classes := embeddedJavaClasses(s.t) + if len(classes) == 0 { + continue + } + inf := &javaClassInfo{ + methods: make(map[string]*java.Func), + hasNoargCon: true, // java.lang.Object has a noarg constructor + } + for _, n := range classes { + cls := g.clsMap[n] + for _, f := range cls.AllMethods { + if f.Final { + continue + } + inf.methods[f.GoName] = f + } + inf.supers = append(inf.supers, cls) + if !cls.Interface { + if inf.extends != nil { + g.errorf("%s embeds more than one Java class; only one is allowed.", s.obj) + } + if cls.Final { + g.errorf("%s embeds final Java class %s", s.obj, cls.Name) + } + inf.extends = cls + inf.hasNoargCon = false + for _, f := range cls.Funcs { + if f.Constructor && len(f.Params) == 0 { + inf.hasNoargCon = true + break + } + } + } + } + g.jstructs[s.obj] = inf + } + for _, f := range g.funcs { + if t := g.constructorType(f); t != nil { + jinf := g.jstructs[t] + if jinf != nil { + jinf.cons = append(jinf.cons, f) + } + } + } } // ClassNames returns the list of names of the generated Java classes and interfaces. @@ -39,7 +113,7 @@ func (g *JavaGen) GenClass(idx int) error { ns := len(g.structs) if idx < ns { s := g.structs[idx] - g.genStruct(s.obj, s.t) + g.genStruct(s) } else { iface := g.interfaces[idx-ns] g.genInterface(iface) @@ -50,18 +124,29 @@ func (g *JavaGen) GenClass(idx int) error { return nil } -func (g *JavaGen) genStruct(obj *types.TypeName, T *types.Struct) { +func (g *JavaGen) genStruct(s structInfo) { pkgPath := "" if g.Pkg != nil { pkgPath = g.Pkg.Path() } - g.Printf(javaPreamble, g.javaPkgName(g.Pkg), obj.Name(), g.gobindOpts(), pkgPath) + n := s.obj.Name() + g.Printf(javaPreamble, g.javaPkgName(g.Pkg), n, g.gobindOpts(), pkgPath) - fields := exportedFields(T) - methods := exportedMethodSet(types.NewPointer(obj.Type())) + fields := exportedFields(s.t) + methods := exportedMethodSet(types.NewPointer(s.obj.Type())) var impls []string - pT := types.NewPointer(obj.Type()) + jinf := g.jstructs[s.obj] + if jinf != nil { + impls = append(impls, "Seq.GoObject") + for _, cls := range jinf.supers { + if cls.Interface { + impls = append(impls, cls.Name) + } + } + } + + pT := types.NewPointer(s.obj.Type()) for _, iface := range g.allIntf { if types.AssignableTo(pT, iface.obj.Type()) { n := iface.obj.Name() @@ -71,15 +156,46 @@ func (g *JavaGen) genStruct(obj *types.TypeName, T *types.Struct) { impls = append(impls, n) } } - g.Printf("public final class %s extends Seq.Proxy", obj.Name()) + + g.Printf("public final class %s", n) + if jinf != nil { + if jinf.extends != nil { + g.Printf(" extends %s", jinf.extends.Name) + } + } else { + g.Printf(" extends Seq.Proxy") + } if len(impls) > 0 { g.Printf(" implements %s", strings.Join(impls, ", ")) } g.Printf(" {\n") g.Indent() - n := obj.Name() - g.Printf("private %s(go.Seq.Ref ref) { super(ref); }\n\n", n) + g.Printf("{ Seq.touch(); }\n\n") + if jinf != nil { + g.Printf("private final Seq.Ref ref;\n\n") + for _, f := range jinf.cons { + if !g.isSigSupported(f.Type()) { + g.Printf("// skipped constructor %s.%s with unsupported parameter or return types\n\n", n, f.Name()) + continue + } + g.genConstructor(f, n) + } + if jinf.hasNoargCon { + // Generate constructor for Go instantiated instances. + g.Printf("%s(Seq.Ref ref) { this.ref = ref; }\n\n", n) + // Generate default no-arg constructor + g.Printf("public %s() { this.ref = __New(); }\n\n", n) + g.Printf("private static native Seq.Ref __New();\n\n") + } + g.Printf("@Override public final int incRefnum() {\n") + g.Printf(" int refnum = ref.refnum;\n") + g.Printf(" Seq.incGoRef(refnum);\n") + g.Printf(" return refnum;\n") + g.Printf("}\n\n") + } else { + g.Printf("%s(Seq.Ref ref) { super(ref); }\n\n", n) + } for _, f := range fields { if t := f.Type(); !g.isSupported(t) { @@ -93,15 +209,116 @@ func (g *JavaGen) genStruct(obj *types.TypeName, T *types.Struct) { var isStringer bool for _, m := range methods { if !g.isSigSupported(m.Type()) { - g.Printf("// skipped method %s.%s with unsupported parameter or return types\n\n", obj.Name(), m.Name()) + g.Printf("// skipped method %s.%s with unsupported parameter or return types\n\n", n, m.Name()) continue } - g.genFuncSignature(m, false, false) + var jm *java.Func + if jinf != nil { + jm = jinf.methods[m.Name()] + if jm != nil { + // Check the implicit this argument, if any + sig := m.Type().(*types.Signature) + params := sig.Params() + excess := params.Len() - len(jm.Params) + switch { + case excess < 0: + g.errorf("method %s.%s has fewer arguments than the method it overrides", n, m.Name()) + continue + case excess > 1: + g.errorf("overriding method %s.%s has more arguments than the method it overrides", n, m.Name()) + continue + case excess == 1: + v := params.At(0) + t := v.Type() + if !isJavaType(t) { + g.errorf("the `this` argument to method %s.%s is not a Java type", n, m.Name()) + continue + } + clsName := classNameFor(t) + cls := g.clsMap[clsName] + found := false + for _, sup := range jinf.supers { + if cls == sup { + found = true + break + } + } + if !found { + g.errorf("the type %s of the `this` argument to method %s.%s is not a super class to %s", cls.Name, n, m.Name(), n) + continue + } + } + g.Printf("@Override ") + } + } + g.Printf("public native ") + g.genFuncSignature(m, jm) t := m.Type().(*types.Signature) isStringer = isStringer || (m.Name() == "String" && t.Params().Len() == 0 && t.Results().Len() == 1 && types.Identical(t.Results().At(0).Type(), types.Typ[types.String])) } + if jinf == nil { + g.genObjectMethods(n, fields, isStringer) + } + + g.Outdent() + g.Printf("}\n\n") +} + +func (g *JavaGen) genConstructor(f *types.Func, n string) { + g.Printf("public %s(", n) + g.genFuncArgs(f, nil) + g.Printf(") {\n") + g.Indent() + g.Printf("super(") + sig := f.Type().(*types.Signature) + params := sig.Params() + for i := 0; i < params.Len(); i++ { + if i > 0 { + g.Printf(", ") + } + g.Printf(paramName(params, i)) + } + g.Printf(");\n") + g.Printf("this.ref = __%s(", f.Name()) + for i := 0; i < params.Len(); i++ { + if i > 0 { + g.Printf(", ") + } + g.Printf(paramName(params, i)) + } + g.Printf(");\n") + g.Outdent() + g.Printf("}\n\n") + g.Printf("private static native Seq.Ref __%s(", f.Name()) + g.genFuncArgs(f, nil) + g.Printf(");\n\n") +} + +// genFuncArgs generated Java function arguments declaration for the function f. +// If the supplied overridden java function is supplied, genFuncArgs omits the implicit +// this argument. +func (g *JavaGen) genFuncArgs(f *types.Func, jm *java.Func) { + sig := f.Type().(*types.Signature) + params := sig.Params() + i := 0 + if jm != nil { + // Skip the implicit this argument to the Go method + i = params.Len() - len(jm.Params) + } + for ; i < params.Len(); i++ { + if i > 0 { + g.Printf(", ") + } + v := params.At(i) + name := paramName(params, i) + jt := g.javaType(v.Type()) + g.Printf("%s %s", jt, name) + } +} + +func (g *JavaGen) genObjectMethods(n string, fields []*types.Var, isStringer bool) { g.Printf("@Override public boolean equals(Object o) {\n") g.Indent() g.Printf("if (o == null || !(o instanceof %s)) {\n return false;\n}\n", n) @@ -150,7 +367,7 @@ func (g *JavaGen) genStruct(obj *types.TypeName, T *types.Struct) { g.Printf("return string();\n") } else { g.Printf("StringBuilder b = new StringBuilder();\n") - g.Printf(`b.append("%s").append("{");`, obj.Name()) + g.Printf(`b.append("%s").append("{");`, n) g.Printf("\n") for _, f := range fields { if t := f.Type(); !g.isSupported(t) { @@ -165,9 +382,6 @@ func (g *JavaGen) genStruct(obj *types.TypeName, T *types.Struct) { } g.Outdent() g.Printf("}\n") - - g.Outdent() - g.Printf("}\n\n") } func (g *JavaGen) genInterface(iface interfaceInfo) { @@ -201,7 +415,8 @@ func (g *JavaGen) genInterface(iface interfaceInfo) { g.Printf("// skipped method %s.%s with unsupported parameter or return types\n\n", iface.obj.Name(), m.Name()) continue } - g.genFuncSignature(m, false, true) + g.Printf("public ") + g.genFuncSignature(m, nil) } g.Printf("\n") @@ -309,6 +524,8 @@ func (g *JavaGen) javaType(T types.Type) string { // Java, however the type can be exposed in other ways, such // as an exported field. return "java.lang.Exception" + } else if isJavaType(T) { + return classNameFor(T) } switch T := T.(type) { case *types.Basic: @@ -341,7 +558,7 @@ func (g *JavaGen) javaType(T types.Type) string { return "TODO" } -func (g *JavaGen) genJNIFuncSignature(o *types.Func, sName string, proxy bool) { +func (g *JavaGen) genJNIFuncSignature(o *types.Func, sName string, jm *java.Func, proxy bool) { sig := o.Type().(*types.Signature) res := sig.Results() @@ -375,18 +592,29 @@ func (g *JavaGen) genJNIFuncSignature(o *types.Func, sName string, proxy bool) { } else { g.Printf(g.className()) } - oName := javaNameReplacer(lowerFirst(o.Name())) - if strings.HasSuffix(oName, "_") { - oName += "1" // JNI doesn't like methods ending with underscore, needs the _1 suffixing - } - g.Printf("_%s(JNIEnv* env, ", oName) - if sName != "" { - g.Printf("jobject this") + g.Printf("_") + if jm != nil { + g.Printf(jm.JNIName) } else { - g.Printf("jclass clazz") + oName := javaNameReplacer(lowerFirst(o.Name())) + if strings.HasSuffix(oName, "_") { + oName += "1" // JNI doesn't like methods ending with underscore, needs the _1 suffixing + } + g.Printf(oName) + } + g.Printf("(JNIEnv* env, ") + if sName != "" { + g.Printf("jobject __this__") + } else { + g.Printf("jclass _clazz") } params := sig.Params() - for i := 0; i < params.Len(); i++ { + i := 0 + if jm != nil { + // Skip the implicit this argument, if any. + i = params.Len() - len(jm.Params) + } + for ; i < params.Len(); i++ { g.Printf(", ") v := sig.Params().At(i) name := paramName(params, i) @@ -400,7 +628,7 @@ func (g *JavaGen) jniPkgName() string { return strings.Replace(g.javaPkgName(g.Pkg), ".", "_", -1) } -func (g *JavaGen) genFuncSignature(o *types.Func, static, header bool) { +func (g *JavaGen) genFuncSignature(o *types.Func, jm *java.Func) { sig := o.Type().(*types.Signature) res := sig.Results() @@ -428,27 +656,25 @@ func (g *JavaGen) genFuncSignature(o *types.Func, static, header bool) { return } - g.Printf("public ") - if static { - g.Printf("static ") - } - if !header { - g.Printf("native ") - } - g.Printf("%s %s(", ret, javaNameReplacer(lowerFirst(o.Name()))) - params := sig.Params() - for i := 0; i < params.Len(); i++ { - if i > 0 { - g.Printf(", ") - } - v := sig.Params().At(i) - name := paramName(params, i) - jt := g.javaType(v.Type()) - g.Printf("%s %s", jt, name) + g.Printf("%s ", ret) + if jm != nil { + g.Printf(jm.Name) + } else { + g.Printf(javaNameReplacer(lowerFirst(o.Name()))) } + g.Printf("(") + g.genFuncArgs(o, jm) g.Printf(")") if returnsError { - g.Printf(" throws Exception") + if jm != nil { + if jm.Throws == "" { + g.errorf("%s declares an error return value but the overriden method does not throw", o) + return + } + g.Printf(" throws %s", jm.Throws) + } else { + g.Printf(" throws Exception") + } } g.Printf(";\n") } @@ -481,7 +707,7 @@ func (g *JavaGen) genJavaToC(varName string, t types.Type, mode varMode) { case *types.Basic: switch e.Kind() { case types.Uint8: // Byte. - g.Printf("nbyteslice _%s = go_seq_from_java_bytearray(env, %s, %d);\n", varName, varName, g.toCFlag(mode == modeRetained)) + g.Printf("nbyteslice _%s = go_seq_from_java_bytearray(env, %s, %d);\n", varName, varName, toCFlag(mode == modeRetained)) default: g.errorf("unsupported type: %s", t) } @@ -518,7 +744,7 @@ func (g *JavaGen) genCToJava(toName, fromName string, t types.Type, mode varMode case *types.Basic: switch e.Kind() { case types.Uint8: // Byte. - g.Printf("jbyteArray %s = go_seq_to_java_bytearray(env, %s, %d);\n", toName, fromName, g.toCFlag(mode == modeRetained)) + g.Printf("jbyteArray %s = go_seq_to_java_bytearray(env, %s, %d);\n", toName, fromName, toCFlag(mode == modeRetained)) default: g.errorf("unsupported type: %s", t) } @@ -548,12 +774,19 @@ func (g *JavaGen) genCToJava(toName, fromName string, t types.Type, mode varMode func (g *JavaGen) genFromRefnum(toName, fromName string, t types.Type, o *types.TypeName) { oPkg := o.Pkg() - if !isErrorType(o.Type()) && !g.validPkg(oPkg) { + isJava := isJavaType(o.Type()) + if !isErrorType(o.Type()) && !g.validPkg(oPkg) && !isJava { g.errorf("type %s is defined in package %s, which is not bound", t, oPkg) return } p := pkgPrefix(oPkg) - g.Printf("jobject %s = go_seq_from_refnum(env, %s, proxy_class_%s_%s, proxy_class_%s_%s_cons);\n", toName, fromName, p, o.Name(), p, o.Name()) + g.Printf("jobject %s = go_seq_from_refnum(env, %s, ", toName, fromName) + if isJava { + g.Printf("NULL, NULL") + } else { + g.Printf("proxy_class_%s_%s, proxy_class_%s_%s_cons", p, o.Name(), p, o.Name()) + } + g.Printf(");\n") } func (g *JavaGen) gobindOpts() string { @@ -685,27 +918,84 @@ func (g *JavaGen) genJNIVar(o *types.Var) { g.Printf("}\n\n") } -func (g *JavaGen) genJNIFunc(o *types.Func, sName string, proxy bool) { +func (g *JavaGen) genJNIConstructor(f *types.Func, sName string) { + if !g.isSigSupported(f.Type()) { + return + } + sig := f.Type().(*types.Signature) + + g.Printf("JNIEXPORT jobject JNICALL\n") + g.Printf("Java_%s_%s_%s(JNIEnv *env, jclass clazz", g.jniPkgName(), sName, java.JNIMangle("__"+f.Name())) + params := sig.Params() + for i := 0; i < params.Len(); i++ { + v := params.At(i) + jt := g.jniType(v.Type()) + g.Printf(", %s %s", jt, paramName(params, i)) + } + g.Printf(") {\n") + g.Indent() + for i := 0; i < params.Len(); i++ { + name := paramName(params, i) + g.genJavaToC(name, params.At(i).Type(), modeTransient) + } + // Constructors always have one result parameter, a *T. + g.Printf("int32_t refnum = proxy%s__%s(", g.pkgPrefix, f.Name()) + for i := 0; i < params.Len(); i++ { + if i > 0 { + g.Printf(", ") + } + g.Printf("_%s", paramName(params, i)) + } + g.Printf(");\n") + for i := 0; i < params.Len(); i++ { + g.genRelease(paramName(params, i), params.At(i).Type(), modeTransient) + } + // Pass no proxy class so that the Seq.Ref is returned instead. + g.Printf("return go_seq_from_refnum(env, refnum, NULL, NULL);\n") + g.Outdent() + g.Printf("}\n\n") +} + +func (g *JavaGen) genJNIFunc(o *types.Func, sName string, jm *java.Func, proxy, isjava bool) { if !g.isSigSupported(o.Type()) { n := o.Name() if sName != "" { n = sName + "." + n } - g.Printf("// skipped function %s with unsupported parameter or return types\n\n", o.Name()) + g.Printf("// skipped function %s with unsupported parameter or return types\n\n", n) return } - g.genJNIFuncSignature(o, sName, proxy) - sig := o.Type().(*types.Signature) - res := sig.Results() + g.genJNIFuncSignature(o, sName, jm, proxy) g.Printf(" {\n") g.Indent() + g.genJNIFuncBody(o, sName, jm, isjava) + g.Outdent() + g.Printf("}\n\n") +} +func (g *JavaGen) genJNIFuncBody(o *types.Func, sName string, jm *java.Func, isjava bool) { + sig := o.Type().(*types.Signature) + res := sig.Results() if sName != "" { - g.Printf("int32_t o = go_seq_to_refnum(env, this);\n") + if isjava { + // We need the Go object backing this GoObject. Use + // the _go variant (here only) to get the Go refnum. + g.Printf("int32_t o = go_seq_to_refnum_go(env, __this__);\n") + } else { + g.Printf("int32_t o = go_seq_to_refnum(env, __this__);\n") + } } params := sig.Params() - for i := 0; i < params.Len(); i++ { + first := 0 + if jm != nil { + // Start after the implicit this argument. + first = params.Len() - len(jm.Params) + if first >= 1 { + g.Printf("int32_t _%s = go_seq_to_refnum(env, __this__);\n", paramName(params, 0)) + } + } + for i := first; i < params.Len(); i++ { name := paramName(params, i) g.genJavaToC(name, params.At(i).Type(), modeTransient) } @@ -722,6 +1012,7 @@ func (g *JavaGen) genJNIFunc(o *types.Func, sName string, proxy bool) { if sName != "" { g.Printf("o") } + // Pass all arguments, including the implicit this argument. for i := 0; i < params.Len(); i++ { if i > 0 || sName != "" { g.Printf(", ") @@ -729,7 +1020,7 @@ func (g *JavaGen) genJNIFunc(o *types.Func, sName string, proxy bool) { g.Printf("_%s", paramName(params, i)) } g.Printf(");\n") - for i := 0; i < params.Len(); i++ { + for i := first; i < params.Len(); i++ { g.genRelease(paramName(params, i), params.At(i).Type(), modeTransient) } for i := 0; i < res.Len(); i++ { @@ -747,8 +1038,6 @@ func (g *JavaGen) genJNIFunc(o *types.Func, sName string, proxy bool) { g.Printf("go_seq_maybe_throw_exception(env, _r%d);\n", i) } } - g.Outdent() - g.Printf("}\n\n") } // genRelease cleans up arguments that weren't copied in genJavaToC. @@ -761,9 +1050,7 @@ func (g *JavaGen) genRelease(varName string, t types.Type, mode varMode) { switch e.Kind() { case types.Uint8: // Byte. if mode == modeTransient { - g.Printf("if (_%s.ptr != NULL) {\n", varName) - g.Printf(" (*env)->ReleaseByteArrayElements(env, %s, _%s.ptr, 0);\n", varName, varName) - g.Printf("}\n") + g.Printf("go_seq_release_byte_array(env, %s, _%s.ptr);\n", varName, varName) } } } @@ -780,9 +1067,7 @@ func (g *JavaGen) genMethodInterfaceProxy(oName string, m *types.Func) { res := sig.Results() g.genInterfaceMethodSignature(m, oName, false) g.Indent() - // Push a JNI reference frame with a conservative capacity of two for each per parameter (Seq.Ref and Seq.Object), - // plus extra space for the receiver, the return value, and exception (if any). - g.Printf("JNIEnv *env = go_seq_push_local_frame(%d);\n", 2*params.Len()+10) + g.Printf("JNIEnv *env = go_seq_push_local_frame(%d);\n", params.Len()) g.Printf("jobject o = go_seq_from_refnum(env, refnum, proxy_class_%s_%s, proxy_class_%s_%s_cons);\n", g.pkgPrefix, oName, g.pkgPrefix, oName) for i := 0; i < params.Len(); i++ { pn := paramName(params, i) @@ -991,6 +1276,13 @@ func (g *JavaGen) GenC() error { g.Indent() g.Printf("jclass clazz;\n") for _, s := range g.structs { + if jinf, ok := g.jstructs[s.obj]; ok { + // Leave the class and constructor NULL for Java classes with no + // default constructor. + if !jinf.hasNoargCon { + continue + } + } g.Printf("clazz = (*env)->FindClass(env, %q);\n", g.jniClassSigPrefix(s.obj.Pkg())+s.obj.Name()) g.Printf("proxy_class_%s_%s = (*env)->NewGlobalRef(env, clazz);\n", g.pkgPrefix, s.obj.Name()) g.Printf("proxy_class_%s_%s_cons = (*env)->GetMethodID(env, clazz, \"\", \"(Lgo/Seq$Ref;)V\");\n", g.pkgPrefix, s.obj.Name()) @@ -1027,12 +1319,33 @@ func (g *JavaGen) GenC() error { g.Outdent() g.Printf("}\n\n") for _, f := range g.funcs { - g.genJNIFunc(f, "", false) + g.genJNIFunc(f, "", nil, false, false) } for _, s := range g.structs { sName := s.obj.Name() + jinf := g.jstructs[s.obj] + if jinf != nil { + for _, f := range jinf.cons { + g.genJNIConstructor(f, sName) + } + if jinf.hasNoargCon { + g.Printf("JNIEXPORT jobject JNICALL\n") + g.Printf("Java_%s_%s_%s(JNIEnv *env, jclass clazz) {\n", g.jniPkgName(), sName, java.JNIMangle("__New")) + g.Indent() + g.Printf("int32_t refnum = new_%s_%s();\n", g.pkgPrefix, sName) + // Pass no proxy class so that the Seq.Ref is returned instead. + g.Printf("return go_seq_from_refnum(env, refnum, NULL, NULL);\n") + g.Outdent() + g.Printf("}\n\n") + } + } + for _, m := range exportedMethodSet(types.NewPointer(s.obj.Type())) { - g.genJNIFunc(m, sName, false) + var jm *java.Func + if jinf != nil { + jm = jinf.methods[m.Name()] + } + g.genJNIFunc(m, sName, jm, false, jinf != nil) } for _, f := range exportedFields(s.t) { g.genJNIField(s.obj, f) @@ -1040,7 +1353,7 @@ func (g *JavaGen) GenC() error { } for _, iface := range g.interfaces { for _, m := range iface.summary.callable { - g.genJNIFunc(m, iface.obj.Name(), true) + g.genJNIFunc(m, iface.obj.Name(), nil, true, false) g.genMethodInterfaceProxy(iface.obj.Name(), m) } } @@ -1089,7 +1402,8 @@ func (g *JavaGen) GenJava() error { g.Printf("// skipped method %s.%s with unsupported parameter or return types\n\n", iface.obj.Name(), m.Name()) continue } - g.genFuncSignature(m, false, false) + g.Printf("public native ") + g.genFuncSignature(m, nil) } g.Outdent() @@ -1110,7 +1424,8 @@ func (g *JavaGen) GenJava() error { g.Printf("// skipped function %s with unsupported parameter or return types\n\n", f.Name()) continue } - g.genFuncSignature(f, true, false) + g.Printf("public static native ") + g.genFuncSignature(f, nil) } g.Outdent() @@ -1122,9 +1437,36 @@ func (g *JavaGen) GenJava() error { return nil } +// embeddedJavaClasses returns the possible empty list of Java types embedded +// in the given struct type. +func embeddedJavaClasses(t *types.Struct) []string { + clsSet := make(map[string]struct{}) + var classes []string + for i := 0; i < t.NumFields(); i++ { + f := t.Field(i) + if !f.Exported() { + continue + } + if t := f.Type(); isJavaType(t) { + cls := classNameFor(t) + if _, exists := clsSet[cls]; !exists { + clsSet[cls] = struct{}{} + classes = append(classes, cls) + } + } + } + return classes +} + +func classNameFor(t types.Type) string { + obj := t.(*types.Named).Obj() + pkg := obj.Pkg() + return strings.Replace(pkg.Path()[len("Java/"):], "/", ".", -1) + "." + obj.Name() +} + const ( javaProxyPreamble = `private static final class proxy%[1]s extends Seq.Proxy implements %[1]s { - proxy%[1]s(Seq.Ref ref) { super(ref); } + proxy%[1]s(Seq.Ref ref) { super(ref); } ` javaPreamble = `// Java class %[1]s.%[2]s is a proxy for talking to a Go program. diff --git a/bind/genobjc.go b/bind/genobjc.go index cce1f0a..49467f0 100644 --- a/bind/genobjc.go +++ b/bind/genobjc.go @@ -28,17 +28,6 @@ type objcGen struct { *Generator } -type interfaceInfo struct { - obj *types.TypeName - t *types.Interface - summary ifaceSummary -} - -type structInfo struct { - obj *types.TypeName - t *types.Struct -} - func (g *objcGen) init() { g.Generator.Init() g.namePrefix = g.namePrefixOf(g.Pkg) @@ -558,7 +547,7 @@ func (g *objcGen) genWrite(varName string, t types.Type, mode varMode) { case *types.Basic: switch e.Kind() { case types.Uint8: // Byte. - g.Printf("nbyteslice _%s = go_seq_from_objc_bytearray(%s, %d);\n", varName, varName, g.toCFlag(mode == modeRetained)) + g.Printf("nbyteslice _%s = go_seq_from_objc_bytearray(%s, %d);\n", varName, varName, toCFlag(mode == modeRetained)) default: g.errorf("unsupported type: %s", t) } @@ -621,7 +610,7 @@ func (g *objcGen) genRead(toName, fromName string, t types.Type, mode varMode) { case *types.Basic: switch e.Kind() { case types.Uint8: // Byte. - g.Printf("NSData *%s = go_seq_to_objc_bytearray(%s, %d);\n", toName, fromName, g.toCFlag(mode == modeRetained)) + g.Printf("NSData *%s = go_seq_to_objc_bytearray(%s, %d);\n", toName, fromName, toCFlag(mode == modeRetained)) default: g.errorf("unsupported type: %s", t) } diff --git a/bind/java/ClassesTest.java b/bind/java/ClassesTest.java index abe4bac..54d3f4e 100644 --- a/bind/java/ClassesTest.java +++ b/bind/java/ClassesTest.java @@ -13,6 +13,10 @@ import java.util.Arrays; import java.util.Random; import go.javapkg.Javapkg; +import go.javapkg.GoObject; +import go.javapkg.GoRunnable; +import go.javapkg.GoSubset; +import go.javapkg.GoInputStream; public class ClassesTest extends InstrumentationTestCase { public void testConst() { @@ -65,4 +69,56 @@ public class ClassesTest extends InstrumentationTestCase { } assertNotNull("RuntimeException", exc); } + + public void testGoObject() { + Runnable r = new GoRunnable(); + r.run(); + assertTrue("GoRunnable.toString", r.toString().equals(Javapkg.ToStringPrefix)); + Runnable r2 = ((GoRunnable)r).getThis(); + assertTrue("GoObject.this", r == r2); + Object o = new GoObject(); + assertEquals("GoObject hashCode", 42, o.hashCode()); + Object o2 = Javapkg.constructGoObject(); + assertEquals("GoObject hashCode", 42, o2.hashCode()); + assertTrue("GoObject.toString", o.toString().startsWith(Javapkg.ToStringPrefix)); + Javapkg.runRunnable(r); + final boolean[] ran = new boolean[1]; + Runnable r3 = new Runnable(){ + @Override public void run() { + ran[0] = true; + } + }; + Javapkg.runRunnable(r3); + assertTrue("RunRunnable", ran[0]); + assertTrue("RunnableRoundtrip Java", r3 == Javapkg.runnableRoundtrip(r3)); + assertTrue("RunnableRoundtrip Go", r == Javapkg.runnableRoundtrip(r)); + Runnable r5 = Javapkg.constructGoRunnable(); + r5.run(); + } + + public void testTypedException() { + InputStream is = new GoInputStream(); + Exception exc = null; + try { + is.read(); + } catch (IOException e) { + exc = e; + } + assertNotNull("IOException", exc); + assertEquals("IOException message", Javapkg.IOExceptionMessage, exc.getMessage()); + } + + public void testInnerClass() { + Character.Subset s = new Character.Subset(""){}; + Character.Subset s2 = new GoSubset(""); + Javapkg.callSubset(s); + Javapkg.callSubset(s2); + } + + public void testNew() { + Object o = Javapkg.newJavaObject(); + assertTrue("new Object()", o != null); + Integer i = Javapkg.newJavaInteger(); + assertEquals("new Integer(42)", 42, i.intValue()); + } } diff --git a/bind/java/Seq.java b/bind/java/Seq.java index 3d26c8d..2d636a9 100644 --- a/bind/java/Seq.java +++ b/bind/java/Seq.java @@ -67,16 +67,24 @@ public class Seq { tracker.incRefnum(refnum); } + // incRef increments the reference count of Java objects. + // For proxies for Go objects, it calls into the Proxy method + // incRefnum() to make sure the Go reference count is positive + // even if the Proxy is garbage collected and its Ref is finalized. public static int incRef(Object o) { return tracker.inc(o); } + public static int incGoObjectRef(GoObject o) { + return o.incRefnum(); + } + public static Ref getRef(int refnum) { return tracker.get(refnum); } // Increment the Go reference count before sending over a refnum. - static native void incGoRef(int refnum); + public static native void incGoRef(int refnum); // Informs the Go ref tracker that Java is done with this ref. static native void destroyRef(int refnum); @@ -86,20 +94,31 @@ public class Seq { tracker.dec(refnum); } - // A Proxy is a Java object that proxies a Go object. - public static abstract class Proxy { + // A GoObject is a Java class implemented in Go. When a GoObject + // is passed to Go, it is wrapped in a Go proxy, to make it behave + // the same as passing a regular Java class. + public interface GoObject { + // Increment refcount and return the refnum of the proxy. + // + // The Go reference count need to be bumped while the + // refnum is passed to Go, to avoid finalizing and + // invalidating it before being translated on the Go side. + int incRefnum(); + } + + // A Proxy is a Java object that proxies a Go object. Proxies, unlike + // GoObjects, are unwrapped to their Go counterpart when deserialized + // in Go. + public static abstract class Proxy implements GoObject { private final Ref ref; protected Proxy(Ref ref) { this.ref = ref; } - public final int incRefnum() { - // The Go reference count need to be bumped while the - // refnum is passed to Go, to avoid finalizing and - // invalidating it before being translated on the Go side. + @Override public final int incRefnum() { int refnum = ref.refnum; - incGoRef(refnum); + Seq.incGoRef(refnum); return refnum; } } diff --git a/bind/java/seq.h b/bind/java/seq.h index ce18a46..6c0ae58 100644 --- a/bind/java/seq.h +++ b/bind/java/seq.h @@ -35,6 +35,7 @@ typedef jlong nint; extern void go_seq_dec_ref(int32_t ref); extern void go_seq_inc_ref(int32_t ref); extern int32_t go_seq_to_refnum(JNIEnv *env, jobject o); +extern int32_t go_seq_to_refnum_go(JNIEnv *env, jobject o); extern jobject go_seq_from_refnum(JNIEnv *env, int32_t refnum, jclass proxy_class, jmethodID proxy_cons); extern void go_seq_maybe_throw_exception(JNIEnv *env, jobject msg); @@ -44,6 +45,7 @@ extern jobject go_seq_wrap_exception(JNIEnv *env); extern jbyteArray go_seq_to_java_bytearray(JNIEnv *env, nbyteslice s, int copy); extern nbyteslice go_seq_from_java_bytearray(JNIEnv *env, jbyteArray s, int copy); +extern void go_seq_release_byte_array(JNIEnv *env, jbyteArray arr, jbyte* ptr); extern jstring go_seq_to_java_string(JNIEnv *env, nstring str); extern nstring go_seq_from_java_string(JNIEnv *env, jstring s); diff --git a/bind/java/seq_android.c.support b/bind/java/seq_android.c.support index c0f3647..19a57d3 100644 --- a/bind/java/seq_android.c.support +++ b/bind/java/seq_android.c.support @@ -29,13 +29,14 @@ static jmethodID seq_throw_exc; static jmethodID seq_getRef; static jmethodID seq_decRef; static jmethodID seq_incRef; +static jmethodID seq_incGoObjectRef; static jmethodID seq_incRefnum; static jmethodID seq_wrapThrowable; -static jmethodID throwable_getMessage; - static jfieldID ref_objField; +static jclass throwable_class; + // env_destructor is registered as a thread data key destructor to // clean up a Go thread that is attached to the JVM. static void env_destructor(void *env) { @@ -61,7 +62,11 @@ static JNIEnv *go_seq_get_thread_env(void) { void go_seq_maybe_throw_exception(JNIEnv *env, jobject msg) { if (msg != NULL) { - (*env)->CallStaticVoidMethod(env, seq_class, seq_throw_exc, msg); + if ((*env)->IsInstanceOf(env, msg, throwable_class)) { + (*env)->Throw(env, msg); + } else { + (*env)->CallStaticVoidMethod(env, seq_class, seq_throw_exc, msg); + } } } @@ -220,6 +225,13 @@ nbyteslice go_seq_from_java_bytearray(JNIEnv *env, jbyteArray arr, int copy) { return res; } +int32_t go_seq_to_refnum_go(JNIEnv *env, jobject o) { + if (o == NULL) { + return NULL_REFNUM; + } + return (int32_t)(*env)->CallStaticIntMethod(env, seq_class, seq_incGoObjectRef, o); +} + int32_t go_seq_to_refnum(JNIEnv *env, jobject o) { if (o == NULL) { return NULL_REFNUM; @@ -241,9 +253,12 @@ jobject go_seq_from_refnum(JNIEnv *env, int32_t refnum, jclass proxy_class, jmet (*env)->CallStaticVoidMethod(env, seq_class, seq_decRef, (jint)refnum); // return ref.obj return (*env)->GetObjectField(env, ref, ref_objField); - } else { + } else if (proxy_class != NULL) { // return new (ref) return (*env)->NewObject(env, proxy_class, proxy_cons, ref); + } else { + // We're inside a Java proxy constructor and only need the Seq.Ref + return ref; } } @@ -258,9 +273,13 @@ jstring go_seq_to_java_string(JNIEnv *env, nstring str) { // go_seq_push_local_frame retrieves or creates the JNIEnv* for the current thread // and pushes a JNI reference frame. Must be matched with call to go_seq_pop_local_frame. -JNIEnv *go_seq_push_local_frame(jint cap) { +JNIEnv *go_seq_push_local_frame(jint nargs) { JNIEnv *env = go_seq_get_thread_env(); - if ((*env)->PushLocalFrame(env, cap) < 0) { + // Given the number of function arguments, compute a conservative bound for the minimal frame size. + // Assume two slots for each per parameter (Seq.Ref and Seq.Object) and add extra + // extra space for the receiver, the return value, and exception (if any). + jint frameSize = 2*nargs + 10; + if ((*env)->PushLocalFrame(env, frameSize) < 0) { LOG_FATAL("PushLocalFrame failed"); } return env; @@ -312,18 +331,19 @@ Java_go_Seq_init(JNIEnv *env, jclass clazz) { if (seq_incRef == NULL) { LOG_FATAL("failed to find method Seq.incRef"); } + seq_incGoObjectRef = (*env)->GetStaticMethodID(env, seq_class, "incGoObjectRef", "(Lgo/Seq$GoObject;)I"); + if (seq_incGoObjectRef == NULL) { + LOG_FATAL("failed to find method Seq.incGoObjectRef"); + } seq_wrapThrowable = (*env)->GetStaticMethodID(env, seq_class, "wrapThrowable", "(Ljava/lang/Throwable;)Lgo/error;"); if (seq_wrapThrowable == NULL) { LOG_FATAL("failed to find method Seq.wrapThrowable"); } - jclass throwable_class = (*env)->FindClass(env, "java/lang/Throwable"); + throwable_class = (*env)->FindClass(env, "java/lang/Throwable"); if (throwable_class == NULL) { LOG_FATAL("failed to find Throwable class"); } - throwable_getMessage = (*env)->GetMethodID(env, throwable_class, "getMessage", "()Ljava/lang/String;"); - if (throwable_getMessage == NULL) { - LOG_FATAL("failed to find method Throwable.getMessage"); - } + throwable_class = (*env)->NewGlobalRef(env, throwable_class); jclass ref_class = (*env)->FindClass(env, "go/Seq$Ref"); if (ref_class == NULL) { LOG_FATAL("failed to find the Seq.Ref class"); @@ -376,3 +396,9 @@ jmethodID go_seq_get_method_id(jclass clazz, const char *name, const char *sig) go_seq_pop_local_frame(env); return m; } + +void go_seq_release_byte_array(JNIEnv *env, jbyteArray arr, jbyte* ptr) { + if (ptr != NULL) { + (*env)->ReleaseByteArrayElements(env, arr, ptr, 0); + } +} diff --git a/bind/testdata/basictypes.java.c.golden b/bind/testdata/basictypes.java.c.golden index c645224..11738f5 100644 --- a/bind/testdata/basictypes.java.c.golden +++ b/bind/testdata/basictypes.java.c.golden @@ -16,7 +16,7 @@ Java_go_basictypes_Basictypes__1init(JNIEnv *env, jclass _unused) { } JNIEXPORT jboolean JNICALL -Java_go_basictypes_Basictypes_bool(JNIEnv* env, jclass clazz, jboolean p0) { +Java_go_basictypes_Basictypes_bool(JNIEnv* env, jclass _clazz, jboolean p0) { char _p0 = (char)p0; char r0 = proxybasictypes__Bool(_p0); jboolean _r0 = r0 ? JNI_TRUE : JNI_FALSE; @@ -24,25 +24,23 @@ Java_go_basictypes_Basictypes_bool(JNIEnv* env, jclass clazz, jboolean p0) { } JNIEXPORT jbyteArray JNICALL -Java_go_basictypes_Basictypes_byteArrays(JNIEnv* env, jclass clazz, jbyteArray x) { +Java_go_basictypes_Basictypes_byteArrays(JNIEnv* env, jclass _clazz, jbyteArray x) { nbyteslice _x = go_seq_from_java_bytearray(env, x, 0); nbyteslice r0 = proxybasictypes__ByteArrays(_x); - if (_x.ptr != NULL) { - (*env)->ReleaseByteArrayElements(env, x, _x.ptr, 0); - } + go_seq_release_byte_array(env, x, _x.ptr); jbyteArray _r0 = go_seq_to_java_bytearray(env, r0, 1); return _r0; } JNIEXPORT void JNICALL -Java_go_basictypes_Basictypes_error(JNIEnv* env, jclass clazz) { +Java_go_basictypes_Basictypes_error(JNIEnv* env, jclass _clazz) { int32_t r0 = proxybasictypes__Error(); jobject _r0 = go_seq_from_refnum(env, r0, proxy_class__error, proxy_class__error_cons); go_seq_maybe_throw_exception(env, _r0); } JNIEXPORT jlong JNICALL -Java_go_basictypes_Basictypes_errorPair(JNIEnv* env, jclass clazz) { +Java_go_basictypes_Basictypes_errorPair(JNIEnv* env, jclass _clazz) { struct proxybasictypes__ErrorPair_return res = proxybasictypes__ErrorPair(); jlong _r0 = (jlong)res.r0; jobject _r1 = go_seq_from_refnum(env, res.r1, proxy_class__error, proxy_class__error_cons); @@ -51,7 +49,7 @@ Java_go_basictypes_Basictypes_errorPair(JNIEnv* env, jclass clazz) { } JNIEXPORT void JNICALL -Java_go_basictypes_Basictypes_ints(JNIEnv* env, jclass clazz, jbyte x, jshort y, jint z, jlong t, jlong u) { +Java_go_basictypes_Basictypes_ints(JNIEnv* env, jclass _clazz, jbyte x, jshort y, jint z, jlong t, jlong u) { int8_t _x = (int8_t)x; int16_t _y = (int16_t)y; int32_t _z = (int32_t)z; diff --git a/bind/testdata/classes.go b/bind/testdata/classes.go new file mode 100644 index 0000000..17497dd --- /dev/null +++ b/bind/testdata/classes.go @@ -0,0 +1,46 @@ +// Copyright 2014 The Go Authors. All rights reserved. +// Use of this source code is governed by a BSD-style +// license that can be found in the LICENSE file. + +package java + +import ( + "Java/java/io" + "Java/java/lang" + "Java/java/util/concurrent" +) + +type Runnable struct { + lang.Runnable +} + +func (r *Runnable) Run(this lang.Runnable) { +} + +type InputStream struct { + io.InputStream +} + +func (_ *InputStream) Read() (int32, error) { + return 0, nil +} + +func NewInputStream() *InputStream { + return new(InputStream) +} + +type Future struct { + concurrent.Future +} + +func (_ *Future) Get() lang.Object { + return nil +} + +func (_ *Future) Get2(_ int64, _ concurrent.TimeUnit) lang.Object { + return nil +} + +type Object struct { + lang.Object +} diff --git a/bind/testdata/classes.go.golden b/bind/testdata/classes.go.golden new file mode 100644 index 0000000..d912b50 --- /dev/null +++ b/bind/testdata/classes.go.golden @@ -0,0 +1,463 @@ +// File is generated by gobind. Do not edit. + +package Java + +// Used to silence this package not used errors +const Dummy = 0 + +type Java_lang_Runnable interface { + Run() +} + +type Java_io_InputStream interface { + Read() (int32, error) + Super() Java_io_InputStream +} + +type Java_util_concurrent_Future interface { + Get() (Java_lang_Object, error) + Get2(a0 int64, a1 Java_util_concurrent_TimeUnit) (Java_lang_Object, error) +} + +type Java_lang_Object interface { + Super() Java_lang_Object +} + +type Java_util_concurrent_TimeUnit interface { + Super() Java_util_concurrent_TimeUnit +} + +// File is generated by gobind. Do not edit. + +package gomobile_bind + +/* +#include // for free() +#include +#include "seq.h" +#include "classes.h" +*/ +import "C" + +import ( + "Java" + _seq "golang.org/x/mobile/bind/seq" +) + +type proxy interface { Bind_proxy_refnum__() int32 } + +// Suppress unused package error + +var _ = _seq.FromRefNum +const _ = Java.Dummy + +//export initClasses +func initClasses() { + C.init_proxies() + init_java_lang_Runnable() + init_java_io_InputStream() + init_java_util_concurrent_Future() + init_java_lang_Object() + init_java_util_concurrent_TimeUnit() +} + +func init_java_lang_Runnable() { + cls := C.CString("java/lang/Runnable") + clazz := C.go_seq_find_class(cls) + C.free(unsafe.Pointer(cls)) + if clazz == nil { + return + } +} + +type proxy_class_java_lang_Runnable _seq.Ref + +func (p *proxy_class_java_lang_Runnable) Bind_proxy_refnum__() int32 { return (*_seq.Ref)(p).Bind_IncNum() } + +func (p *proxy_class_java_lang_Runnable) Run() { + res := C.cproxy_java_lang_Runnable_run(C.jint(p.Bind_proxy_refnum__())) + var _exc error + _exc_ref := _seq.FromRefNum(int32(res)) + if _exc_ref != nil { + if res < 0 { // go object + _exc = _exc_ref.Get().(error) + } else { // foreign object + _exc = (*proxy_error)(_exc_ref) + } + } + if (_exc != nil) { panic(_exc) } +} + +func init_java_io_InputStream() { + cls := C.CString("java/io/InputStream") + clazz := C.go_seq_find_class(cls) + C.free(unsafe.Pointer(cls)) + if clazz == nil { + return + } +} + +type proxy_class_java_io_InputStream _seq.Ref + +func (p *proxy_class_java_io_InputStream) Bind_proxy_refnum__() int32 { return (*_seq.Ref)(p).Bind_IncNum() } + +func (p *proxy_class_java_io_InputStream) Read() (int32, error) { + res := C.cproxy_java_io_InputStream_read__(C.jint(p.Bind_proxy_refnum__())) + _res := int32(res.res) + var _exc error + _exc_ref := _seq.FromRefNum(int32(res.exc)) + if _exc_ref != nil { + if res.exc < 0 { // go object + _exc = _exc_ref.Get().(error) + } else { // foreign object + _exc = (*proxy_error)(_exc_ref) + } + } + return _res, _exc +} + +func (p *proxy_class_java_io_InputStream) Super() Java.Java_io_InputStream { + return &super_java_io_InputStream{p} +} + +type super_java_io_InputStream struct {*proxy_class_java_io_InputStream} + +func (p *super_java_io_InputStream) Read() (int32, error) { + res := C.csuper_java_io_InputStream_read__(C.jint(p.Bind_proxy_refnum__())) + _res := int32(res.res) + var _exc error + _exc_ref := _seq.FromRefNum(int32(res.exc)) + if _exc_ref != nil { + if res.exc < 0 { // go object + _exc = _exc_ref.Get().(error) + } else { // foreign object + _exc = (*proxy_error)(_exc_ref) + } + } + return _res, _exc +} + +func init_java_util_concurrent_Future() { + cls := C.CString("java/util/concurrent/Future") + clazz := C.go_seq_find_class(cls) + C.free(unsafe.Pointer(cls)) + if clazz == nil { + return + } +} + +type proxy_class_java_util_concurrent_Future _seq.Ref + +func (p *proxy_class_java_util_concurrent_Future) Bind_proxy_refnum__() int32 { return (*_seq.Ref)(p).Bind_IncNum() } + +func (p *proxy_class_java_util_concurrent_Future) Get() (Java.Java_lang_Object, error) { + res := C.cproxy_java_util_concurrent_Future_get__(C.jint(p.Bind_proxy_refnum__())) + var _res Java.Java_lang_Object + _res_ref := _seq.FromRefNum(int32(res.res)) + if _res_ref != nil { + if res.res < 0 { // go object + _res = _res_ref.Get().(Java.Java_lang_Object) + } else { // foreign object + _res = (*proxy_class_java_lang_Object)(_res_ref) + } + } + var _exc error + _exc_ref := _seq.FromRefNum(int32(res.exc)) + if _exc_ref != nil { + if res.exc < 0 { // go object + _exc = _exc_ref.Get().(error) + } else { // foreign object + _exc = (*proxy_error)(_exc_ref) + } + } + return _res, _exc +} + +func (p *proxy_class_java_util_concurrent_Future) Get2(a0 int64, a1 Java.Java_util_concurrent_TimeUnit) (Java.Java_lang_Object, error) { + _a0 := C.jlong(a0) + var _a1 C.jint = _seq.NullRefNum + if a1 != nil { + _a1 = C.jint(_seq.ToRefNum(a1)) + } + res := C.cproxy_java_util_concurrent_Future_get__JLjava_util_concurrent_TimeUnit_2(C.jint(p.Bind_proxy_refnum__()), _a0, _a1) + var _res Java.Java_lang_Object + _res_ref := _seq.FromRefNum(int32(res.res)) + if _res_ref != nil { + if res.res < 0 { // go object + _res = _res_ref.Get().(Java.Java_lang_Object) + } else { // foreign object + _res = (*proxy_class_java_lang_Object)(_res_ref) + } + } + var _exc error + _exc_ref := _seq.FromRefNum(int32(res.exc)) + if _exc_ref != nil { + if res.exc < 0 { // go object + _exc = _exc_ref.Get().(error) + } else { // foreign object + _exc = (*proxy_error)(_exc_ref) + } + } + return _res, _exc +} + +func init_java_lang_Object() { + cls := C.CString("java/lang/Object") + clazz := C.go_seq_find_class(cls) + C.free(unsafe.Pointer(cls)) + if clazz == nil { + return + } +} + +type proxy_class_java_lang_Object _seq.Ref + +func (p *proxy_class_java_lang_Object) Bind_proxy_refnum__() int32 { return (*_seq.Ref)(p).Bind_IncNum() } + +func (p *proxy_class_java_lang_Object) Super() Java.Java_lang_Object { + return &super_java_lang_Object{p} +} + +type super_java_lang_Object struct {*proxy_class_java_lang_Object} + +func init_java_util_concurrent_TimeUnit() { + cls := C.CString("java/util/concurrent/TimeUnit") + clazz := C.go_seq_find_class(cls) + C.free(unsafe.Pointer(cls)) + if clazz == nil { + return + } +} + +type proxy_class_java_util_concurrent_TimeUnit _seq.Ref + +func (p *proxy_class_java_util_concurrent_TimeUnit) Bind_proxy_refnum__() int32 { return (*_seq.Ref)(p).Bind_IncNum() } + +func (p *proxy_class_java_util_concurrent_TimeUnit) Super() Java.Java_util_concurrent_TimeUnit { + return &super_java_util_concurrent_TimeUnit{p} +} + +type super_java_util_concurrent_TimeUnit struct {*proxy_class_java_util_concurrent_TimeUnit} + +// Package gomobile_bind is an autogenerated binder stub for package java. +// gobind -lang=go classes +// +// File is generated by gobind. Do not edit. +package gomobile_bind + +/* +#include +#include +#include "seq.h" +#include "java.h" + +*/ +import "C" + +import ( + "Java/java/io" + "Java/java/lang" + "Java/java/util/concurrent" + "classes" + _seq "golang.org/x/mobile/bind/seq" +) + +// suppress the error if seq ends up unused +var _ = _seq.FromRefNum + +//export proxyjava_Future_Future_Set +func proxyjava_Future_Future_Set(refnum C.int32_t, v C.int32_t) { + ref := _seq.FromRefNum(int32(refnum)) + var _v concurrent.Future + _v_ref := _seq.FromRefNum(int32(v)) + if _v_ref != nil { + if v < 0 { // go object + _v = _v_ref.Get().(concurrent.Future) + } else { // foreign object + _v = (*proxy_class_java_util_concurrent_Future)(_v_ref) + } + } + ref.Get().(*java.Future).Future = _v +} + +//export proxyjava_Future_Future_Get +func proxyjava_Future_Future_Get(refnum C.int32_t) C.int32_t { + ref := _seq.FromRefNum(int32(refnum)) + v := ref.Get().(*java.Future).Future + var _v C.int32_t = _seq.NullRefNum + if v != nil { + _v = C.int32_t(_seq.ToRefNum(v)) + } + return _v +} + +//export proxyjava_Future_Get +func proxyjava_Future_Get(refnum C.int32_t) C.int32_t { + ref := _seq.FromRefNum(int32(refnum)) + v := ref.Get().(*java.Future) + res_0 := v.Get() + var _res_0 C.int32_t = _seq.NullRefNum + if res_0 != nil { + _res_0 = C.int32_t(_seq.ToRefNum(res_0)) + } + return _res_0 +} + +//export proxyjava_Future_Get2 +func proxyjava_Future_Get2(refnum C.int32_t, param_p0 C.int64_t, param_p1 C.int32_t) C.int32_t { + ref := _seq.FromRefNum(int32(refnum)) + v := ref.Get().(*java.Future) + _param_p0 := int64(param_p0) + var _param_p1 concurrent.TimeUnit + _param_p1_ref := _seq.FromRefNum(int32(param_p1)) + if _param_p1_ref != nil { + if param_p1 < 0 { // go object + _param_p1 = _param_p1_ref.Get().(concurrent.TimeUnit) + } else { // foreign object + _param_p1 = (*proxy_class_java_util_concurrent_TimeUnit)(_param_p1_ref) + } + } + res_0 := v.Get2(_param_p0, _param_p1) + var _res_0 C.int32_t = _seq.NullRefNum + if res_0 != nil { + _res_0 = C.int32_t(_seq.ToRefNum(res_0)) + } + return _res_0 +} + +//export new_java_Future +func new_java_Future() C.int32_t { + return C.int32_t(_seq.ToRefNum(new(java.Future))) +} + +//export proxyjava_InputStream_InputStream_Set +func proxyjava_InputStream_InputStream_Set(refnum C.int32_t, v C.int32_t) { + ref := _seq.FromRefNum(int32(refnum)) + var _v io.InputStream + _v_ref := _seq.FromRefNum(int32(v)) + if _v_ref != nil { + if v < 0 { // go object + _v = _v_ref.Get().(io.InputStream) + } else { // foreign object + _v = (*proxy_class_java_io_InputStream)(_v_ref) + } + } + ref.Get().(*java.InputStream).InputStream = _v +} + +//export proxyjava_InputStream_InputStream_Get +func proxyjava_InputStream_InputStream_Get(refnum C.int32_t) C.int32_t { + ref := _seq.FromRefNum(int32(refnum)) + v := ref.Get().(*java.InputStream).InputStream + var _v C.int32_t = _seq.NullRefNum + if v != nil { + _v = C.int32_t(_seq.ToRefNum(v)) + } + return _v +} + +//export proxyjava_InputStream_Read +func proxyjava_InputStream_Read(refnum C.int32_t) (C.int32_t, C.int32_t) { + ref := _seq.FromRefNum(int32(refnum)) + v := ref.Get().(*java.InputStream) + res_0, res_1 := v.Read() + _res_0 := C.int32_t(res_0) + var _res_1 C.int32_t = _seq.NullRefNum + if res_1 != nil { + _res_1 = C.int32_t(_seq.ToRefNum(res_1)) + } + return _res_0, _res_1 +} + +//export new_java_InputStream +func new_java_InputStream() C.int32_t { + return C.int32_t(_seq.ToRefNum(new(java.InputStream))) +} + +//export proxyjava_Object_Object_Set +func proxyjava_Object_Object_Set(refnum C.int32_t, v C.int32_t) { + ref := _seq.FromRefNum(int32(refnum)) + var _v lang.Object + _v_ref := _seq.FromRefNum(int32(v)) + if _v_ref != nil { + if v < 0 { // go object + _v = _v_ref.Get().(lang.Object) + } else { // foreign object + _v = (*proxy_class_java_lang_Object)(_v_ref) + } + } + ref.Get().(*java.Object).Object = _v +} + +//export proxyjava_Object_Object_Get +func proxyjava_Object_Object_Get(refnum C.int32_t) C.int32_t { + ref := _seq.FromRefNum(int32(refnum)) + v := ref.Get().(*java.Object).Object + var _v C.int32_t = _seq.NullRefNum + if v != nil { + _v = C.int32_t(_seq.ToRefNum(v)) + } + return _v +} + +//export new_java_Object +func new_java_Object() C.int32_t { + return C.int32_t(_seq.ToRefNum(new(java.Object))) +} + +//export proxyjava_Runnable_Runnable_Set +func proxyjava_Runnable_Runnable_Set(refnum C.int32_t, v C.int32_t) { + ref := _seq.FromRefNum(int32(refnum)) + var _v lang.Runnable + _v_ref := _seq.FromRefNum(int32(v)) + if _v_ref != nil { + if v < 0 { // go object + _v = _v_ref.Get().(lang.Runnable) + } else { // foreign object + _v = (*proxy_class_java_lang_Runnable)(_v_ref) + } + } + ref.Get().(*java.Runnable).Runnable = _v +} + +//export proxyjava_Runnable_Runnable_Get +func proxyjava_Runnable_Runnable_Get(refnum C.int32_t) C.int32_t { + ref := _seq.FromRefNum(int32(refnum)) + v := ref.Get().(*java.Runnable).Runnable + var _v C.int32_t = _seq.NullRefNum + if v != nil { + _v = C.int32_t(_seq.ToRefNum(v)) + } + return _v +} + +//export proxyjava_Runnable_Run +func proxyjava_Runnable_Run(refnum C.int32_t, param_this C.int32_t) { + ref := _seq.FromRefNum(int32(refnum)) + v := ref.Get().(*java.Runnable) + var _param_this lang.Runnable + _param_this_ref := _seq.FromRefNum(int32(param_this)) + if _param_this_ref != nil { + if param_this < 0 { // go object + _param_this = _param_this_ref.Get().(lang.Runnable) + } else { // foreign object + _param_this = (*proxy_class_java_lang_Runnable)(_param_this_ref) + } + } + v.Run(_param_this) +} + +//export new_java_Runnable +func new_java_Runnable() C.int32_t { + return C.int32_t(_seq.ToRefNum(new(java.Runnable))) +} + +//export proxyjava__NewInputStream +func proxyjava__NewInputStream() C.int32_t { + res_0 := java.NewInputStream() + var _res_0 C.int32_t = _seq.NullRefNum + if res_0 != nil { + _res_0 = C.int32_t(_seq.ToRefNum(res_0)) + } + return _res_0 +} diff --git a/bind/testdata/classes.java.c.golden b/bind/testdata/classes.java.c.golden new file mode 100644 index 0000000..6e58879 --- /dev/null +++ b/bind/testdata/classes.java.c.golden @@ -0,0 +1,252 @@ +// File is generated by gobind. Do not edit. + +#include +#include "seq.h" +#include "classes.h" + +static jclass class_java_lang_Runnable; +static jmethodID m_java_lang_Runnable_run; +static jclass class_java_io_InputStream; +static jmethodID m_java_io_InputStream_read__; +static jclass class_java_util_concurrent_Future; +static jmethodID m_java_util_concurrent_Future_get__; +static jmethodID m_java_util_concurrent_Future_get__JLjava_util_concurrent_TimeUnit_2; +static jclass class_java_lang_Object; +static jclass class_java_util_concurrent_TimeUnit; + +void init_proxies() { + JNIEnv *env = go_seq_push_local_frame(5); + jclass clazz; + clazz = (*env)->FindClass(env, "java/lang/Runnable"); + class_java_lang_Runnable = (*env)->NewGlobalRef(env, clazz); + m_java_lang_Runnable_run = go_seq_get_method_id(clazz, "run", "()V"); + clazz = (*env)->FindClass(env, "java/io/InputStream"); + class_java_io_InputStream = (*env)->NewGlobalRef(env, clazz); + m_java_io_InputStream_read__ = go_seq_get_method_id(clazz, "read", "()I"); + clazz = (*env)->FindClass(env, "java/util/concurrent/Future"); + class_java_util_concurrent_Future = (*env)->NewGlobalRef(env, clazz); + m_java_util_concurrent_Future_get__ = go_seq_get_method_id(clazz, "get", "()Ljava/lang/Object;"); + m_java_util_concurrent_Future_get__JLjava_util_concurrent_TimeUnit_2 = go_seq_get_method_id(clazz, "get", "(JLjava/util/concurrent/TimeUnit;)Ljava/lang/Object;"); + clazz = (*env)->FindClass(env, "java/lang/Object"); + class_java_lang_Object = (*env)->NewGlobalRef(env, clazz); + clazz = (*env)->FindClass(env, "java/util/concurrent/TimeUnit"); + class_java_util_concurrent_TimeUnit = (*env)->NewGlobalRef(env, clazz); + go_seq_pop_local_frame(env); +} + +jint cproxy_java_lang_Runnable_run(jint this) { + JNIEnv *env = go_seq_push_local_frame(1); + // Must be a Java object + jobject _this = go_seq_from_refnum(env, this, NULL, NULL); + (*env)->CallVoidMethod(env, _this, m_java_lang_Runnable_run); + jobject _exc = go_seq_wrap_exception(env); + int32_t _exc_ref = go_seq_to_refnum(env, _exc); + go_seq_pop_local_frame(env); + return _exc_ref; +} + +ret_jint cproxy_java_io_InputStream_read__(jint this) { + JNIEnv *env = go_seq_push_local_frame(1); + // Must be a Java object + jobject _this = go_seq_from_refnum(env, this, NULL, NULL); + jint res = (*env)->CallIntMethod(env, _this, m_java_io_InputStream_read__); + jobject _exc = go_seq_wrap_exception(env); + int32_t _exc_ref = go_seq_to_refnum(env, _exc); + jint _res = res; + go_seq_pop_local_frame(env); + ret_jint __res = {_res, _exc_ref}; + return __res; +} + +ret_jint csuper_java_io_InputStream_read__(jint this) { + JNIEnv *env = go_seq_push_local_frame(1); + // Must be a Java object + jobject _this = go_seq_from_refnum(env, this, NULL, NULL); + jint res = (*env)->CallNonvirtualIntMethod(env, _this, class_java_io_InputStream, m_java_io_InputStream_read__); + jobject _exc = go_seq_wrap_exception(env); + int32_t _exc_ref = go_seq_to_refnum(env, _exc); + jint _res = res; + go_seq_pop_local_frame(env); + ret_jint __res = {_res, _exc_ref}; + return __res; +} + +ret_jint cproxy_java_util_concurrent_Future_get__(jint this) { + JNIEnv *env = go_seq_push_local_frame(1); + // Must be a Java object + jobject _this = go_seq_from_refnum(env, this, NULL, NULL); + jobject res = (*env)->CallObjectMethod(env, _this, m_java_util_concurrent_Future_get__); + jobject _exc = go_seq_wrap_exception(env); + int32_t _exc_ref = go_seq_to_refnum(env, _exc); + jint _res = go_seq_to_refnum(env, res); + go_seq_pop_local_frame(env); + ret_jint __res = {_res, _exc_ref}; + return __res; +} + +ret_jint cproxy_java_util_concurrent_Future_get__JLjava_util_concurrent_TimeUnit_2(jint this, jlong a0, jint a1) { + JNIEnv *env = go_seq_push_local_frame(3); + // Must be a Java object + jobject _this = go_seq_from_refnum(env, this, NULL, NULL); + jlong _a0 = a0; + jobject _a1 = go_seq_from_refnum(env, a1, NULL, NULL); + jobject res = (*env)->CallObjectMethod(env, _this, m_java_util_concurrent_Future_get__JLjava_util_concurrent_TimeUnit_2, _a0, _a1); + jobject _exc = go_seq_wrap_exception(env); + int32_t _exc_ref = go_seq_to_refnum(env, _exc); + jint _res = go_seq_to_refnum(env, res); + go_seq_pop_local_frame(env); + ret_jint __res = {_res, _exc_ref}; + return __res; +} + +// JNI functions for the Go <=> Java bridge. +// gobind -lang=java classes +// +// File is generated by gobind. Do not edit. + +#include +#include +#include "seq.h" +#include "_cgo_export.h" +#include "java.h" + +jclass proxy_class_java_Future; +jmethodID proxy_class_java_Future_cons; +jclass proxy_class_java_InputStream; +jmethodID proxy_class_java_InputStream_cons; +jclass proxy_class_java_Object; +jmethodID proxy_class_java_Object_cons; +jclass proxy_class_java_Runnable; +jmethodID proxy_class_java_Runnable_cons; + +JNIEXPORT void JNICALL +Java_go_java_Java__1init(JNIEnv *env, jclass _unused) { + jclass clazz; + clazz = (*env)->FindClass(env, "go/java/Future"); + proxy_class_java_Future = (*env)->NewGlobalRef(env, clazz); + proxy_class_java_Future_cons = (*env)->GetMethodID(env, clazz, "", "(Lgo/Seq$Ref;)V"); + clazz = (*env)->FindClass(env, "go/java/Runnable"); + proxy_class_java_Runnable = (*env)->NewGlobalRef(env, clazz); + proxy_class_java_Runnable_cons = (*env)->GetMethodID(env, clazz, "", "(Lgo/Seq$Ref;)V"); +} + +JNIEXPORT jobject JNICALL +Java_go_java_Java_newInputStream(JNIEnv* env, jclass _clazz) { + int32_t r0 = proxyjava__NewInputStream(); + jobject _r0 = go_seq_from_refnum(env, r0, proxy_class_java_InputStream, proxy_class_java_InputStream_cons); + return _r0; +} + +JNIEXPORT jobject JNICALL +Java_go_java_Future__1_1New(JNIEnv *env, jclass clazz) { + int32_t refnum = new_java_Future(); + return go_seq_from_refnum(env, refnum, NULL, NULL); +} + +JNIEXPORT jobject JNICALL +Java_go_java_Future_get__(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum_go(env, __this__); + int32_t r0 = proxyjava_Future_Get(o); + jobject _r0 = go_seq_from_refnum(env, r0, NULL, NULL); + return _r0; +} + +JNIEXPORT jobject JNICALL +Java_go_java_Future_get__JLjava_util_concurrent_TimeUnit_2(JNIEnv* env, jobject __this__, jlong p0, jobject p1) { + int32_t o = go_seq_to_refnum_go(env, __this__); + int64_t _p0 = (int64_t)p0; + int32_t _p1 = go_seq_to_refnum(env, p1); + int32_t r0 = proxyjava_Future_Get2(o, _p0, _p1); + jobject _r0 = go_seq_from_refnum(env, r0, NULL, NULL); + return _r0; +} + +JNIEXPORT void JNICALL +Java_go_java_Future_setFuture(JNIEnv *env, jobject this, jobject v) { + int32_t o = go_seq_to_refnum(env, this); + int32_t _v = go_seq_to_refnum(env, v); + proxyjava_Future_Future_Set(o, _v); +} + +JNIEXPORT jobject JNICALL +Java_go_java_Future_getFuture(JNIEnv *env, jobject this) { + int32_t o = go_seq_to_refnum(env, this); + int32_t r0 = proxyjava_Future_Future_Get(o); + jobject _r0 = go_seq_from_refnum(env, r0, NULL, NULL); + return _r0; +} + +JNIEXPORT jobject JNICALL +Java_go_java_InputStream__1_1NewInputStream(JNIEnv *env, jclass clazz) { + int32_t refnum = proxyjava__NewInputStream(); + return go_seq_from_refnum(env, refnum, NULL, NULL); +} + +JNIEXPORT jint JNICALL +Java_go_java_InputStream_read__(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum_go(env, __this__); + struct proxyjava_InputStream_Read_return res = proxyjava_InputStream_Read(o); + jint _r0 = (jint)res.r0; + jobject _r1 = go_seq_from_refnum(env, res.r1, proxy_class__error, proxy_class__error_cons); + go_seq_maybe_throw_exception(env, _r1); + return _r0; +} + +JNIEXPORT void JNICALL +Java_go_java_InputStream_setInputStream(JNIEnv *env, jobject this, jobject v) { + int32_t o = go_seq_to_refnum(env, this); + int32_t _v = go_seq_to_refnum(env, v); + proxyjava_InputStream_InputStream_Set(o, _v); +} + +JNIEXPORT jobject JNICALL +Java_go_java_InputStream_getInputStream(JNIEnv *env, jobject this) { + int32_t o = go_seq_to_refnum(env, this); + int32_t r0 = proxyjava_InputStream_InputStream_Get(o); + jobject _r0 = go_seq_from_refnum(env, r0, NULL, NULL); + return _r0; +} + +JNIEXPORT void JNICALL +Java_go_java_Object_setObject(JNIEnv *env, jobject this, jobject v) { + int32_t o = go_seq_to_refnum(env, this); + int32_t _v = go_seq_to_refnum(env, v); + proxyjava_Object_Object_Set(o, _v); +} + +JNIEXPORT jobject JNICALL +Java_go_java_Object_getObject(JNIEnv *env, jobject this) { + int32_t o = go_seq_to_refnum(env, this); + int32_t r0 = proxyjava_Object_Object_Get(o); + jobject _r0 = go_seq_from_refnum(env, r0, NULL, NULL); + return _r0; +} + +JNIEXPORT jobject JNICALL +Java_go_java_Runnable__1_1New(JNIEnv *env, jclass clazz) { + int32_t refnum = new_java_Runnable(); + return go_seq_from_refnum(env, refnum, NULL, NULL); +} + +JNIEXPORT void JNICALL +Java_go_java_Runnable_run(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum_go(env, __this__); + int32_t _this = go_seq_to_refnum(env, __this__); + proxyjava_Runnable_Run(o, _this); +} + +JNIEXPORT void JNICALL +Java_go_java_Runnable_setRunnable(JNIEnv *env, jobject this, jobject v) { + int32_t o = go_seq_to_refnum(env, this); + int32_t _v = go_seq_to_refnum(env, v); + proxyjava_Runnable_Runnable_Set(o, _v); +} + +JNIEXPORT jobject JNICALL +Java_go_java_Runnable_getRunnable(JNIEnv *env, jobject this) { + int32_t o = go_seq_to_refnum(env, this); + int32_t r0 = proxyjava_Runnable_Runnable_Get(o); + jobject _r0 = go_seq_from_refnum(env, r0, NULL, NULL); + return _r0; +} + diff --git a/bind/testdata/classes.java.golden b/bind/testdata/classes.java.golden new file mode 100644 index 0000000..6ef0594 --- /dev/null +++ b/bind/testdata/classes.java.golden @@ -0,0 +1,144 @@ +// Java class go.java.Future is a proxy for talking to a Go program. +// gobind -lang=java classes +// +// File is generated by gobind. Do not edit. +package go.java; + +import go.Seq; + +public final class Future implements Seq.GoObject, java.util.concurrent.Future { + { Seq.touch(); } + + private final Seq.Ref ref; + + Future(Seq.Ref ref) { this.ref = ref; } + + public Future() { this.ref = __New(); } + + private static native Seq.Ref __New(); + + @Override public final int incRefnum() { + int refnum = ref.refnum; + Seq.incGoRef(refnum); + return refnum; + } + + public final native java.util.concurrent.Future getFuture(); + public final native void setFuture(java.util.concurrent.Future v); + + @Override public native java.lang.Object get(); + @Override public native java.lang.Object get(long p0, java.util.concurrent.TimeUnit p1); +} + +// Java class go.java.InputStream is a proxy for talking to a Go program. +// gobind -lang=java classes +// +// File is generated by gobind. Do not edit. +package go.java; + +import go.Seq; + +public final class InputStream extends java.io.InputStream implements Seq.GoObject { + { Seq.touch(); } + + private final Seq.Ref ref; + + public InputStream() { + super(); + this.ref = __NewInputStream(); + } + + private static native Seq.Ref __NewInputStream(); + + @Override public final int incRefnum() { + int refnum = ref.refnum; + Seq.incGoRef(refnum); + return refnum; + } + + public final native java.io.InputStream getInputStream(); + public final native void setInputStream(java.io.InputStream v); + + @Override public native int read() throws java.io.IOException; +} + +// Java class go.java.Object is a proxy for talking to a Go program. +// gobind -lang=java classes +// +// File is generated by gobind. Do not edit. +package go.java; + +import go.Seq; + +public final class Object extends java.lang.Object implements Seq.GoObject { + { Seq.touch(); } + + private final Seq.Ref ref; + + @Override public final int incRefnum() { + int refnum = ref.refnum; + Seq.incGoRef(refnum); + return refnum; + } + + public final native java.lang.Object getObject(); + public final native void setObject(java.lang.Object v); + +} + +// Java class go.java.Runnable is a proxy for talking to a Go program. +// gobind -lang=java classes +// +// File is generated by gobind. Do not edit. +package go.java; + +import go.Seq; + +public final class Runnable implements Seq.GoObject, java.lang.Runnable { + { Seq.touch(); } + + private final Seq.Ref ref; + + Runnable(Seq.Ref ref) { this.ref = ref; } + + public Runnable() { this.ref = __New(); } + + private static native Seq.Ref __New(); + + @Override public final int incRefnum() { + int refnum = ref.refnum; + Seq.incGoRef(refnum); + return refnum; + } + + public final native java.lang.Runnable getRunnable(); + public final native void setRunnable(java.lang.Runnable v); + + @Override public native void run(); +} + +// Java class go.java.Java is a proxy for talking to a Go program. +// gobind -lang=java classes +// +// File is generated by gobind. Do not edit. +package go.java; + +import go.Seq; + +public abstract class Java { + static { + Seq.touch(); // for loading the native library + _init(); + } + + private Java() {} // uninstantiable + + // touch is called from other bound packages to initialize this package + public static void touch() {} + + private static native void _init(); + + + + public static native InputStream newInputStream(); +} diff --git a/bind/testdata/classes.java.h.golden b/bind/testdata/classes.java.h.golden new file mode 100644 index 0000000..bfb1403 --- /dev/null +++ b/bind/testdata/classes.java.h.golden @@ -0,0 +1,72 @@ +// File is generated by gobind. Do not edit. + +#include +#include "seq.h" + +extern void init_proxies(); + +typedef struct ret_jint { + jint res; + jint exc; +} ret_jint; +typedef struct ret_jboolean { + jboolean res; + jint exc; +} ret_jboolean; +typedef struct ret_jshort { + jshort res; + jint exc; +} ret_jshort; +typedef struct ret_jchar { + jchar res; + jint exc; +} ret_jchar; +typedef struct ret_jbyte { + jbyte res; + jint exc; +} ret_jbyte; +typedef struct ret_jlong { + jlong res; + jint exc; +} ret_jlong; +typedef struct ret_jfloat { + jfloat res; + jint exc; +} ret_jfloat; +typedef struct ret_jdouble { + jdouble res; + jint exc; +} ret_jdouble; +typedef struct ret_nstring { + nstring res; + jint exc; +} ret_nstring; +typedef struct ret_nbyteslice { + nbyteslice res; + jint exc; +} ret_nbyteslice; + +extern jint cproxy_java_lang_Runnable_run(jint this); +extern ret_jint cproxy_java_io_InputStream_read__(jint this); +extern ret_jint csuper_java_io_InputStream_read__(jint this); +extern ret_jint cproxy_java_util_concurrent_Future_get__(jint this); +extern ret_jint cproxy_java_util_concurrent_Future_get__JLjava_util_concurrent_TimeUnit_2(jint this, jlong a0, jint a1); +// JNI function headers for the Go <=> Java bridge. +// gobind -lang=java classes +// +// File is generated by gobind. Do not edit. + +#ifndef __Java_H__ +#define __Java_H__ + +#include + +extern jclass proxy_class_java_Future; +extern jmethodID proxy_class_java_Future_cons; +extern jclass proxy_class_java_InputStream; +extern jmethodID proxy_class_java_InputStream_cons; +extern jclass proxy_class_java_Object; +extern jmethodID proxy_class_java_Object_cons; +extern jclass proxy_class_java_Runnable; +extern jmethodID proxy_class_java_Runnable_cons; +#endif diff --git a/bind/testdata/customprefix.java.c.golden b/bind/testdata/customprefix.java.c.golden index f7036c3..5eb3b24 100644 --- a/bind/testdata/customprefix.java.c.golden +++ b/bind/testdata/customprefix.java.c.golden @@ -16,7 +16,7 @@ Java_com_example_customprefix_Customprefix__1init(JNIEnv *env, jclass _unused) { } JNIEXPORT void JNICALL -Java_com_example_customprefix_Customprefix_f(JNIEnv* env, jclass clazz) { +Java_com_example_customprefix_Customprefix_f(JNIEnv* env, jclass _clazz) { proxycustomprefix__F(); } diff --git a/bind/testdata/ignore.go.golden b/bind/testdata/ignore.go.golden index 6701015..4299931 100644 --- a/bind/testdata/ignore.go.golden +++ b/bind/testdata/ignore.go.golden @@ -15,6 +15,7 @@ import "C" import ( _seq "golang.org/x/mobile/bind/seq" + "ignore" ) // suppress the error if seq ends up unused @@ -26,6 +27,11 @@ var _ = _seq.FromRefNum // skipped method S.Result with unsupported parameter or return types +//export new_ignore_S +func new_ignore_S() C.int32_t { + return C.int32_t(_seq.ToRefNum(new(ignore.S))) +} + // skipped method I.Argument with unsupported parameter or return types // skipped method I.Result with unsupported parameter or return types diff --git a/bind/testdata/ignore.java.c.golden b/bind/testdata/ignore.java.c.golden index 7126ad2..1de8dc7 100644 --- a/bind/testdata/ignore.java.c.golden +++ b/bind/testdata/ignore.java.c.golden @@ -39,17 +39,17 @@ Java_go_ignore_Ignore__1init(JNIEnv *env, jclass _unused) { // skipped function Result with unsupported parameter or return types -// skipped function Argument with unsupported parameter or return types +// skipped function S.Argument with unsupported parameter or return types -// skipped function Result with unsupported parameter or return types +// skipped function S.Result with unsupported parameter or return types // skipped field S with unsupported type: *types.Interface -// skipped function Argument with unsupported parameter or return types +// skipped function I.Argument with unsupported parameter or return types // skipped method I with unsupported parameter or return types -// skipped function Result with unsupported parameter or return types +// skipped function I.Result with unsupported parameter or return types // skipped method I with unsupported parameter or return types diff --git a/bind/testdata/ignore.java.golden b/bind/testdata/ignore.java.golden index edc5c48..ae48e95 100644 --- a/bind/testdata/ignore.java.golden +++ b/bind/testdata/ignore.java.golden @@ -7,7 +7,9 @@ package go.ignore; import go.Seq; public final class S extends Seq.Proxy implements I { - private S(go.Seq.Ref ref) { super(ref); } + { Seq.touch(); } + + S(Seq.Ref ref) { super(ref); } // skipped field S.F with unsupported type: *types.Interface @@ -74,7 +76,7 @@ public abstract class Ignore { private static native void _init(); private static final class proxyI extends Seq.Proxy implements I { - proxyI(Seq.Ref ref) { super(ref); } + proxyI(Seq.Ref ref) { super(ref); } // skipped method I.Argument with unsupported parameter or return types diff --git a/bind/testdata/interfaces.java.c.golden b/bind/testdata/interfaces.java.c.golden index bef54fe..71b12b5 100644 --- a/bind/testdata/interfaces.java.c.golden +++ b/bind/testdata/interfaces.java.c.golden @@ -90,7 +90,7 @@ Java_go_interfaces_Interfaces__1init(JNIEnv *env, jclass _unused) { } JNIEXPORT jint JNICALL -Java_go_interfaces_Interfaces_add3(JNIEnv* env, jclass clazz, jobject r) { +Java_go_interfaces_Interfaces_add3(JNIEnv* env, jclass _clazz, jobject r) { int32_t _r = go_seq_to_refnum(env, r); int32_t r0 = proxyinterfaces__Add3(_r); jint _r0 = (jint)r0; @@ -98,7 +98,7 @@ Java_go_interfaces_Interfaces_add3(JNIEnv* env, jclass clazz, jobject r) { } JNIEXPORT void JNICALL -Java_go_interfaces_Interfaces_callErr(JNIEnv* env, jclass clazz, jobject e) { +Java_go_interfaces_Interfaces_callErr(JNIEnv* env, jclass _clazz, jobject e) { int32_t _e = go_seq_to_refnum(env, e); int32_t r0 = proxyinterfaces__CallErr(_e); jobject _r0 = go_seq_from_refnum(env, r0, proxy_class__error, proxy_class__error_cons); @@ -106,22 +106,22 @@ Java_go_interfaces_Interfaces_callErr(JNIEnv* env, jclass clazz, jobject e) { } JNIEXPORT jobject JNICALL -Java_go_interfaces_Interfaces_seven(JNIEnv* env, jclass clazz) { +Java_go_interfaces_Interfaces_seven(JNIEnv* env, jclass _clazz) { int32_t r0 = proxyinterfaces__Seven(); jobject _r0 = go_seq_from_refnum(env, r0, proxy_class_interfaces_I, proxy_class_interfaces_I_cons); return _r0; } JNIEXPORT void JNICALL -Java_go_interfaces_Interfaces_00024proxyError_err(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_interfaces_Interfaces_00024proxyError_err(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); int32_t r0 = proxyinterfaces_Error_Err(o); jobject _r0 = go_seq_from_refnum(env, r0, proxy_class__error, proxy_class__error_cons); go_seq_maybe_throw_exception(env, _r0); } int32_t cproxyinterfaces_Error_Err(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_interfaces_Error, proxy_class_interfaces_Error_cons); (*env)->CallVoidMethod(env, o, mid_Error_Err); jobject exc = go_seq_wrap_exception(env); @@ -131,15 +131,15 @@ int32_t cproxyinterfaces_Error_Err(int32_t refnum) { } JNIEXPORT jint JNICALL -Java_go_interfaces_Interfaces_00024proxyI_rand(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_interfaces_Interfaces_00024proxyI_rand(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); int32_t r0 = proxyinterfaces_I_Rand(o); jint _r0 = (jint)r0; return _r0; } int32_t cproxyinterfaces_I_Rand(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_interfaces_I, proxy_class_interfaces_I_cons); jint res = (*env)->CallIntMethod(env, o, mid_I_Rand); int32_t _res = (int32_t)res; @@ -148,41 +148,41 @@ int32_t cproxyinterfaces_I_Rand(int32_t refnum) { } JNIEXPORT void JNICALL -Java_go_interfaces_Interfaces_00024proxyI1_j(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_interfaces_Interfaces_00024proxyI1_j(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxyinterfaces_I1_J(o); } void cproxyinterfaces_I1_J(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_interfaces_I1, proxy_class_interfaces_I1_cons); (*env)->CallVoidMethod(env, o, mid_I1_J); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_interfaces_Interfaces_00024proxyI2_g(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_interfaces_Interfaces_00024proxyI2_g(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxyinterfaces_I2_G(o); } void cproxyinterfaces_I2_G(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_interfaces_I2, proxy_class_interfaces_I2_cons); (*env)->CallVoidMethod(env, o, mid_I2_G); go_seq_pop_local_frame(env); } JNIEXPORT jobject JNICALL -Java_go_interfaces_Interfaces_00024proxyI3_f(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_interfaces_Interfaces_00024proxyI3_f(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); int32_t r0 = proxyinterfaces_I3_F(o); jobject _r0 = go_seq_from_refnum(env, r0, proxy_class_interfaces_I1, proxy_class_interfaces_I1_cons); return _r0; } int32_t cproxyinterfaces_I3_F(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_interfaces_I3, proxy_class_interfaces_I3_cons); jobject res = (*env)->CallObjectMethod(env, o, mid_I3_F); int32_t _res = go_seq_to_refnum(env, res); @@ -191,28 +191,28 @@ int32_t cproxyinterfaces_I3_F(int32_t refnum) { } JNIEXPORT void JNICALL -Java_go_interfaces_Interfaces_00024proxyLargerI_anotherFunc(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_interfaces_Interfaces_00024proxyLargerI_anotherFunc(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxyinterfaces_LargerI_AnotherFunc(o); } void cproxyinterfaces_LargerI_AnotherFunc(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_interfaces_LargerI, proxy_class_interfaces_LargerI_cons); (*env)->CallVoidMethod(env, o, mid_LargerI_AnotherFunc); go_seq_pop_local_frame(env); } JNIEXPORT jint JNICALL -Java_go_interfaces_Interfaces_00024proxyLargerI_rand(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_interfaces_Interfaces_00024proxyLargerI_rand(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); int32_t r0 = proxyinterfaces_LargerI_Rand(o); jint _r0 = (jint)r0; return _r0; } int32_t cproxyinterfaces_LargerI_Rand(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_interfaces_LargerI, proxy_class_interfaces_LargerI_cons); jint res = (*env)->CallIntMethod(env, o, mid_LargerI_Rand); int32_t _res = (int32_t)res; @@ -221,15 +221,15 @@ int32_t cproxyinterfaces_LargerI_Rand(int32_t refnum) { } JNIEXPORT jint JNICALL -Java_go_interfaces_Interfaces_00024proxySameI_rand(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_interfaces_Interfaces_00024proxySameI_rand(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); int32_t r0 = proxyinterfaces_SameI_Rand(o); jint _r0 = (jint)r0; return _r0; } int32_t cproxyinterfaces_SameI_Rand(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_interfaces_SameI, proxy_class_interfaces_SameI_cons); jint res = (*env)->CallIntMethod(env, o, mid_SameI_Rand); int32_t _res = (int32_t)res; @@ -238,14 +238,14 @@ int32_t cproxyinterfaces_SameI_Rand(int32_t refnum) { } JNIEXPORT void JNICALL -Java_go_interfaces_Interfaces_00024proxyWithParam_hasParam(JNIEnv* env, jobject this, jboolean p0) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_interfaces_Interfaces_00024proxyWithParam_hasParam(JNIEnv* env, jobject __this__, jboolean p0) { + int32_t o = go_seq_to_refnum(env, __this__); char _p0 = (char)p0; proxyinterfaces_WithParam_HasParam(o, _p0); } void cproxyinterfaces_WithParam_HasParam(int32_t refnum, char p0) { - JNIEnv *env = go_seq_push_local_frame(12); + JNIEnv *env = go_seq_push_local_frame(1); jobject o = go_seq_from_refnum(env, refnum, proxy_class_interfaces_WithParam, proxy_class_interfaces_WithParam_cons); jboolean _p0 = p0 ? JNI_TRUE : JNI_FALSE; (*env)->CallVoidMethod(env, o, mid_WithParam_HasParam, _p0); diff --git a/bind/testdata/interfaces.java.golden b/bind/testdata/interfaces.java.golden index 544f0e7..5c49ed0 100644 --- a/bind/testdata/interfaces.java.golden +++ b/bind/testdata/interfaces.java.golden @@ -125,43 +125,43 @@ public abstract class Interfaces { private static native void _init(); private static final class proxyError extends Seq.Proxy implements Error { - proxyError(Seq.Ref ref) { super(ref); } + proxyError(Seq.Ref ref) { super(ref); } public native void err() throws Exception; } private static final class proxyI extends Seq.Proxy implements I { - proxyI(Seq.Ref ref) { super(ref); } + proxyI(Seq.Ref ref) { super(ref); } public native int rand(); } private static final class proxyI1 extends Seq.Proxy implements I1 { - proxyI1(Seq.Ref ref) { super(ref); } + proxyI1(Seq.Ref ref) { super(ref); } public native void j(); } private static final class proxyI2 extends Seq.Proxy implements I2 { - proxyI2(Seq.Ref ref) { super(ref); } + proxyI2(Seq.Ref ref) { super(ref); } public native void g(); } private static final class proxyI3 extends Seq.Proxy implements I3 { - proxyI3(Seq.Ref ref) { super(ref); } + proxyI3(Seq.Ref ref) { super(ref); } public native I1 f(); } private static final class proxyLargerI extends Seq.Proxy implements LargerI { - proxyLargerI(Seq.Ref ref) { super(ref); } + proxyLargerI(Seq.Ref ref) { super(ref); } public native void anotherFunc(); public native int rand(); } private static final class proxySameI extends Seq.Proxy implements SameI { - proxySameI(Seq.Ref ref) { super(ref); } + proxySameI(Seq.Ref ref) { super(ref); } public native int rand(); } private static final class proxyWithParam extends Seq.Proxy implements WithParam { - proxyWithParam(Seq.Ref ref) { super(ref); } + proxyWithParam(Seq.Ref ref) { super(ref); } public native void hasParam(boolean p0); } diff --git a/bind/testdata/issue10788.go.golden b/bind/testdata/issue10788.go.golden index 4c515f3..1d3652a 100644 --- a/bind/testdata/issue10788.go.golden +++ b/bind/testdata/issue10788.go.golden @@ -36,6 +36,11 @@ func proxyissue10788_TestStruct_Value_Get(refnum C.int32_t) C.nstring { return _v } +//export new_issue10788_TestStruct +func new_issue10788_TestStruct() C.int32_t { + return C.int32_t(_seq.ToRefNum(new(issue10788.TestStruct))) +} + //export proxyissue10788_TestInterface_DoSomeWork func proxyissue10788_TestInterface_DoSomeWork(refnum C.int32_t, param_s C.int32_t) { ref := _seq.FromRefNum(int32(refnum)) diff --git a/bind/testdata/issue10788.java.c.golden b/bind/testdata/issue10788.java.c.golden index d606049..a685c1f 100644 --- a/bind/testdata/issue10788.java.c.golden +++ b/bind/testdata/issue10788.java.c.golden @@ -47,14 +47,14 @@ Java_go_issue10788_TestStruct_getValue(JNIEnv *env, jobject this) { } JNIEXPORT void JNICALL -Java_go_issue10788_Issue10788_00024proxyTestInterface_doSomeWork(JNIEnv* env, jobject this, jobject s) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_issue10788_Issue10788_00024proxyTestInterface_doSomeWork(JNIEnv* env, jobject __this__, jobject s) { + int32_t o = go_seq_to_refnum(env, __this__); int32_t _s = go_seq_to_refnum(env, s); proxyissue10788_TestInterface_DoSomeWork(o, _s); } void cproxyissue10788_TestInterface_DoSomeWork(int32_t refnum, int32_t s) { - JNIEnv *env = go_seq_push_local_frame(12); + JNIEnv *env = go_seq_push_local_frame(1); jobject o = go_seq_from_refnum(env, refnum, proxy_class_issue10788_TestInterface, proxy_class_issue10788_TestInterface_cons); jobject _s = go_seq_from_refnum(env, s, proxy_class_issue10788_TestStruct, proxy_class_issue10788_TestStruct_cons); (*env)->CallVoidMethod(env, o, mid_TestInterface_DoSomeWork, _s); @@ -62,8 +62,8 @@ void cproxyissue10788_TestInterface_DoSomeWork(int32_t refnum, int32_t s) { } JNIEXPORT void JNICALL -Java_go_issue10788_Issue10788_00024proxyTestInterface_multipleUnnamedParams(JNIEnv* env, jobject this, jlong p0, jstring p1, jlong p2) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_issue10788_Issue10788_00024proxyTestInterface_multipleUnnamedParams(JNIEnv* env, jobject __this__, jlong p0, jstring p1, jlong p2) { + int32_t o = go_seq_to_refnum(env, __this__); nint _p0 = (nint)p0; nstring _p1 = go_seq_from_java_string(env, p1); int64_t _p2 = (int64_t)p2; @@ -71,7 +71,7 @@ Java_go_issue10788_Issue10788_00024proxyTestInterface_multipleUnnamedParams(JNIE } void cproxyissue10788_TestInterface_MultipleUnnamedParams(int32_t refnum, nint p0, nstring p1, int64_t p2) { - JNIEnv *env = go_seq_push_local_frame(16); + JNIEnv *env = go_seq_push_local_frame(3); jobject o = go_seq_from_refnum(env, refnum, proxy_class_issue10788_TestInterface, proxy_class_issue10788_TestInterface_cons); jlong _p0 = (jlong)p0; jstring _p1 = go_seq_to_java_string(env, p1); diff --git a/bind/testdata/issue10788.java.golden b/bind/testdata/issue10788.java.golden index bc0836b..52e6214 100644 --- a/bind/testdata/issue10788.java.golden +++ b/bind/testdata/issue10788.java.golden @@ -7,7 +7,9 @@ package go.issue10788; import go.Seq; public final class TestStruct extends Seq.Proxy { - private TestStruct(go.Seq.Ref ref) { super(ref); } + { Seq.touch(); } + + TestStruct(Seq.Ref ref) { super(ref); } public final native String getValue(); public final native void setValue(String v); @@ -77,7 +79,7 @@ public abstract class Issue10788 { private static native void _init(); private static final class proxyTestInterface extends Seq.Proxy implements TestInterface { - proxyTestInterface(Seq.Ref ref) { super(ref); } + proxyTestInterface(Seq.Ref ref) { super(ref); } public native void doSomeWork(TestStruct s); public native void multipleUnnamedParams(long p0, String p1, long p2); diff --git a/bind/testdata/issue12328.go.golden b/bind/testdata/issue12328.go.golden index 4dca6cc..c4804f9 100644 --- a/bind/testdata/issue12328.go.golden +++ b/bind/testdata/issue12328.go.golden @@ -46,3 +46,8 @@ func proxyissue12328_T_Err_Get(refnum C.int32_t) C.int32_t { } return _v } + +//export new_issue12328_T +func new_issue12328_T() C.int32_t { + return C.int32_t(_seq.ToRefNum(new(issue12328.T))) +} diff --git a/bind/testdata/issue12328.java.golden b/bind/testdata/issue12328.java.golden index fb92fc0..13f5c71 100644 --- a/bind/testdata/issue12328.java.golden +++ b/bind/testdata/issue12328.java.golden @@ -7,7 +7,9 @@ package go.issue12328; import go.Seq; public final class T extends Seq.Proxy { - private T(go.Seq.Ref ref) { super(ref); } + { Seq.touch(); } + + T(Seq.Ref ref) { super(ref); } public final native java.lang.Exception getErr(); public final native void setErr(java.lang.Exception v); diff --git a/bind/testdata/issue12403.java.c.golden b/bind/testdata/issue12403.java.c.golden index b3eafcf..cbb99ff 100644 --- a/bind/testdata/issue12403.java.c.golden +++ b/bind/testdata/issue12403.java.c.golden @@ -27,8 +27,8 @@ Java_go_issue12403_Issue12403__1init(JNIEnv *env, jclass _unused) { } JNIEXPORT jstring JNICALL -Java_go_issue12403_Issue12403_00024proxyParsable_fromJSON(JNIEnv* env, jobject this, jstring jstr) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_issue12403_Issue12403_00024proxyParsable_fromJSON(JNIEnv* env, jobject __this__, jstring jstr) { + int32_t o = go_seq_to_refnum(env, __this__); nstring _jstr = go_seq_from_java_string(env, jstr); nstring r0 = proxyissue12403_Parsable_FromJSON(o, _jstr); jstring _r0 = go_seq_to_java_string(env, r0); @@ -36,7 +36,7 @@ Java_go_issue12403_Issue12403_00024proxyParsable_fromJSON(JNIEnv* env, jobject t } nstring cproxyissue12403_Parsable_FromJSON(int32_t refnum, nstring jstr) { - JNIEnv *env = go_seq_push_local_frame(12); + JNIEnv *env = go_seq_push_local_frame(1); jobject o = go_seq_from_refnum(env, refnum, proxy_class_issue12403_Parsable, proxy_class_issue12403_Parsable_cons); jstring _jstr = go_seq_to_java_string(env, jstr); jstring res = (*env)->CallObjectMethod(env, o, mid_Parsable_FromJSON, _jstr); @@ -46,8 +46,8 @@ nstring cproxyissue12403_Parsable_FromJSON(int32_t refnum, nstring jstr) { } JNIEXPORT jstring JNICALL -Java_go_issue12403_Issue12403_00024proxyParsable_toJSON(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_issue12403_Issue12403_00024proxyParsable_toJSON(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); struct proxyissue12403_Parsable_ToJSON_return res = proxyissue12403_Parsable_ToJSON(o); jstring _r0 = go_seq_to_java_string(env, res.r0); jobject _r1 = go_seq_from_refnum(env, res.r1, proxy_class__error, proxy_class__error_cons); @@ -56,7 +56,7 @@ Java_go_issue12403_Issue12403_00024proxyParsable_toJSON(JNIEnv* env, jobject thi } struct cproxyissue12403_Parsable_ToJSON_return cproxyissue12403_Parsable_ToJSON(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_issue12403_Parsable, proxy_class_issue12403_Parsable_cons); jstring res = (*env)->CallObjectMethod(env, o, mid_Parsable_ToJSON); nstring _res = go_seq_from_java_string(env, res); diff --git a/bind/testdata/issue12403.java.golden b/bind/testdata/issue12403.java.golden index dde6ebe..30976be 100644 --- a/bind/testdata/issue12403.java.golden +++ b/bind/testdata/issue12403.java.golden @@ -34,7 +34,7 @@ public abstract class Issue12403 { private static native void _init(); private static final class proxyParsable extends Seq.Proxy implements Parsable { - proxyParsable(Seq.Ref ref) { super(ref); } + proxyParsable(Seq.Ref ref) { super(ref); } public native String fromJSON(String jstr); public native String toJSON() throws Exception; diff --git a/bind/testdata/java.java.c.golden b/bind/testdata/java.java.c.golden index 3cef5e8..814478f 100644 --- a/bind/testdata/java.java.c.golden +++ b/bind/testdata/java.java.c.golden @@ -79,11 +79,11 @@ Java_go_java_Java__1init(JNIEnv *env, jclass _unused) { } -// skipped function Super with unsupported parameter or return types +// skipped function O.Super with unsupported parameter or return types // skipped method O with unsupported parameter or return types -// skipped function Super with unsupported parameter or return types +// skipped function S.Super with unsupported parameter or return types // skipped method S with unsupported parameter or return types diff --git a/bind/testdata/java.java.golden b/bind/testdata/java.java.golden index f678fb8..3948a2b 100644 --- a/bind/testdata/java.java.golden +++ b/bind/testdata/java.java.golden @@ -72,21 +72,21 @@ public abstract class Java { private static native void _init(); private static final class proxyF extends Seq.Proxy implements F { - proxyF(Seq.Ref ref) { super(ref); } + proxyF(Seq.Ref ref) { super(ref); } } private static final class proxyO extends Seq.Proxy implements O { - proxyO(Seq.Ref ref) { super(ref); } + proxyO(Seq.Ref ref) { super(ref); } // skipped method O.Super with unsupported parameter or return types } private static final class proxyR extends Seq.Proxy implements R { - proxyR(Seq.Ref ref) { super(ref); } + proxyR(Seq.Ref ref) { super(ref); } } private static final class proxyS extends Seq.Proxy implements S { - proxyS(Seq.Ref ref) { super(ref); } + proxyS(Seq.Ref ref) { super(ref); } // skipped method S.Super with unsupported parameter or return types diff --git a/bind/testdata/keywords.java.c.golden b/bind/testdata/keywords.java.c.golden index 67e8b56..adc419e 100644 --- a/bind/testdata/keywords.java.c.golden +++ b/bind/testdata/keywords.java.c.golden @@ -129,689 +129,689 @@ Java_go_keywords_Keywords__1init(JNIEnv *env, jclass _unused) { } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_abstract_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_abstract_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Abstract(o); } void cproxykeywords_KeywordCaller_Abstract(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Abstract); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_assert_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_assert_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Assert(o); } void cproxykeywords_KeywordCaller_Assert(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Assert); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_boolean_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_boolean_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Boolean(o); } void cproxykeywords_KeywordCaller_Boolean(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Boolean); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_break_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_break_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Break(o); } void cproxykeywords_KeywordCaller_Break(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Break); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_byte_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_byte_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Byte(o); } void cproxykeywords_KeywordCaller_Byte(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Byte); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_case_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_case_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Case(o); } void cproxykeywords_KeywordCaller_Case(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Case); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_catch_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_catch_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Catch(o); } void cproxykeywords_KeywordCaller_Catch(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Catch); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_char_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_char_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Char(o); } void cproxykeywords_KeywordCaller_Char(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Char); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_class_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_class_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Class(o); } void cproxykeywords_KeywordCaller_Class(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Class); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_const_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_const_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Const(o); } void cproxykeywords_KeywordCaller_Const(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Const); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_continue_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_continue_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Continue(o); } void cproxykeywords_KeywordCaller_Continue(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Continue); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_default_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_default_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Default(o); } void cproxykeywords_KeywordCaller_Default(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Default); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_do_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_do_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Do(o); } void cproxykeywords_KeywordCaller_Do(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Do); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_double_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_double_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Double(o); } void cproxykeywords_KeywordCaller_Double(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Double); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_else_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_else_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Else(o); } void cproxykeywords_KeywordCaller_Else(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Else); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_enum_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_enum_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Enum(o); } void cproxykeywords_KeywordCaller_Enum(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Enum); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_extends_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_extends_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Extends(o); } void cproxykeywords_KeywordCaller_Extends(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Extends); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_false_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_false_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_False(o); } void cproxykeywords_KeywordCaller_False(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_False); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_final_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_final_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Final(o); } void cproxykeywords_KeywordCaller_Final(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Final); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_finally_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_finally_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Finally(o); } void cproxykeywords_KeywordCaller_Finally(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Finally); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_float_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_float_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Float(o); } void cproxykeywords_KeywordCaller_Float(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Float); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_for_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_for_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_For(o); } void cproxykeywords_KeywordCaller_For(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_For); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_goto_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_goto_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Goto(o); } void cproxykeywords_KeywordCaller_Goto(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Goto); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_if_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_if_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_If(o); } void cproxykeywords_KeywordCaller_If(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_If); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_implements_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_implements_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Implements(o); } void cproxykeywords_KeywordCaller_Implements(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Implements); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_import_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_import_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Import(o); } void cproxykeywords_KeywordCaller_Import(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Import); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_instanceof_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_instanceof_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Instanceof(o); } void cproxykeywords_KeywordCaller_Instanceof(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Instanceof); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_int_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_int_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Int(o); } void cproxykeywords_KeywordCaller_Int(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Int); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_interface_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_interface_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Interface(o); } void cproxykeywords_KeywordCaller_Interface(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Interface); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_long_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_long_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Long(o); } void cproxykeywords_KeywordCaller_Long(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Long); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_native_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_native_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Native(o); } void cproxykeywords_KeywordCaller_Native(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Native); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_new_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_new_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_New(o); } void cproxykeywords_KeywordCaller_New(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_New); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_null_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_null_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Null(o); } void cproxykeywords_KeywordCaller_Null(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Null); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_package_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_package_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Package(o); } void cproxykeywords_KeywordCaller_Package(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Package); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_private_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_private_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Private(o); } void cproxykeywords_KeywordCaller_Private(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Private); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_protected_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_protected_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Protected(o); } void cproxykeywords_KeywordCaller_Protected(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Protected); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_public_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_public_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Public(o); } void cproxykeywords_KeywordCaller_Public(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Public); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_return_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_return_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Return(o); } void cproxykeywords_KeywordCaller_Return(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Return); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_short_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_short_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Short(o); } void cproxykeywords_KeywordCaller_Short(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Short); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_static_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_static_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Static(o); } void cproxykeywords_KeywordCaller_Static(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Static); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_strictfp_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_strictfp_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Strictfp(o); } void cproxykeywords_KeywordCaller_Strictfp(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Strictfp); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_super_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_super_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Super(o); } void cproxykeywords_KeywordCaller_Super(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Super); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_switch_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_switch_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Switch(o); } void cproxykeywords_KeywordCaller_Switch(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Switch); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_synchronized_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_synchronized_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Synchronized(o); } void cproxykeywords_KeywordCaller_Synchronized(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Synchronized); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_this_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_this_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_This(o); } void cproxykeywords_KeywordCaller_This(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_This); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_throw_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_throw_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Throw(o); } void cproxykeywords_KeywordCaller_Throw(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Throw); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_throws_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_throws_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Throws(o); } void cproxykeywords_KeywordCaller_Throws(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Throws); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_transient_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_transient_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Transient(o); } void cproxykeywords_KeywordCaller_Transient(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Transient); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_true_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_true_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_True(o); } void cproxykeywords_KeywordCaller_True(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_True); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_try_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_try_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Try(o); } void cproxykeywords_KeywordCaller_Try(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Try); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_void_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_void_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Void(o); } void cproxykeywords_KeywordCaller_Void(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Void); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_volatile_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_volatile_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_Volatile(o); } void cproxykeywords_KeywordCaller_Volatile(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_Volatile); go_seq_pop_local_frame(env); } JNIEXPORT void JNICALL -Java_go_keywords_Keywords_00024proxyKeywordCaller_while_1(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_keywords_Keywords_00024proxyKeywordCaller_while_1(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxykeywords_KeywordCaller_While(o); } void cproxykeywords_KeywordCaller_While(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_keywords_KeywordCaller, proxy_class_keywords_KeywordCaller_cons); (*env)->CallVoidMethod(env, o, mid_KeywordCaller_While); go_seq_pop_local_frame(env); diff --git a/bind/testdata/keywords.java.golden b/bind/testdata/keywords.java.golden index a62e4d3..b7f5ea1 100644 --- a/bind/testdata/keywords.java.golden +++ b/bind/testdata/keywords.java.golden @@ -85,7 +85,7 @@ public abstract class Keywords { private static native void _init(); private static final class proxyKeywordCaller extends Seq.Proxy implements KeywordCaller { - proxyKeywordCaller(Seq.Ref ref) { super(ref); } + proxyKeywordCaller(Seq.Ref ref) { super(ref); } public native void abstract_(); public native void assert_(); diff --git a/bind/testdata/structs.go.golden b/bind/testdata/structs.go.golden index 5f6d741..f989e4e 100644 --- a/bind/testdata/structs.go.golden +++ b/bind/testdata/structs.go.golden @@ -76,6 +76,11 @@ func proxystructs_S_Sum(refnum C.int32_t) C.double { return _res_0 } +//export new_structs_S +func new_structs_S() C.int32_t { + return C.int32_t(_seq.ToRefNum(new(structs.S))) +} + //export proxystructs_S2_M func proxystructs_S2_M(refnum C.int32_t) { ref := _seq.FromRefNum(int32(refnum)) @@ -92,6 +97,11 @@ func proxystructs_S2_String(refnum C.int32_t) C.nstring { return _res_0 } +//export new_structs_S2 +func new_structs_S2() C.int32_t { + return C.int32_t(_seq.ToRefNum(new(structs.S2))) +} + //export proxystructs_I_M func proxystructs_I_M(refnum C.int32_t) { ref := _seq.FromRefNum(int32(refnum)) diff --git a/bind/testdata/structs.java.c.golden b/bind/testdata/structs.java.c.golden index 4dc5768..7c55fc4 100644 --- a/bind/testdata/structs.java.c.golden +++ b/bind/testdata/structs.java.c.golden @@ -35,7 +35,7 @@ Java_go_structs_Structs__1init(JNIEnv *env, jclass _unused) { } JNIEXPORT jobject JNICALL -Java_go_structs_Structs_identity(JNIEnv* env, jclass clazz, jobject s) { +Java_go_structs_Structs_identity(JNIEnv* env, jclass _clazz, jobject s) { int32_t _s = go_seq_to_refnum(env, s); int32_t r0 = proxystructs__Identity(_s); jobject _r0 = go_seq_from_refnum(env, r0, proxy_class_structs_S, proxy_class_structs_S_cons); @@ -43,7 +43,7 @@ Java_go_structs_Structs_identity(JNIEnv* env, jclass clazz, jobject s) { } JNIEXPORT jobject JNICALL -Java_go_structs_Structs_identityWithError(JNIEnv* env, jclass clazz, jobject s) { +Java_go_structs_Structs_identityWithError(JNIEnv* env, jclass _clazz, jobject s) { int32_t _s = go_seq_to_refnum(env, s); struct proxystructs__IdentityWithError_return res = proxystructs__IdentityWithError(_s); jobject _r0 = go_seq_from_refnum(env, res.r0, proxy_class_structs_S, proxy_class_structs_S_cons); @@ -53,8 +53,8 @@ Java_go_structs_Structs_identityWithError(JNIEnv* env, jclass clazz, jobject s) } JNIEXPORT jobject JNICALL -Java_go_structs_S_identity(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_structs_S_identity(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); struct proxystructs_S_Identity_return res = proxystructs_S_Identity(o); jobject _r0 = go_seq_from_refnum(env, res.r0, proxy_class_structs_S, proxy_class_structs_S_cons); jobject _r1 = go_seq_from_refnum(env, res.r1, proxy_class__error, proxy_class__error_cons); @@ -63,8 +63,8 @@ Java_go_structs_S_identity(JNIEnv* env, jobject this) { } JNIEXPORT jdouble JNICALL -Java_go_structs_S_sum(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_structs_S_sum(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); double r0 = proxystructs_S_Sum(o); jdouble _r0 = (jdouble)r0; return _r0; @@ -101,27 +101,27 @@ Java_go_structs_S_getY(JNIEnv *env, jobject this) { } JNIEXPORT void JNICALL -Java_go_structs_S2_m(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_structs_S2_m(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxystructs_S2_M(o); } JNIEXPORT jstring JNICALL -Java_go_structs_S2_string(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_structs_S2_string(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); nstring r0 = proxystructs_S2_String(o); jstring _r0 = go_seq_to_java_string(env, r0); return _r0; } JNIEXPORT void JNICALL -Java_go_structs_Structs_00024proxyI_m(JNIEnv* env, jobject this) { - int32_t o = go_seq_to_refnum(env, this); +Java_go_structs_Structs_00024proxyI_m(JNIEnv* env, jobject __this__) { + int32_t o = go_seq_to_refnum(env, __this__); proxystructs_I_M(o); } void cproxystructs_I_M(int32_t refnum) { - JNIEnv *env = go_seq_push_local_frame(10); + JNIEnv *env = go_seq_push_local_frame(0); jobject o = go_seq_from_refnum(env, refnum, proxy_class_structs_I, proxy_class_structs_I_cons); (*env)->CallVoidMethod(env, o, mid_I_M); go_seq_pop_local_frame(env); diff --git a/bind/testdata/structs.java.golden b/bind/testdata/structs.java.golden index a83eb72..73c9c41 100644 --- a/bind/testdata/structs.java.golden +++ b/bind/testdata/structs.java.golden @@ -7,7 +7,9 @@ package go.structs; import go.Seq; public final class S extends Seq.Proxy { - private S(go.Seq.Ref ref) { super(ref); } + { Seq.touch(); } + + S(Seq.Ref ref) { super(ref); } public final native double getX(); public final native void setX(double v); @@ -57,7 +59,9 @@ package go.structs; import go.Seq; public final class S2 extends Seq.Proxy implements I { - private S2(go.Seq.Ref ref) { super(ref); } + { Seq.touch(); } + + S2(Seq.Ref ref) { super(ref); } public native void m(); public native String string(); @@ -113,7 +117,7 @@ public abstract class Structs { private static native void _init(); private static final class proxyI extends Seq.Proxy implements I { - proxyI(Seq.Ref ref) { super(ref); } + proxyI(Seq.Ref ref) { super(ref); } public native void m(); } diff --git a/bind/testdata/try.java.c.golden b/bind/testdata/try.java.c.golden index ab00426..f31ec12 100644 --- a/bind/testdata/try.java.c.golden +++ b/bind/testdata/try.java.c.golden @@ -16,7 +16,7 @@ Java_go_try__Try__1init(JNIEnv *env, jclass _unused) { } JNIEXPORT jstring JNICALL -Java_go_try__Try_this_1(JNIEnv* env, jclass clazz) { +Java_go_try__Try_this_1(JNIEnv* env, jclass _clazz) { nstring r0 = proxytry__This(); jstring _r0 = go_seq_to_java_string(env, r0); return _r0; diff --git a/bind/testdata/vars.go.golden b/bind/testdata/vars.go.golden index 16e6a63..f3a1132 100644 --- a/bind/testdata/vars.go.golden +++ b/bind/testdata/vars.go.golden @@ -21,6 +21,11 @@ import ( // suppress the error if seq ends up unused var _ = _seq.FromRefNum +//export new_vars_S +func new_vars_S() C.int32_t { + return C.int32_t(_seq.ToRefNum(new(vars.S))) +} + type proxyvars_I _seq.Ref func (p *proxyvars_I) Bind_proxy_refnum__() int32 { return (*_seq.Ref)(p).Bind_IncNum() } diff --git a/bind/testdata/vars.java.golden b/bind/testdata/vars.java.golden index f8d1f27..ffe88a3 100644 --- a/bind/testdata/vars.java.golden +++ b/bind/testdata/vars.java.golden @@ -7,7 +7,9 @@ package go.vars; import go.Seq; public final class S extends Seq.Proxy implements I { - private S(go.Seq.Ref ref) { super(ref); } + { Seq.touch(); } + + S(Seq.Ref ref) { super(ref); } @Override public boolean equals(Object o) { if (o == null || !(o instanceof S)) { @@ -62,7 +64,7 @@ public abstract class Vars { private static native void _init(); private static final class proxyI extends Seq.Proxy implements I { - proxyI(Seq.Ref ref) { super(ref); } + proxyI(Seq.Ref ref) { super(ref); } } diff --git a/bind/testpkg/javapkg/classes.go b/bind/testpkg/javapkg/classes.go new file mode 100644 index 0000000..8386596 --- /dev/null +++ b/bind/testpkg/javapkg/classes.go @@ -0,0 +1,147 @@ +// Copyright 2016 The Go Authors. All rights reserved. +// Use of this source code is governed by a BSD-style +// license that can be found in the LICENSE file. + +package javapkg + +import ( + "Java/java/beans" + "Java/java/io" + "Java/java/io/IOException" + "Java/java/lang" + "Java/java/lang/Character" + "Java/java/lang/Integer" + "Java/java/lang/Object" + "Java/java/util" + "Java/java/util/concurrent" +) + +const ( + ToStringPrefix = "Go toString: " + IOExceptionMessage = "GoInputStream IOException" +) + +type GoRunnable struct { + lang.Runnable + this lang.Runnable +} + +func (r *GoRunnable) ToString(_ lang.Runnable) string { + return ToStringPrefix +} + +func (r *GoRunnable) Run(this lang.Runnable) { + r.this = this // Careful: This creates a reference cycle +} + +func (r *GoRunnable) GetThis() lang.Runnable { + return r.this +} + +type GoInputStream struct { + io.InputStream +} + +func (_ *GoInputStream) Read() (int32, error) { + return 0, IOException.New_Ljava_lang_String_2(IOExceptionMessage) +} + +func NewGoInputStream() *GoInputStream { + return new(GoInputStream) +} + +type GoFuture struct { + concurrent.Future +} + +func (_ *GoFuture) Cancel(_ bool) bool { + return false +} + +func (_ *GoFuture) Get() lang.Object { + return nil +} + +func (_ *GoFuture) Get2(_ int64, _ concurrent.TimeUnit) lang.Object { + return nil +} + +func (_ *GoFuture) IsCancelled() bool { + return false +} + +func (_ *GoFuture) IsDone() bool { + return false +} + +type GoObject struct { + lang.Object +} + +func (_ *GoObject) ToString(this lang.Object) string { + return ToStringPrefix + this.Super().ToString() +} + +func (_ *GoObject) HashCode() int32 { + return 42 +} + +func RunRunnable(r lang.Runnable) { + r.Run() +} + +func RunnableRoundtrip(r lang.Runnable) lang.Runnable { + return r +} + +// Test constructing and returning Go instances of GoObject and GoRunnable +// outside a constructor +func ConstructGoRunnable() *GoRunnable { + return new(GoRunnable) +} + +func ConstructGoObject() *GoObject { + return new(GoObject) +} + +// java.beans.PropertyChangeEvent is a class a with no default constructors. +type GoPCE struct { + beans.PropertyChangeEvent +} + +func NewGoPCE(_ lang.Object, _ string, _ lang.Object, _ lang.Object) *GoPCE { + return new(GoPCE) +} + +// java.util.ArrayList is a class with multiple constructors +type GoArrayList struct { + util.ArrayList +} + +func NewGoArrayList() *GoArrayList { + return new(GoArrayList) +} + +func NewGoArrayListWithCap(_ int32) *GoArrayList { + return new(GoArrayList) +} + +func CallSubset(s Character.Subset) { + s.ToString() +} + +type GoSubset struct { + Character.Subset +} + +func NewGoSubset(_ string) *GoSubset { + return new(GoSubset) +} + +func NewJavaObject() lang.Object { + return Object.New() +} + +func NewJavaInteger() lang.Integer { + return Integer.New_I(42) +} diff --git a/bind/types.go b/bind/types.go index 2f368dd..95167f7 100644 --- a/bind/types.go +++ b/bind/types.go @@ -8,6 +8,7 @@ import ( "fmt" "go/types" "log" + "strings" ) type ifaceSummary struct { @@ -75,6 +76,11 @@ func exportedMethodSet(T types.Type) []*types.Func { if !obj.Exported() { continue } + // Skip methods from the embedded java classes, so that + // only methods that are implemented in Go are included. + if isJavaPkg(obj.Pkg()) { + continue + } switch obj := obj.(type) { case *types.Func: methods = append(methods, obj) @@ -135,3 +141,15 @@ func isRefType(t types.Type) bool { return false } } + +func isJavaType(t types.Type) bool { + nt, ok := t.(*types.Named) + if !ok { + return false + } + return isJavaPkg(nt.Obj().Pkg()) +} + +func isJavaPkg(p *types.Package) bool { + return p != nil && strings.HasPrefix(p.Path(), "Java/") +} diff --git a/cmd/gobind/gen.go b/cmd/gobind/gen.go index f60b7de..b7aa5cf 100644 --- a/cmd/gobind/gen.go +++ b/cmd/gobind/gen.go @@ -36,7 +36,7 @@ func genPkg(p *types.Package, allPkg []*types.Package) { Pkg: conf.Pkg, }, } - g.Init() + g.Init(nil) buf.Reset() w, closer := writer(fname) diff --git a/cmd/gomobile/bind.go b/cmd/gomobile/bind.go index 8488ed5..4c09609 100644 --- a/cmd/gomobile/bind.go +++ b/cmd/gomobile/bind.go @@ -377,7 +377,7 @@ func (b *binder) GenJava(pkg *types.Package, allPkg []*types.Package, classes [] Pkg: pkg, }, } - g.Init() + g.Init(classes) generate := func(w io.Writer) error { if buildX {