diff options
author | Ian Lance Taylor <iant@golang.org> | 2014-08-05 17:10:15 -0700 |
---|---|---|
committer | Ian Lance Taylor <iant@golang.org> | 2014-08-05 17:10:15 -0700 |
commit | 53f6f0a3f78b218b3aba77e39acb7c601c223957 (patch) | |
tree | d55478aa8b5554b7ced45fe73d8c654404526832 /src/cmd/cgo | |
parent | 0ad1c6efce3e555ba5337b849fcc6295494a3be6 (diff) | |
download | go-53f6f0a3f78b218b3aba77e39acb7c601c223957.tar.gz |
cmd/cgo: for -godefs, promote first field of anonymous union
Update issue 6677
When a struct contains an anonymous union, use the type and
name of the first field in the union.
This should make the glibc <sys/resource.h> file work; in that
file struct rusage has fields like
__extension__ union
{
long int ru_maxrss;
__syscall_slong_t __ru_maxrss_word;
};
in which the field that matters is ru_maxrss and
__ru_maxrss_word just exists to advance to the next field on
systems where the kernel uses long long fields but userspace
expects long fields.
LGTM=mikioh.mikioh
R=golang-codereviews, mikioh.mikioh
CC=golang-codereviews
https://codereview.appspot.com/106260044
Diffstat (limited to 'src/cmd/cgo')
-rw-r--r-- | src/cmd/cgo/gcc.go | 23 |
1 files changed, 21 insertions, 2 deletions
diff --git a/src/cmd/cgo/gcc.go b/src/cmd/cgo/gcc.go index 7a802102d..13e834029 100644 --- a/src/cmd/cgo/gcc.go +++ b/src/cmd/cgo/gcc.go @@ -1548,7 +1548,27 @@ func (c *typeConv) Struct(dt *dwarf.StructType, pos token.Pos) (expr *ast.Struct fld = c.pad(fld, f.ByteOffset-off) off = f.ByteOffset } - t := c.Type(f.Type, pos) + + name := f.Name + ft := f.Type + + // In godefs or cdefs mode, if this field is a C11 + // anonymous union then treat the first field in the + // union as the field in the struct. This handles + // cases like the glibc <sys/resource.h> file; see + // issue 6677. + if *godefs || *cdefs { + if st, ok := f.Type.(*dwarf.StructType); ok && name == "" && st.Kind == "union" && len(st.Field) > 0 && !used[st.Field[0].Name] { + name = st.Field[0].Name + ident[name] = name + ft = st.Field[0].Type + } + } + + // TODO: Handle fields that are anonymous structs by + // promoting the fields of the inner struct. + + t := c.Type(ft, pos) tgo := t.Go size := t.Size talign := t.Align @@ -1577,7 +1597,6 @@ func (c *typeConv) Struct(dt *dwarf.StructType, pos token.Pos) (expr *ast.Struct } n := len(fld) fld = fld[0 : n+1] - name := f.Name if name == "" { name = fmt.Sprintf("anon%d", anon) anon++ |