Skip to content

cmd/cgo: SIGSEGV using C++ files in package on Darwin #5629

Closed
@sbinet

Description

@sbinet
hi,

I tried the new C++ support of CGo from https://golang.org/cl/8248043/

unfortunately, there are a few shortcomings:
on linux (archlinux kernel-3.9.2, gcc-4.8.1), one has to explicitly add -lstdc++ to:
//#cgo LDFLAGS: -lstdc++

and, on darwin, the following compiles:
//#cgo LDFLAGS: -static-libstdc++

but segfaults at runtime:
SIGSEGV: segmentation violation
PC=0x7fff8147568a
signal arrived during cgo execution

ttt._Cfunc_MyPrint(0xc0bc0)
    ttt/_obj/_cgo_defun.c:44 +0x2f
ttt.T()
    ttt/_obj/ttt.cgo1.go:15 +0x45
main.main()
    /Users/binet/dev/hg-go/gopath/src/ttt/ttt-run/run.go:10 +0x18

$ gdb ttt-run
(gdb) run
Starting program: /Users/binet/dev/hg-go/gopath/bin/ttt-run 
Reading symbols for shared libraries ++. done
foo

Program received signal EXC_BAD_ACCESS, Could not access memory.
Reason: KERN_INVALID_ADDRESS at address: 0xffffffffffffffe8
0x00007fff8147568a in std::ostream::sentry::sentry ()
(gdb) bt
#0  0x00007fff8147568a in std::ostream::sentry::sentry ()
#1  0x00007fff81475b0d in std::__ostream_insert<char, std::char_traits<char>
> ()
Die: DW_TAG_unspecified_type (abbrev = 10, offset = 144)
    has children: FALSE
    attributes:
        DW_AT_name (DW_FORM_string) string: "<unspecified>"
Dwarf Error: Cannot find type of die [in module
/Users/binet/dev/hg-go/gopath/bin/ttt-run]

to reproduce:

mkdir -p $GOPATH/src/ttt
cd $GOPATH/src/ttt
cat >| ttt.go << EOF
package ttt

// #include "ttt.h"
// #cgo LDFLAGS: -static-libstdc++
import "C"

import "fmt"

func T() {
 fmt.Printf("foo\n")
 C.MyPrint()
}
EOF

cat >| ttt.h << EOF
#ifndef TTT_TTT_H
#define TTT_TTT_H 1

#ifdef __cplusplus
extern "C" {
#endif

void MyPrint(void);

#ifdef __cplusplus
}
#endif

#endif /* !TTT_TTT_H */
EOF

cat >| ttt.cxx << EOF
#include "ttt.h"
#include <iostream>

extern "C" {
void MyPrint() {
  std::cout << "hello from c++" << std::endl;
}
}
EOF

and finally, a simple go-executable:
cat >| run.go << EOF
package main

import "ttt"

func main() {
 ttt.T()
}
EOF

The expected outcome of running that executable should be:
$ go run run.go
foo
hello from c++

===
$ go version
go version devel +103cf9db59e1 Mon Jun 03 11:52:36 2013 +1000 darwin/amd64

parting notes:
I suppose the code in cmd/go/build.go should also detect libstdc++.a (on linux; on
darwin that's spelled libstdc++-static.a IIRC) in the same fashion than for libgcc.a.

the attached tar-ball contains the code snippets above (but sans the -static-libstdc++
bits)

hth,
-s

Attachments:

  1. ttt.tar.gz (563 bytes)

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions