1
0
mirror of https://github.com/golang/go synced 2024-11-24 21:10:04 -07:00

cgo: use correct frame size for 0 arguments

Passing a frame size of 1 was causing the cgo callback
to push 1 byte of arguments onto the stack, making
the stack pointer misaligned, which had the effect of
hiding all the pointers on the stack from the garbage
collector.

SWIG only wraps calls to C++ virtual methods, so it
always has at least 1 argument, so SWIG does not need
to be fixed too.

Fixes #1328.

R=iant
CC=golang-dev
https://golang.org/cl/4261046
This commit is contained in:
Russ Cox 2011-03-05 14:24:44 -05:00
parent d42bfe26ad
commit 1169559658

View File

@ -180,7 +180,6 @@ func (p *Package) structType(n *Name) (string, int64) {
} }
if off == 0 { if off == 0 {
fmt.Fprintf(&buf, "\t\tchar unused;\n") // avoid empty struct fmt.Fprintf(&buf, "\t\tchar unused;\n") // avoid empty struct
off++
} }
fmt.Fprintf(&buf, "\t}") fmt.Fprintf(&buf, "\t}")
return buf.String(), off return buf.String(), off
@ -225,6 +224,9 @@ func (p *Package) writeDefsFunc(fc, fgo2 *os.File, n *Name) {
fmt.Fprintf(fc, "void _cgo%s%s(void*);\n", cPrefix, n.Mangle) fmt.Fprintf(fc, "void _cgo%s%s(void*);\n", cPrefix, n.Mangle)
fmt.Fprintf(fc, "\n") fmt.Fprintf(fc, "\n")
fmt.Fprintf(fc, "void\n") fmt.Fprintf(fc, "void\n")
if argSize == 0 {
argSize++
}
fmt.Fprintf(fc, "·%s(struct{uint8 x[%d];}p)\n", n.Mangle, argSize) fmt.Fprintf(fc, "·%s(struct{uint8 x[%d];}p)\n", n.Mangle, argSize)
fmt.Fprintf(fc, "{\n") fmt.Fprintf(fc, "{\n")
fmt.Fprintf(fc, "\truntime·cgocall(_cgo%s%s, &p);\n", cPrefix, n.Mangle) fmt.Fprintf(fc, "\truntime·cgocall(_cgo%s%s, &p);\n", cPrefix, n.Mangle)
@ -392,7 +394,6 @@ func (p *Package) writeExports(fgo2, fc, fm *os.File) {
} }
if ctype == "struct {\n" { if ctype == "struct {\n" {
ctype += "\t\tchar unused;\n" // avoid empty struct ctype += "\t\tchar unused;\n" // avoid empty struct
off++
} }
ctype += "\t}" ctype += "\t}"
@ -444,7 +445,7 @@ func (p *Package) writeExports(fgo2, fc, fm *os.File) {
func(i int, atype ast.Expr) { func(i int, atype ast.Expr) {
fmt.Fprintf(fgcc, "\ta.p%d = p%d;\n", i, i) fmt.Fprintf(fgcc, "\ta.p%d = p%d;\n", i, i)
}) })
fmt.Fprintf(fgcc, "\tcrosscall2(_cgoexp%s_%s, &a, (int) sizeof a);\n", cPrefix, exp.ExpName) fmt.Fprintf(fgcc, "\tcrosscall2(_cgoexp%s_%s, &a, %d);\n", cPrefix, exp.ExpName, off)
if gccResult != "void" { if gccResult != "void" {
if len(fntype.Results.List) == 1 && len(fntype.Results.List[0].Names) <= 1 { if len(fntype.Results.List) == 1 && len(fntype.Results.List[0].Names) <= 1 {
fmt.Fprintf(fgcc, "\treturn a.r0;\n") fmt.Fprintf(fgcc, "\treturn a.r0;\n")