github.com/zxy12/go_duplicate_112_new@v0.0.0-20200807091221-747231827200/src/cmd/gcc.go (about)

     1  // Copyright 2009 The Go Authors. All rights reserved.
     2  // Use of this source code is governed by a BSD-style
     3  // license that can be found in the LICENSE file.
     4  
     5  // Annotate Ref in Prog with C types by parsing gcc debug output.
     6  // Conversion of debug output to Go types.
     7  
     8  package main
     9  
    10  import (
    11  	"bytes"
    12  	"debug/dwarf"
    13  	"debug/elf"
    14  	"debug/macho"
    15  	"debug/pe"
    16  	"encoding/binary"
    17  	"errors"
    18  	"flag"
    19  	"fmt"
    20  	"go/ast"
    21  	"go/parser"
    22  	"go/token"
    23  	"internal/xcoff"
    24  	"math"
    25  	"os"
    26  	"strconv"
    27  	"strings"
    28  	"unicode"
    29  	"unicode/utf8"
    30  )
    31  
    32  var debugDefine = flag.Bool("debug-define", false, "print relevant #defines")
    33  var debugGcc = flag.Bool("debug-gcc", false, "print gcc invocations")
    34  
    35  var nameToC = map[string]string{
    36  	"schar":         "signed char",
    37  	"uchar":         "unsigned char",
    38  	"ushort":        "unsigned short",
    39  	"uint":          "unsigned int",
    40  	"ulong":         "unsigned long",
    41  	"longlong":      "long long",
    42  	"ulonglong":     "unsigned long long",
    43  	"complexfloat":  "float _Complex",
    44  	"complexdouble": "double _Complex",
    45  }
    46  
    47  // cname returns the C name to use for C.s.
    48  // The expansions are listed in nameToC and also
    49  // struct_foo becomes "struct foo", and similarly for
    50  // union and enum.
    51  func cname(s string) string {
    52  	if t, ok := nameToC[s]; ok {
    53  		return t
    54  	}
    55  
    56  	if strings.HasPrefix(s, "struct_") {
    57  		return "struct " + s[len("struct_"):]
    58  	}
    59  	if strings.HasPrefix(s, "union_") {
    60  		return "union " + s[len("union_"):]
    61  	}
    62  	if strings.HasPrefix(s, "enum_") {
    63  		return "enum " + s[len("enum_"):]
    64  	}
    65  	if strings.HasPrefix(s, "sizeof_") {
    66  		return "sizeof(" + cname(s[len("sizeof_"):]) + ")"
    67  	}
    68  	return s
    69  }
    70  
    71  // DiscardCgoDirectives processes the import C preamble, and discards
    72  // all #cgo CFLAGS and LDFLAGS directives, so they don't make their
    73  // way into _cgo_export.h.
    74  func (f *File) DiscardCgoDirectives() {
    75  	linesIn := strings.Split(f.Preamble, "\n")
    76  	linesOut := make([]string, 0, len(linesIn))
    77  	for _, line := range linesIn {
    78  		l := strings.TrimSpace(line)
    79  		if len(l) < 5 || l[:4] != "#cgo" || !unicode.IsSpace(rune(l[4])) {
    80  			linesOut = append(linesOut, line)
    81  		} else {
    82  			linesOut = append(linesOut, "")
    83  		}
    84  	}
    85  	f.Preamble = strings.Join(linesOut, "\n")
    86  }
    87  
    88  // addToFlag appends args to flag. All flags are later written out onto the
    89  // _cgo_flags file for the build system to use.
    90  func (p *Package) addToFlag(flag string, args []string) {
    91  	p.CgoFlags[flag] = append(p.CgoFlags[flag], args...)
    92  	if flag == "CFLAGS" {
    93  		// We'll also need these when preprocessing for dwarf information.
    94  		// However, discard any -g options: we need to be able
    95  		// to parse the debug info, so stick to what we expect.
    96  		for _, arg := range args {
    97  			if !strings.HasPrefix(arg, "-g") {
    98  				p.GccOptions = append(p.GccOptions, arg)
    99  			}
   100  		}
   101  	}
   102  }
   103  
   104  // splitQuoted splits the string s around each instance of one or more consecutive
   105  // white space characters while taking into account quotes and escaping, and
   106  // returns an array of substrings of s or an empty list if s contains only white space.
   107  // Single quotes and double quotes are recognized to prevent splitting within the
   108  // quoted region, and are removed from the resulting substrings. If a quote in s
   109  // isn't closed err will be set and r will have the unclosed argument as the
   110  // last element. The backslash is used for escaping.
   111  //
   112  // For example, the following string:
   113  //
   114  //     `a b:"c d" 'e''f'  "g\""`
   115  //
   116  // Would be parsed as:
   117  //
   118  //     []string{"a", "b:c d", "ef", `g"`}
   119  //
   120  func splitQuoted(s string) (r []string, err error) {
   121  	var args []string
   122  	arg := make([]rune, len(s))
   123  	escaped := false
   124  	quoted := false
   125  	quote := '\x00'
   126  	i := 0
   127  	for _, r := range s {
   128  		switch {
   129  		case escaped:
   130  			escaped = false
   131  		case r == '\\':
   132  			escaped = true
   133  			continue
   134  		case quote != 0:
   135  			if r == quote {
   136  				quote = 0
   137  				continue
   138  			}
   139  		case r == '"' || r == '\'':
   140  			quoted = true
   141  			quote = r
   142  			continue
   143  		case unicode.IsSpace(r):
   144  			if quoted || i > 0 {
   145  				quoted = false
   146  				args = append(args, string(arg[:i]))
   147  				i = 0
   148  			}
   149  			continue
   150  		}
   151  		arg[i] = r
   152  		i++
   153  	}
   154  	if quoted || i > 0 {
   155  		args = append(args, string(arg[:i]))
   156  	}
   157  	if quote != 0 {
   158  		err = errors.New("unclosed quote")
   159  	} else if escaped {
   160  		err = errors.New("unfinished escaping")
   161  	}
   162  	return args, err
   163  }
   164  
   165  // Translate rewrites f.AST, the original Go input, to remove
   166  // references to the imported package C, replacing them with
   167  // references to the equivalent Go types, functions, and variables.
   168  func (p *Package) Translate(f *File) {
   169  	for _, cref := range f.Ref {
   170  		// Convert C.ulong to C.unsigned long, etc.
   171  		cref.Name.C = cname(cref.Name.Go)
   172  	}
   173  
   174  	var conv typeConv
   175  	conv.Init(p.PtrSize, p.IntSize)
   176  
   177  	p.loadDefines(f)
   178  	p.typedefs = map[string]bool{}
   179  	p.typedefList = nil
   180  	numTypedefs := -1
   181  	for len(p.typedefs) > numTypedefs {
   182  		numTypedefs = len(p.typedefs)
   183  		// Also ask about any typedefs we've seen so far.
   184  		for _, info := range p.typedefList {
   185  			n := &Name{
   186  				Go: info.typedef,
   187  				C:  info.typedef,
   188  			}
   189  			f.Name[info.typedef] = n
   190  			f.NamePos[n] = info.pos
   191  		}
   192  		needType := p.guessKinds(f)
   193  		if len(needType) > 0 {
   194  			p.loadDWARF(f, &conv, needType)
   195  		}
   196  
   197  		// In godefs mode we're OK with the typedefs, which
   198  		// will presumably also be defined in the file, we
   199  		// don't want to resolve them to their base types.
   200  		if *godefs {
   201  			break
   202  		}
   203  	}
   204  	p.prepareNames(f)
   205  	if p.rewriteCalls(f) {
   206  		// Add `import _cgo_unsafe "unsafe"` after the package statement.
   207  		f.Edit.Insert(f.offset(f.AST.Name.End()), "; import _cgo_unsafe \"unsafe\"")
   208  	}
   209  	p.rewriteRef(f)
   210  }
   211  
   212  // loadDefines coerces gcc into spitting out the #defines in use
   213  // in the file f and saves relevant renamings in f.Name[name].Define.
   214  func (p *Package) loadDefines(f *File) {
   215  	var b bytes.Buffer
   216  	b.WriteString(builtinProlog)
   217  	b.WriteString(f.Preamble)
   218  	stdout := p.gccDefines(b.Bytes())
   219  
   220  	for _, line := range strings.Split(stdout, "\n") {
   221  		if len(line) < 9 || line[0:7] != "#define" {
   222  			continue
   223  		}
   224  
   225  		line = strings.TrimSpace(line[8:])
   226  
   227  		var key, val string
   228  		spaceIndex := strings.Index(line, " ")
   229  		tabIndex := strings.Index(line, "\t")
   230  
   231  		if spaceIndex == -1 && tabIndex == -1 {
   232  			continue
   233  		} else if tabIndex == -1 || (spaceIndex != -1 && spaceIndex < tabIndex) {
   234  			key = line[0:spaceIndex]
   235  			val = strings.TrimSpace(line[spaceIndex:])
   236  		} else {
   237  			key = line[0:tabIndex]
   238  			val = strings.TrimSpace(line[tabIndex:])
   239  		}
   240  
   241  		if key == "__clang__" {
   242  			p.GccIsClang = true
   243  		}
   244  
   245  		if n := f.Name[key]; n != nil {
   246  			if *debugDefine {
   247  				fmt.Fprintf(os.Stderr, "#define %s %s\n", key, val)
   248  			}
   249  			n.Define = val
   250  		}
   251  	}
   252  }
   253  
   254  // guessKinds tricks gcc into revealing the kind of each
   255  // name xxx for the references C.xxx in the Go input.
   256  // The kind is either a constant, type, or variable.
   257  func (p *Package) guessKinds(f *File) []*Name {
   258  	// Determine kinds for names we already know about,
   259  	// like #defines or 'struct foo', before bothering with gcc.
   260  	var names, needType []*Name
   261  	optional := map[*Name]bool{}
   262  	for _, key := range nameKeys(f.Name) {
   263  		n := f.Name[key]
   264  		// If we've already found this name as a #define
   265  		// and we can translate it as a constant value, do so.
   266  		if n.Define != "" {
   267  			if i, err := strconv.ParseInt(n.Define, 0, 64); err == nil {
   268  				n.Kind = "iconst"
   269  				// Turn decimal into hex, just for consistency
   270  				// with enum-derived constants. Otherwise
   271  				// in the cgo -godefs output half the constants
   272  				// are in hex and half are in whatever the #define used.
   273  				n.Const = fmt.Sprintf("%#x", i)
   274  			} else if n.Define[0] == '\'' {
   275  				if _, err := parser.ParseExpr(n.Define); err == nil {
   276  					n.Kind = "iconst"
   277  					n.Const = n.Define
   278  				}
   279  			} else if n.Define[0] == '"' {
   280  				if _, err := parser.ParseExpr(n.Define); err == nil {
   281  					n.Kind = "sconst"
   282  					n.Const = n.Define
   283  				}
   284  			}
   285  
   286  			if n.IsConst() {
   287  				continue
   288  			}
   289  		}
   290  
   291  		// If this is a struct, union, or enum type name, no need to guess the kind.
   292  		if strings.HasPrefix(n.C, "struct ") || strings.HasPrefix(n.C, "union ") || strings.HasPrefix(n.C, "enum ") {
   293  			n.Kind = "type"
   294  			needType = append(needType, n)
   295  			continue
   296  		}
   297  
   298  		if goos == "darwin" && strings.HasSuffix(n.C, "Ref") {
   299  			// For FooRef, find out if FooGetTypeID exists.
   300  			s := n.C[:len(n.C)-3] + "GetTypeID"
   301  			n := &Name{Go: s, C: s}
   302  			names = append(names, n)
   303  			optional[n] = true
   304  		}
   305  
   306  		// Otherwise, we'll need to find out from gcc.
   307  		names = append(names, n)
   308  	}
   309  
   310  	// Bypass gcc if there's nothing left to find out.
   311  	if len(names) == 0 {
   312  		return needType
   313  	}
   314  
   315  	// Coerce gcc into telling us whether each name is a type, a value, or undeclared.
   316  	// For names, find out whether they are integer constants.
   317  	// We used to look at specific warning or error messages here, but that tied the
   318  	// behavior too closely to specific versions of the compilers.
   319  	// Instead, arrange that we can infer what we need from only the presence or absence
   320  	// of an error on a specific line.
   321  	//
   322  	// For each name, we generate these lines, where xxx is the index in toSniff plus one.
   323  	//
   324  	//	#line xxx "not-declared"
   325  	//	void __cgo_f_xxx_1(void) { __typeof__(name) *__cgo_undefined__1; }
   326  	//	#line xxx "not-type"
   327  	//	void __cgo_f_xxx_2(void) { name *__cgo_undefined__2; }
   328  	//	#line xxx "not-int-const"
   329  	//	void __cgo_f_xxx_3(void) { enum { __cgo_undefined__3 = (name)*1 }; }
   330  	//	#line xxx "not-num-const"
   331  	//	void __cgo_f_xxx_4(void) { static const double __cgo_undefined__4 = (name); }
   332  	//	#line xxx "not-str-lit"
   333  	//	void __cgo_f_xxx_5(void) { static const char __cgo_undefined__5[] = (name); }
   334  	//
   335  	// If we see an error at not-declared:xxx, the corresponding name is not declared.
   336  	// If we see an error at not-type:xxx, the corresponding name is a type.
   337  	// If we see an error at not-int-const:xxx, the corresponding name is not an integer constant.
   338  	// If we see an error at not-num-const:xxx, the corresponding name is not a number constant.
   339  	// If we see an error at not-str-lit:xxx, the corresponding name is not a string literal.
   340  	//
   341  	// The specific input forms are chosen so that they are valid C syntax regardless of
   342  	// whether name denotes a type or an expression.
   343  
   344  	var b bytes.Buffer
   345  	b.WriteString(builtinProlog)
   346  	b.WriteString(f.Preamble)
   347  
   348  	for i, n := range names {
   349  		fmt.Fprintf(&b, "#line %d \"not-declared\"\n"+
   350  			"void __cgo_f_%d_1(void) { __typeof__(%s) *__cgo_undefined__1; }\n"+
   351  			"#line %d \"not-type\"\n"+
   352  			"void __cgo_f_%d_2(void) { %s *__cgo_undefined__2; }\n"+
   353  			"#line %d \"not-int-const\"\n"+
   354  			"void __cgo_f_%d_3(void) { enum { __cgo_undefined__3 = (%s)*1 }; }\n"+
   355  			"#line %d \"not-num-const\"\n"+
   356  			"void __cgo_f_%d_4(void) { static const double __cgo_undefined__4 = (%s); }\n"+
   357  			"#line %d \"not-str-lit\"\n"+
   358  			"void __cgo_f_%d_5(void) { static const char __cgo_undefined__5[] = (%s); }\n",
   359  			i+1, i+1, n.C,
   360  			i+1, i+1, n.C,
   361  			i+1, i+1, n.C,
   362  			i+1, i+1, n.C,
   363  			i+1, i+1, n.C,
   364  		)
   365  	}
   366  	fmt.Fprintf(&b, "#line 1 \"completed\"\n"+
   367  		"int __cgo__1 = __cgo__2;\n")
   368  
   369  	stderr := p.gccErrors(b.Bytes())
   370  	if stderr == "" {
   371  		fatalf("%s produced no output\non input:\n%s", p.gccBaseCmd()[0], b.Bytes())
   372  	}
   373  
   374  	completed := false
   375  	sniff := make([]int, len(names))
   376  	const (
   377  		notType = 1 << iota
   378  		notIntConst
   379  		notNumConst
   380  		notStrLiteral
   381  		notDeclared
   382  	)
   383  	sawUnmatchedErrors := false
   384  	for _, line := range strings.Split(stderr, "\n") {
   385  		// Ignore warnings and random comments, with one
   386  		// exception: newer GCC versions will sometimes emit
   387  		// an error on a macro #define with a note referring
   388  		// to where the expansion occurs. We care about where
   389  		// the expansion occurs, so in that case treat the note
   390  		// as an error.
   391  		isError := strings.Contains(line, ": error:")
   392  		isErrorNote := strings.Contains(line, ": note:") && sawUnmatchedErrors
   393  		if !isError && !isErrorNote {
   394  			continue
   395  		}
   396  
   397  		c1 := strings.Index(line, ":")
   398  		if c1 < 0 {
   399  			continue
   400  		}
   401  		c2 := strings.Index(line[c1+1:], ":")
   402  		if c2 < 0 {
   403  			continue
   404  		}
   405  		c2 += c1 + 1
   406  
   407  		filename := line[:c1]
   408  		i, _ := strconv.Atoi(line[c1+1 : c2])
   409  		i--
   410  		if i < 0 || i >= len(names) {
   411  			if isError {
   412  				sawUnmatchedErrors = true
   413  			}
   414  			continue
   415  		}
   416  
   417  		switch filename {
   418  		case "completed":
   419  			// Strictly speaking, there is no guarantee that seeing the error at completed:1
   420  			// (at the end of the file) means we've seen all the errors from earlier in the file,
   421  			// but usually it does. Certainly if we don't see the completed:1 error, we did
   422  			// not get all the errors we expected.
   423  			completed = true
   424  
   425  		case "not-declared":
   426  			sniff[i] |= notDeclared
   427  		case "not-type":
   428  			sniff[i] |= notType
   429  		case "not-int-const":
   430  			sniff[i] |= notIntConst
   431  		case "not-num-const":
   432  			sniff[i] |= notNumConst
   433  		case "not-str-lit":
   434  			sniff[i] |= notStrLiteral
   435  		default:
   436  			if isError {
   437  				sawUnmatchedErrors = true
   438  			}
   439  			continue
   440  		}
   441  
   442  		sawUnmatchedErrors = false
   443  	}
   444  
   445  	if !completed {
   446  		fatalf("%s did not produce error at completed:1\non input:\n%s\nfull error output:\n%s", p.gccBaseCmd()[0], b.Bytes(), stderr)
   447  	}
   448  
   449  	for i, n := range names {
   450  		switch sniff[i] {
   451  		default:
   452  			if sniff[i]&notDeclared != 0 && optional[n] {
   453  				// Ignore optional undeclared identifiers.
   454  				// Don't report an error, and skip adding n to the needType array.
   455  				continue
   456  			}
   457  			error_(f.NamePos[n], "could not determine kind of name for C.%s", fixGo(n.Go))
   458  		case notStrLiteral | notType:
   459  			n.Kind = "iconst"
   460  		case notIntConst | notStrLiteral | notType:
   461  			n.Kind = "fconst"
   462  		case notIntConst | notNumConst | notType:
   463  			n.Kind = "sconst"
   464  		case notIntConst | notNumConst | notStrLiteral:
   465  			n.Kind = "type"
   466  		case notIntConst | notNumConst | notStrLiteral | notType:
   467  			n.Kind = "not-type"
   468  		}
   469  		needType = append(needType, n)
   470  	}
   471  	if nerrors > 0 {
   472  		// Check if compiling the preamble by itself causes any errors,
   473  		// because the messages we've printed out so far aren't helpful
   474  		// to users debugging preamble mistakes. See issue 8442.
   475  		preambleErrors := p.gccErrors([]byte(f.Preamble))
   476  		if len(preambleErrors) > 0 {
   477  			error_(token.NoPos, "\n%s errors for preamble:\n%s", p.gccBaseCmd()[0], preambleErrors)
   478  		}
   479  
   480  		fatalf("unresolved names")
   481  	}
   482  
   483  	return needType
   484  }
   485  
   486  // loadDWARF parses the DWARF debug information generated
   487  // by gcc to learn the details of the constants, variables, and types
   488  // being referred to as C.xxx.
   489  func (p *Package) loadDWARF(f *File, conv *typeConv, names []*Name) {
   490  	// Extract the types from the DWARF section of an object
   491  	// from a well-formed C program. Gcc only generates DWARF info
   492  	// for symbols in the object file, so it is not enough to print the
   493  	// preamble and hope the symbols we care about will be there.
   494  	// Instead, emit
   495  	//	__typeof__(names[i]) *__cgo__i;
   496  	// for each entry in names and then dereference the type we
   497  	// learn for __cgo__i.
   498  	var b bytes.Buffer
   499  	b.WriteString(builtinProlog)
   500  	b.WriteString(f.Preamble)
   501  	b.WriteString("#line 1 \"cgo-dwarf-inference\"\n")
   502  	for i, n := range names {
   503  		fmt.Fprintf(&b, "__typeof__(%s) *__cgo__%d;\n", n.C, i)
   504  		if n.Kind == "iconst" {
   505  			fmt.Fprintf(&b, "enum { __cgo_enum__%d = %s };\n", i, n.C)
   506  		}
   507  	}
   508  
   509  	// We create a data block initialized with the values,
   510  	// so we can read them out of the object file.
   511  	fmt.Fprintf(&b, "long long __cgodebug_ints[] = {\n")
   512  	for _, n := range names {
   513  		if n.Kind == "iconst" {
   514  			fmt.Fprintf(&b, "\t%s,\n", n.C)
   515  		} else {
   516  			fmt.Fprintf(&b, "\t0,\n")
   517  		}
   518  	}
   519  	// for the last entry, we cannot use 0, otherwise
   520  	// in case all __cgodebug_data is zero initialized,
   521  	// LLVM-based gcc will place the it in the __DATA.__common
   522  	// zero-filled section (our debug/macho doesn't support
   523  	// this)
   524  	fmt.Fprintf(&b, "\t1\n")
   525  	fmt.Fprintf(&b, "};\n")
   526  
   527  	// do the same work for floats.
   528  	fmt.Fprintf(&b, "double __cgodebug_floats[] = {\n")
   529  	for _, n := range names {
   530  		if n.Kind == "fconst" {
   531  			fmt.Fprintf(&b, "\t%s,\n", n.C)
   532  		} else {
   533  			fmt.Fprintf(&b, "\t0,\n")
   534  		}
   535  	}
   536  	fmt.Fprintf(&b, "\t1\n")
   537  	fmt.Fprintf(&b, "};\n")
   538  
   539  	// do the same work for strings.
   540  	for i, n := range names {
   541  		if n.Kind == "sconst" {
   542  			fmt.Fprintf(&b, "const char __cgodebug_str__%d[] = %s;\n", i, n.C)
   543  			fmt.Fprintf(&b, "const unsigned long long __cgodebug_strlen__%d = sizeof(%s)-1;\n", i, n.C)
   544  		}
   545  	}
   546  
   547  	d, ints, floats, strs := p.gccDebug(b.Bytes(), len(names))
   548  
   549  	// Scan DWARF info for top-level TagVariable entries with AttrName __cgo__i.
   550  	types := make([]dwarf.Type, len(names))
   551  	r := d.Reader()
   552  	for {
   553  		e, err := r.Next()
   554  		if err != nil {
   555  			fatalf("reading DWARF entry: %s", err)
   556  		}
   557  		if e == nil {
   558  			break
   559  		}
   560  		switch e.Tag {
   561  		case dwarf.TagVariable:
   562  			name, _ := e.Val(dwarf.AttrName).(string)
   563  			typOff, _ := e.Val(dwarf.AttrType).(dwarf.Offset)
   564  			if name == "" || typOff == 0 {
   565  				if e.Val(dwarf.AttrSpecification) != nil {
   566  					// Since we are reading all the DWARF,
   567  					// assume we will see the variable elsewhere.
   568  					break
   569  				}
   570  				fatalf("malformed DWARF TagVariable entry")
   571  			}
   572  			if !strings.HasPrefix(name, "__cgo__") {
   573  				break
   574  			}
   575  			typ, err := d.Type(typOff)
   576  			if err != nil {
   577  				fatalf("loading DWARF type: %s", err)
   578  			}
   579  			t, ok := typ.(*dwarf.PtrType)
   580  			if !ok || t == nil {
   581  				fatalf("internal error: %s has non-pointer type", name)
   582  			}
   583  			i, err := strconv.Atoi(name[7:])
   584  			if err != nil {
   585  				fatalf("malformed __cgo__ name: %s", name)
   586  			}
   587  			types[i] = t.Type
   588  			p.recordTypedefs(t.Type, f.NamePos[names[i]])
   589  		}
   590  		if e.Tag != dwarf.TagCompileUnit {
   591  			r.SkipChildren()
   592  		}
   593  	}
   594  
   595  	// Record types and typedef information.
   596  	for i, n := range names {
   597  		if strings.HasSuffix(n.Go, "GetTypeID") && types[i].String() == "func() CFTypeID" {
   598  			conv.getTypeIDs[n.Go[:len(n.Go)-9]] = true
   599  		}
   600  	}
   601  	for i, n := range names {
   602  		if types[i] == nil {
   603  			continue
   604  		}
   605  		pos := f.NamePos[n]
   606  		f, fok := types[i].(*dwarf.FuncType)
   607  		if n.Kind != "type" && fok {
   608  			n.Kind = "func"
   609  			n.FuncType = conv.FuncType(f, pos)
   610  		} else {
   611  			n.Type = conv.Type(types[i], pos)
   612  			switch n.Kind {
   613  			case "iconst":
   614  				if i < len(ints) {
   615  					if _, ok := types[i].(*dwarf.UintType); ok {
   616  						n.Const = fmt.Sprintf("%#x", uint64(ints[i]))
   617  					} else {
   618  						n.Const = fmt.Sprintf("%#x", ints[i])
   619  					}
   620  				}
   621  			case "fconst":
   622  				if i >= len(floats) {
   623  					break
   624  				}
   625  				switch base(types[i]).(type) {
   626  				case *dwarf.IntType, *dwarf.UintType:
   627  					// This has an integer type so it's
   628  					// not really a floating point
   629  					// constant. This can happen when the
   630  					// C compiler complains about using
   631  					// the value as an integer constant,
   632  					// but not as a general constant.
   633  					// Treat this as a variable of the
   634  					// appropriate type, not a constant,
   635  					// to get C-style type handling,
   636  					// avoiding the problem that C permits
   637  					// uint64(-1) but Go does not.
   638  					// See issue 26066.
   639  					n.Kind = "var"
   640  				default:
   641  					n.Const = fmt.Sprintf("%f", floats[i])
   642  				}
   643  			case "sconst":
   644  				if i < len(strs) {
   645  					n.Const = fmt.Sprintf("%q", strs[i])
   646  				}
   647  			}
   648  		}
   649  		conv.FinishType(pos)
   650  	}
   651  }
   652  
   653  // recordTypedefs remembers in p.typedefs all the typedefs used in dtypes and its children.
   654  func (p *Package) recordTypedefs(dtype dwarf.Type, pos token.Pos) {
   655  	p.recordTypedefs1(dtype, pos, map[dwarf.Type]bool{})
   656  }
   657  
   658  func (p *Package) recordTypedefs1(dtype dwarf.Type, pos token.Pos, visited map[dwarf.Type]bool) {
   659  	if dtype == nil {
   660  		return
   661  	}
   662  	if visited[dtype] {
   663  		return
   664  	}
   665  	visited[dtype] = true
   666  	switch dt := dtype.(type) {
   667  	case *dwarf.TypedefType:
   668  		if strings.HasPrefix(dt.Name, "__builtin") {
   669  			// Don't look inside builtin types. There be dragons.
   670  			return
   671  		}
   672  		if !p.typedefs[dt.Name] {
   673  			p.typedefs[dt.Name] = true
   674  			p.typedefList = append(p.typedefList, typedefInfo{dt.Name, pos})
   675  			p.recordTypedefs1(dt.Type, pos, visited)
   676  		}
   677  	case *dwarf.PtrType:
   678  		p.recordTypedefs1(dt.Type, pos, visited)
   679  	case *dwarf.ArrayType:
   680  		p.recordTypedefs1(dt.Type, pos, visited)
   681  	case *dwarf.QualType:
   682  		p.recordTypedefs1(dt.Type, pos, visited)
   683  	case *dwarf.FuncType:
   684  		p.recordTypedefs1(dt.ReturnType, pos, visited)
   685  		for _, a := range dt.ParamType {
   686  			p.recordTypedefs1(a, pos, visited)
   687  		}
   688  	case *dwarf.StructType:
   689  		for _, f := range dt.Field {
   690  			p.recordTypedefs1(f.Type, pos, visited)
   691  		}
   692  	}
   693  }
   694  
   695  // prepareNames finalizes the Kind field of not-type names and sets
   696  // the mangled name of all names.
   697  func (p *Package) prepareNames(f *File) {
   698  	for _, n := range f.Name {
   699  		if n.Kind == "not-type" {
   700  			if n.Define == "" {
   701  				n.Kind = "var"
   702  			} else {
   703  				n.Kind = "macro"
   704  				n.FuncType = &FuncType{
   705  					Result: n.Type,
   706  					Go: &ast.FuncType{
   707  						Results: &ast.FieldList{List: []*ast.Field{{Type: n.Type.Go}}},
   708  					},
   709  				}
   710  			}
   711  		}
   712  		p.mangleName(n)
   713  	}
   714  }
   715  
   716  // mangleName does name mangling to translate names
   717  // from the original Go source files to the names
   718  // used in the final Go files generated by cgo.
   719  func (p *Package) mangleName(n *Name) {
   720  	// When using gccgo variables have to be
   721  	// exported so that they become global symbols
   722  	// that the C code can refer to.
   723  	prefix := "_C"
   724  	if *gccgo && n.IsVar() {
   725  		prefix = "C"
   726  	}
   727  	n.Mangle = prefix + n.Kind + "_" + n.Go
   728  }
   729  
   730  func (f *File) isMangledName(s string) bool {
   731  	prefix := "_C"
   732  	if strings.HasPrefix(s, prefix) {
   733  		t := s[len(prefix):]
   734  		for _, k := range nameKinds {
   735  			if strings.HasPrefix(t, k+"_") {
   736  				return true
   737  			}
   738  		}
   739  	}
   740  	return false
   741  }
   742  
   743  // rewriteCalls rewrites all calls that pass pointers to check that
   744  // they follow the rules for passing pointers between Go and C.
   745  // This reports whether the package needs to import unsafe as _cgo_unsafe.
   746  func (p *Package) rewriteCalls(f *File) bool {
   747  	needsUnsafe := false
   748  	// Walk backward so that in C.f1(C.f2()) we rewrite C.f2 first.
   749  	for _, call := range f.Calls {
   750  		if call.Done {
   751  			continue
   752  		}
   753  		start := f.offset(call.Call.Pos())
   754  		end := f.offset(call.Call.End())
   755  		str, nu := p.rewriteCall(f, call)
   756  		if str != "" {
   757  			f.Edit.Replace(start, end, str)
   758  			if nu {
   759  				needsUnsafe = true
   760  			}
   761  		}
   762  	}
   763  	return needsUnsafe
   764  }
   765  
   766  // rewriteCall rewrites one call to add pointer checks.
   767  // If any pointer checks are required, we rewrite the call into a
   768  // function literal that calls _cgoCheckPointer for each pointer
   769  // argument and then calls the original function.
   770  // This returns the rewritten call and whether the package needs to
   771  // import unsafe as _cgo_unsafe.
   772  // If it returns the empty string, the call did not need to be rewritten.
   773  func (p *Package) rewriteCall(f *File, call *Call) (string, bool) {
   774  	// This is a call to C.xxx; set goname to "xxx".
   775  	// It may have already been mangled by rewriteName.
   776  	var goname string
   777  	switch fun := call.Call.Fun.(type) {
   778  	case *ast.SelectorExpr:
   779  		goname = fun.Sel.Name
   780  	case *ast.Ident:
   781  		goname = strings.TrimPrefix(fun.Name, "_C2func_")
   782  		goname = strings.TrimPrefix(goname, "_Cfunc_")
   783  	}
   784  	if goname == "" || goname == "malloc" {
   785  		return "", false
   786  	}
   787  	name := f.Name[goname]
   788  	if name == nil || name.Kind != "func" {
   789  		// Probably a type conversion.
   790  		return "", false
   791  	}
   792  
   793  	params := name.FuncType.Params
   794  	args := call.Call.Args
   795  
   796  	// Avoid a crash if the number of arguments is
   797  	// less than the number of parameters.
   798  	// This will be caught when the generated file is compiled.
   799  	if len(args) < len(params) {
   800  		return "", false
   801  	}
   802  
   803  	any := false
   804  	for i, param := range params {
   805  		if p.needsPointerCheck(f, param.Go, args[i]) {
   806  			any = true
   807  			break
   808  		}
   809  	}
   810  	if !any {
   811  		return "", false
   812  	}
   813  
   814  	// We need to rewrite this call.
   815  	//
   816  	// Rewrite C.f(p) to
   817  	//    func() {
   818  	//            _cgo0 := p
   819  	//            _cgoCheckPointer(_cgo0)
   820  	//            C.f(_cgo0)
   821  	//    }()
   822  	// Using a function literal like this lets us evaluate the
   823  	// function arguments only once while doing pointer checks.
   824  	// This is particularly useful when passing additional arguments
   825  	// to _cgoCheckPointer, as done in checkIndex and checkAddr.
   826  	//
   827  	// When the function argument is a conversion to unsafe.Pointer,
   828  	// we unwrap the conversion before checking the pointer,
   829  	// and then wrap again when calling C.f. This lets us check
   830  	// the real type of the pointer in some cases. See issue #25941.
   831  	//
   832  	// When the call to C.f is deferred, we use an additional function
   833  	// literal to evaluate the arguments at the right time.
   834  	//    defer func() func() {
   835  	//            _cgo0 := p
   836  	//            return func() {
   837  	//                    _cgoCheckPointer(_cgo0)
   838  	//                    C.f(_cgo0)
   839  	//            }
   840  	//    }()()
   841  	// This works because the defer statement evaluates the first
   842  	// function literal in order to get the function to call.
   843  
   844  	var sb bytes.Buffer
   845  	sb.WriteString("func() ")
   846  	if call.Deferred {
   847  		sb.WriteString("func() ")
   848  	}
   849  
   850  	needsUnsafe := false
   851  	result := false
   852  	twoResults := false
   853  	if !call.Deferred {
   854  		// Check whether this call expects two results.
   855  		for _, ref := range f.Ref {
   856  			if ref.Expr != &call.Call.Fun {
   857  				continue
   858  			}
   859  			if ref.Context == ctxCall2 {
   860  				sb.WriteString("(")
   861  				result = true
   862  				twoResults = true
   863  			}
   864  			break
   865  		}
   866  
   867  		// Add the result type, if any.
   868  		if name.FuncType.Result != nil {
   869  			rtype := p.rewriteUnsafe(name.FuncType.Result.Go)
   870  			if rtype != name.FuncType.Result.Go {
   871  				needsUnsafe = true
   872  			}
   873  			sb.WriteString(gofmtLine(rtype))
   874  			result = true
   875  		}
   876  
   877  		// Add the second result type, if any.
   878  		if twoResults {
   879  			if name.FuncType.Result == nil {
   880  				// An explicit void result looks odd but it
   881  				// seems to be how cgo has worked historically.
   882  				sb.WriteString("_Ctype_void")
   883  			}
   884  			sb.WriteString(", error)")
   885  		}
   886  	}
   887  
   888  	sb.WriteString("{ ")
   889  
   890  	// Define _cgoN for each argument value.
   891  	// Write _cgoCheckPointer calls to sbCheck.
   892  	var sbCheck bytes.Buffer
   893  	for i, param := range params {
   894  		origArg := args[i]
   895  		arg, nu := p.mangle(f, &args[i])
   896  		if nu {
   897  			needsUnsafe = true
   898  		}
   899  
   900  		// Use "var x T = ..." syntax to explicitly convert untyped
   901  		// constants to the parameter type, to avoid a type mismatch.
   902  		ptype := p.rewriteUnsafe(param.Go)
   903  
   904  		if !p.needsPointerCheck(f, param.Go, args[i]) || param.BadPointer {
   905  			if ptype != param.Go {
   906  				needsUnsafe = true
   907  			}
   908  			fmt.Fprintf(&sb, "var _cgo%d %s = %s; ", i,
   909  				gofmtLine(ptype), gofmtPos(arg, origArg.Pos()))
   910  			continue
   911  		}
   912  
   913  		// Check for &a[i].
   914  		if p.checkIndex(&sb, &sbCheck, arg, i) {
   915  			continue
   916  		}
   917  
   918  		// Check for &x.
   919  		if p.checkAddr(&sb, &sbCheck, arg, i) {
   920  			continue
   921  		}
   922  
   923  		fmt.Fprintf(&sb, "_cgo%d := %s; ", i, gofmtPos(arg, origArg.Pos()))
   924  		fmt.Fprintf(&sbCheck, "_cgoCheckPointer(_cgo%d); ", i)
   925  	}
   926  
   927  	if call.Deferred {
   928  		sb.WriteString("return func() { ")
   929  	}
   930  
   931  	// Write out the calls to _cgoCheckPointer.
   932  	sb.WriteString(sbCheck.String())
   933  
   934  	if result {
   935  		sb.WriteString("return ")
   936  	}
   937  
   938  	m, nu := p.mangle(f, &call.Call.Fun)
   939  	if nu {
   940  		needsUnsafe = true
   941  	}
   942  	sb.WriteString(gofmtLine(m))
   943  
   944  	sb.WriteString("(")
   945  	for i := range params {
   946  		if i > 0 {
   947  			sb.WriteString(", ")
   948  		}
   949  		fmt.Fprintf(&sb, "_cgo%d", i)
   950  	}
   951  	sb.WriteString("); ")
   952  	if call.Deferred {
   953  		sb.WriteString("}")
   954  	}
   955  	sb.WriteString("}")
   956  	if call.Deferred {
   957  		sb.WriteString("()")
   958  	}
   959  	sb.WriteString("()")
   960  
   961  	return sb.String(), needsUnsafe
   962  }
   963  
   964  // needsPointerCheck reports whether the type t needs a pointer check.
   965  // This is true if t is a pointer and if the value to which it points
   966  // might contain a pointer.
   967  func (p *Package) needsPointerCheck(f *File, t ast.Expr, arg ast.Expr) bool {
   968  	// An untyped nil does not need a pointer check, and when
   969  	// _cgoCheckPointer returns the untyped nil the type assertion we
   970  	// are going to insert will fail.  Easier to just skip nil arguments.
   971  	// TODO: Note that this fails if nil is shadowed.
   972  	if id, ok := arg.(*ast.Ident); ok && id.Name == "nil" {
   973  		return false
   974  	}
   975  
   976  	return p.hasPointer(f, t, true)
   977  }
   978  
   979  // hasPointer is used by needsPointerCheck. If top is true it returns
   980  // whether t is or contains a pointer that might point to a pointer.
   981  // If top is false it reports whether t is or contains a pointer.
   982  // f may be nil.
   983  func (p *Package) hasPointer(f *File, t ast.Expr, top bool) bool {
   984  	switch t := t.(type) {
   985  	case *ast.ArrayType:
   986  		if t.Len == nil {
   987  			if !top {
   988  				return true
   989  			}
   990  			return p.hasPointer(f, t.Elt, false)
   991  		}
   992  		return p.hasPointer(f, t.Elt, top)
   993  	case *ast.StructType:
   994  		for _, field := range t.Fields.List {
   995  			if p.hasPointer(f, field.Type, top) {
   996  				return true
   997  			}
   998  		}
   999  		return false
  1000  	case *ast.StarExpr: // Pointer type.
  1001  		if !top {
  1002  			return true
  1003  		}
  1004  		// Check whether this is a pointer to a C union (or class)
  1005  		// type that contains a pointer.
  1006  		if unionWithPointer[t.X] {
  1007  			return true
  1008  		}
  1009  		return p.hasPointer(f, t.X, false)
  1010  	case *ast.FuncType, *ast.InterfaceType, *ast.MapType, *ast.ChanType:
  1011  		return true
  1012  	case *ast.Ident:
  1013  		// TODO: Handle types defined within function.
  1014  		for _, d := range p.Decl {
  1015  			gd, ok := d.(*ast.GenDecl)
  1016  			if !ok || gd.Tok != token.TYPE {
  1017  				continue
  1018  			}
  1019  			for _, spec := range gd.Specs {
  1020  				ts, ok := spec.(*ast.TypeSpec)
  1021  				if !ok {
  1022  					continue
  1023  				}
  1024  				if ts.Name.Name == t.Name {
  1025  					return p.hasPointer(f, ts.Type, top)
  1026  				}
  1027  			}
  1028  		}
  1029  		if def := typedef[t.Name]; def != nil {
  1030  			return p.hasPointer(f, def.Go, top)
  1031  		}
  1032  		if t.Name == "string" {
  1033  			return !top
  1034  		}
  1035  		if t.Name == "error" {
  1036  			return true
  1037  		}
  1038  		if goTypes[t.Name] != nil {
  1039  			return false
  1040  		}
  1041  		// We can't figure out the type. Conservative
  1042  		// approach is to assume it has a pointer.
  1043  		return true
  1044  	case *ast.SelectorExpr:
  1045  		if l, ok := t.X.(*ast.Ident); !ok || l.Name != "C" {
  1046  			// Type defined in a different package.
  1047  			// Conservative approach is to assume it has a
  1048  			// pointer.
  1049  			return true
  1050  		}
  1051  		if f == nil {
  1052  			// Conservative approach: assume pointer.
  1053  			return true
  1054  		}
  1055  		name := f.Name[t.Sel.Name]
  1056  		if name != nil && name.Kind == "type" && name.Type != nil && name.Type.Go != nil {
  1057  			return p.hasPointer(f, name.Type.Go, top)
  1058  		}
  1059  		// We can't figure out the type. Conservative
  1060  		// approach is to assume it has a pointer.
  1061  		return true
  1062  	default:
  1063  		error_(t.Pos(), "could not understand type %s", gofmt(t))
  1064  		return true
  1065  	}
  1066  }
  1067  
  1068  // mangle replaces references to C names in arg with the mangled names,
  1069  // rewriting calls when it finds them.
  1070  // It removes the corresponding references in f.Ref and f.Calls, so that we
  1071  // don't try to do the replacement again in rewriteRef or rewriteCall.
  1072  func (p *Package) mangle(f *File, arg *ast.Expr) (ast.Expr, bool) {
  1073  	needsUnsafe := false
  1074  	f.walk(arg, ctxExpr, func(f *File, arg interface{}, context astContext) {
  1075  		px, ok := arg.(*ast.Expr)
  1076  		if !ok {
  1077  			return
  1078  		}
  1079  		sel, ok := (*px).(*ast.SelectorExpr)
  1080  		if ok {
  1081  			if l, ok := sel.X.(*ast.Ident); !ok || l.Name != "C" {
  1082  				return
  1083  			}
  1084  
  1085  			for _, r := range f.Ref {
  1086  				if r.Expr == px {
  1087  					*px = p.rewriteName(f, r)
  1088  					r.Done = true
  1089  					break
  1090  				}
  1091  			}
  1092  
  1093  			return
  1094  		}
  1095  
  1096  		call, ok := (*px).(*ast.CallExpr)
  1097  		if !ok {
  1098  			return
  1099  		}
  1100  
  1101  		for _, c := range f.Calls {
  1102  			if !c.Done && c.Call.Lparen == call.Lparen {
  1103  				cstr, nu := p.rewriteCall(f, c)
  1104  				if cstr != "" {
  1105  					// Smuggle the rewritten call through an ident.
  1106  					*px = ast.NewIdent(cstr)
  1107  					if nu {
  1108  						needsUnsafe = true
  1109  					}
  1110  					c.Done = true
  1111  				}
  1112  			}
  1113  		}
  1114  	})
  1115  	return *arg, needsUnsafe
  1116  }
  1117  
  1118  // checkIndex checks whether arg has the form &a[i], possibly inside
  1119  // type conversions. If so, then in the general case it writes
  1120  //    _cgoIndexNN := a
  1121  //    _cgoNN := &cgoIndexNN[i] // with type conversions, if any
  1122  // to sb, and writes
  1123  //    _cgoCheckPointer(_cgoNN, _cgoIndexNN)
  1124  // to sbCheck, and returns true. If a is a simple variable or field reference,
  1125  // it writes
  1126  //    _cgoIndexNN := &a
  1127  // and dereferences the uses of _cgoIndexNN. Taking the address avoids
  1128  // making a copy of an array.
  1129  //
  1130  // This tells _cgoCheckPointer to check the complete contents of the
  1131  // slice or array being indexed, but no other part of the memory allocation.
  1132  func (p *Package) checkIndex(sb, sbCheck *bytes.Buffer, arg ast.Expr, i int) bool {
  1133  	// Strip type conversions.
  1134  	x := arg
  1135  	for {
  1136  		c, ok := x.(*ast.CallExpr)
  1137  		if !ok || len(c.Args) != 1 || !p.isType(c.Fun) {
  1138  			break
  1139  		}
  1140  		x = c.Args[0]
  1141  	}
  1142  	u, ok := x.(*ast.UnaryExpr)
  1143  	if !ok || u.Op != token.AND {
  1144  		return false
  1145  	}
  1146  	index, ok := u.X.(*ast.IndexExpr)
  1147  	if !ok {
  1148  		return false
  1149  	}
  1150  
  1151  	addr := ""
  1152  	deref := ""
  1153  	if p.isVariable(index.X) {
  1154  		addr = "&"
  1155  		deref = "*"
  1156  	}
  1157  
  1158  	fmt.Fprintf(sb, "_cgoIndex%d := %s%s; ", i, addr, gofmtPos(index.X, index.X.Pos()))
  1159  	origX := index.X
  1160  	index.X = ast.NewIdent(fmt.Sprintf("_cgoIndex%d", i))
  1161  	if deref == "*" {
  1162  		index.X = &ast.StarExpr{X: index.X}
  1163  	}
  1164  	fmt.Fprintf(sb, "_cgo%d := %s; ", i, gofmtPos(arg, arg.Pos()))
  1165  	index.X = origX
  1166  
  1167  	fmt.Fprintf(sbCheck, "_cgoCheckPointer(_cgo%d, %s_cgoIndex%d); ", i, deref, i)
  1168  
  1169  	return true
  1170  }
  1171  
  1172  // checkAddr checks whether arg has the form &x, possibly inside type
  1173  // conversions. If so, it writes
  1174  //    _cgoBaseNN := &x
  1175  //    _cgoNN := _cgoBaseNN // with type conversions, if any
  1176  // to sb, and writes
  1177  //    _cgoCheckPointer(_cgoBaseNN, true)
  1178  // to sbCheck, and returns true. This tells _cgoCheckPointer to check
  1179  // just the contents of the pointer being passed, not any other part
  1180  // of the memory allocation. This is run after checkIndex, which looks
  1181  // for the special case of &a[i], which requires different checks.
  1182  func (p *Package) checkAddr(sb, sbCheck *bytes.Buffer, arg ast.Expr, i int) bool {
  1183  	// Strip type conversions.
  1184  	px := &arg
  1185  	for {
  1186  		c, ok := (*px).(*ast.CallExpr)
  1187  		if !ok || len(c.Args) != 1 || !p.isType(c.Fun) {
  1188  			break
  1189  		}
  1190  		px = &c.Args[0]
  1191  	}
  1192  	if u, ok := (*px).(*ast.UnaryExpr); !ok || u.Op != token.AND {
  1193  		return false
  1194  	}
  1195  
  1196  	fmt.Fprintf(sb, "_cgoBase%d := %s; ", i, gofmtPos(*px, (*px).Pos()))
  1197  
  1198  	origX := *px
  1199  	*px = ast.NewIdent(fmt.Sprintf("_cgoBase%d", i))
  1200  	fmt.Fprintf(sb, "_cgo%d := %s; ", i, gofmtPos(arg, arg.Pos()))
  1201  	*px = origX
  1202  
  1203  	// Use "0 == 0" to do the right thing in the unlikely event
  1204  	// that "true" is shadowed.
  1205  	fmt.Fprintf(sbCheck, "_cgoCheckPointer(_cgoBase%d, 0 == 0); ", i)
  1206  
  1207  	return true
  1208  }
  1209  
  1210  // isType reports whether the expression is definitely a type.
  1211  // This is conservative--it returns false for an unknown identifier.
  1212  func (p *Package) isType(t ast.Expr) bool {
  1213  	switch t := t.(type) {
  1214  	case *ast.SelectorExpr:
  1215  		id, ok := t.X.(*ast.Ident)
  1216  		if !ok {
  1217  			return false
  1218  		}
  1219  		if id.Name == "unsafe" && t.Sel.Name == "Pointer" {
  1220  			return true
  1221  		}
  1222  		if id.Name == "C" && typedef["_Ctype_"+t.Sel.Name] != nil {
  1223  			return true
  1224  		}
  1225  		return false
  1226  	case *ast.Ident:
  1227  		// TODO: This ignores shadowing.
  1228  		switch t.Name {
  1229  		case "unsafe.Pointer", "bool", "byte",
  1230  			"complex64", "complex128",
  1231  			"error",
  1232  			"float32", "float64",
  1233  			"int", "int8", "int16", "int32", "int64",
  1234  			"rune", "string",
  1235  			"uint", "uint8", "uint16", "uint32", "uint64", "uintptr":
  1236  
  1237  			return true
  1238  		}
  1239  		if strings.HasPrefix(t.Name, "_Ctype_") {
  1240  			return true
  1241  		}
  1242  	case *ast.StarExpr:
  1243  		return p.isType(t.X)
  1244  	case *ast.ArrayType, *ast.StructType, *ast.FuncType, *ast.InterfaceType,
  1245  		*ast.MapType, *ast.ChanType:
  1246  
  1247  		return true
  1248  	}
  1249  	return false
  1250  }
  1251  
  1252  // isVariable reports whether x is a variable, possibly with field references.
  1253  func (p *Package) isVariable(x ast.Expr) bool {
  1254  	switch x := x.(type) {
  1255  	case *ast.Ident:
  1256  		return true
  1257  	case *ast.SelectorExpr:
  1258  		return p.isVariable(x.X)
  1259  	case *ast.IndexExpr:
  1260  		return true
  1261  	}
  1262  	return false
  1263  }
  1264  
  1265  // rewriteUnsafe returns a version of t with references to unsafe.Pointer
  1266  // rewritten to use _cgo_unsafe.Pointer instead.
  1267  func (p *Package) rewriteUnsafe(t ast.Expr) ast.Expr {
  1268  	switch t := t.(type) {
  1269  	case *ast.Ident:
  1270  		// We don't see a SelectorExpr for unsafe.Pointer;
  1271  		// this is created by code in this file.
  1272  		if t.Name == "unsafe.Pointer" {
  1273  			return ast.NewIdent("_cgo_unsafe.Pointer")
  1274  		}
  1275  	case *ast.ArrayType:
  1276  		t1 := p.rewriteUnsafe(t.Elt)
  1277  		if t1 != t.Elt {
  1278  			r := *t
  1279  			r.Elt = t1
  1280  			return &r
  1281  		}
  1282  	case *ast.StructType:
  1283  		changed := false
  1284  		fields := *t.Fields
  1285  		fields.List = nil
  1286  		for _, f := range t.Fields.List {
  1287  			ft := p.rewriteUnsafe(f.Type)
  1288  			if ft == f.Type {
  1289  				fields.List = append(fields.List, f)
  1290  			} else {
  1291  				fn := *f
  1292  				fn.Type = ft
  1293  				fields.List = append(fields.List, &fn)
  1294  				changed = true
  1295  			}
  1296  		}
  1297  		if changed {
  1298  			r := *t
  1299  			r.Fields = &fields
  1300  			return &r
  1301  		}
  1302  	case *ast.StarExpr: // Pointer type.
  1303  		x1 := p.rewriteUnsafe(t.X)
  1304  		if x1 != t.X {
  1305  			r := *t
  1306  			r.X = x1
  1307  			return &r
  1308  		}
  1309  	}
  1310  	return t
  1311  }
  1312  
  1313  // rewriteRef rewrites all the C.xxx references in f.AST to refer to the
  1314  // Go equivalents, now that we have figured out the meaning of all
  1315  // the xxx. In *godefs mode, rewriteRef replaces the names
  1316  // with full definitions instead of mangled names.
  1317  func (p *Package) rewriteRef(f *File) {
  1318  	// Keep a list of all the functions, to remove the ones
  1319  	// only used as expressions and avoid generating bridge
  1320  	// code for them.
  1321  	functions := make(map[string]bool)
  1322  
  1323  	for _, n := range f.Name {
  1324  		if n.Kind == "func" {
  1325  			functions[n.Go] = false
  1326  		}
  1327  	}
  1328  
  1329  	// Now that we have all the name types filled in,
  1330  	// scan through the Refs to identify the ones that
  1331  	// are trying to do a ,err call. Also check that
  1332  	// functions are only used in calls.
  1333  	for _, r := range f.Ref {
  1334  		if r.Name.IsConst() && r.Name.Const == "" {
  1335  			error_(r.Pos(), "unable to find value of constant C.%s", fixGo(r.Name.Go))
  1336  		}
  1337  
  1338  		if r.Name.Kind == "func" {
  1339  			switch r.Context {
  1340  			case ctxCall, ctxCall2:
  1341  				functions[r.Name.Go] = true
  1342  			}
  1343  		}
  1344  
  1345  		expr := p.rewriteName(f, r)
  1346  
  1347  		if *godefs {
  1348  			// Substitute definition for mangled type name.
  1349  			if id, ok := expr.(*ast.Ident); ok {
  1350  				if t := typedef[id.Name]; t != nil {
  1351  					expr = t.Go
  1352  				}
  1353  				if id.Name == r.Name.Mangle && r.Name.Const != "" {
  1354  					expr = ast.NewIdent(r.Name.Const)
  1355  				}
  1356  			}
  1357  		}
  1358  
  1359  		// Copy position information from old expr into new expr,
  1360  		// in case expression being replaced is first on line.
  1361  		// See golang.org/issue/6563.
  1362  		pos := (*r.Expr).Pos()
  1363  		if x, ok := expr.(*ast.Ident); ok {
  1364  			expr = &ast.Ident{NamePos: pos, Name: x.Name}
  1365  		}
  1366  
  1367  		// Change AST, because some later processing depends on it,
  1368  		// and also because -godefs mode still prints the AST.
  1369  		old := *r.Expr
  1370  		*r.Expr = expr
  1371  
  1372  		// Record source-level edit for cgo output.
  1373  		if !r.Done {
  1374  			// Prepend a space in case the earlier code ends
  1375  			// with '/', which would give us a "//" comment.
  1376  			repl := " " + gofmtPos(expr, old.Pos())
  1377  			end := fset.Position(old.End())
  1378  			// Subtract 1 from the column if we are going to
  1379  			// append a close parenthesis. That will set the
  1380  			// correct column for the following characters.
  1381  			sub := 0
  1382  			if r.Name.Kind != "type" {
  1383  				sub = 1
  1384  			}
  1385  			if end.Column > sub {
  1386  				repl = fmt.Sprintf("%s /*line :%d:%d*/", repl, end.Line, end.Column-sub)
  1387  			}
  1388  			if r.Name.Kind != "type" {
  1389  				repl = "(" + repl + ")"
  1390  			}
  1391  			f.Edit.Replace(f.offset(old.Pos()), f.offset(old.End()), repl)
  1392  		}
  1393  	}
  1394  
  1395  	// Remove functions only used as expressions, so their respective
  1396  	// bridge functions are not generated.
  1397  	for name, used := range functions {
  1398  		if !used {
  1399  			delete(f.Name, name)
  1400  		}
  1401  	}
  1402  }
  1403  
  1404  // rewriteName returns the expression used to rewrite a reference.
  1405  func (p *Package) rewriteName(f *File, r *Ref) ast.Expr {
  1406  	var expr ast.Expr = ast.NewIdent(r.Name.Mangle) // default
  1407  	switch r.Context {
  1408  	case ctxCall, ctxCall2:
  1409  		if r.Name.Kind != "func" {
  1410  			if r.Name.Kind == "type" {
  1411  				r.Context = ctxType
  1412  				if r.Name.Type == nil {
  1413  					error_(r.Pos(), "invalid conversion to C.%s: undefined C type '%s'", fixGo(r.Name.Go), r.Name.C)
  1414  					break
  1415  				}
  1416  				expr = r.Name.Type.Go
  1417  				break
  1418  			}
  1419  			error_(r.Pos(), "call of non-function C.%s", fixGo(r.Name.Go))
  1420  			break
  1421  		}
  1422  		if r.Context == ctxCall2 {
  1423  			if r.Name.Go == "_CMalloc" {
  1424  				error_(r.Pos(), "no two-result form for C.malloc")
  1425  				break
  1426  			}
  1427  			// Invent new Name for the two-result function.
  1428  			n := f.Name["2"+r.Name.Go]
  1429  			if n == nil {
  1430  				n = new(Name)
  1431  				*n = *r.Name
  1432  				n.AddError = true
  1433  				n.Mangle = "_C2func_" + n.Go
  1434  				f.Name["2"+r.Name.Go] = n
  1435  			}
  1436  			expr = ast.NewIdent(n.Mangle)
  1437  			r.Name = n
  1438  			break
  1439  		}
  1440  	case ctxExpr:
  1441  		switch r.Name.Kind {
  1442  		case "func":
  1443  			if builtinDefs[r.Name.C] != "" {
  1444  				error_(r.Pos(), "use of builtin '%s' not in function call", fixGo(r.Name.C))
  1445  			}
  1446  
  1447  			// Function is being used in an expression, to e.g. pass around a C function pointer.
  1448  			// Create a new Name for this Ref which causes the variable to be declared in Go land.
  1449  			fpName := "fp_" + r.Name.Go
  1450  			name := f.Name[fpName]
  1451  			if name == nil {
  1452  				name = &Name{
  1453  					Go:   fpName,
  1454  					C:    r.Name.C,
  1455  					Kind: "fpvar",
  1456  					Type: &Type{Size: p.PtrSize, Align: p.PtrSize, C: c("void*"), Go: ast.NewIdent("unsafe.Pointer")},
  1457  				}
  1458  				p.mangleName(name)
  1459  				f.Name[fpName] = name
  1460  			}
  1461  			r.Name = name
  1462  			// Rewrite into call to _Cgo_ptr to prevent assignments. The _Cgo_ptr
  1463  			// function is defined in out.go and simply returns its argument. See
  1464  			// issue 7757.
  1465  			expr = &ast.CallExpr{
  1466  				Fun:  &ast.Ident{NamePos: (*r.Expr).Pos(), Name: "_Cgo_ptr"},
  1467  				Args: []ast.Expr{ast.NewIdent(name.Mangle)},
  1468  			}
  1469  		case "type":
  1470  			// Okay - might be new(T)
  1471  			if r.Name.Type == nil {
  1472  				error_(r.Pos(), "expression C.%s: undefined C type '%s'", fixGo(r.Name.Go), r.Name.C)
  1473  				break
  1474  			}
  1475  			expr = r.Name.Type.Go
  1476  		case "var":
  1477  			expr = &ast.StarExpr{Star: (*r.Expr).Pos(), X: expr}
  1478  		case "macro":
  1479  			expr = &ast.CallExpr{Fun: expr}
  1480  		}
  1481  	case ctxSelector:
  1482  		if r.Name.Kind == "var" {
  1483  			expr = &ast.StarExpr{Star: (*r.Expr).Pos(), X: expr}
  1484  		} else {
  1485  			error_(r.Pos(), "only C variables allowed in selector expression %s", fixGo(r.Name.Go))
  1486  		}
  1487  	case ctxType:
  1488  		if r.Name.Kind != "type" {
  1489  			error_(r.Pos(), "expression C.%s used as type", fixGo(r.Name.Go))
  1490  		} else if r.Name.Type == nil {
  1491  			// Use of C.enum_x, C.struct_x or C.union_x without C definition.
  1492  			// GCC won't raise an error when using pointers to such unknown types.
  1493  			error_(r.Pos(), "type C.%s: undefined C type '%s'", fixGo(r.Name.Go), r.Name.C)
  1494  		} else {
  1495  			expr = r.Name.Type.Go
  1496  		}
  1497  	default:
  1498  		if r.Name.Kind == "func" {
  1499  			error_(r.Pos(), "must call C.%s", fixGo(r.Name.Go))
  1500  		}
  1501  	}
  1502  	return expr
  1503  }
  1504  
  1505  // gofmtPos returns the gofmt-formatted string for an AST node,
  1506  // with a comment setting the position before the node.
  1507  func gofmtPos(n ast.Expr, pos token.Pos) string {
  1508  	s := gofmtLine(n)
  1509  	p := fset.Position(pos)
  1510  	if p.Column == 0 {
  1511  		return s
  1512  	}
  1513  	return fmt.Sprintf("/*line :%d:%d*/%s", p.Line, p.Column, s)
  1514  }
  1515  
  1516  // gccBaseCmd returns the start of the compiler command line.
  1517  // It uses $CC if set, or else $GCC, or else the compiler recorded
  1518  // during the initial build as defaultCC.
  1519  // defaultCC is defined in zdefaultcc.go, written by cmd/dist.
  1520  func (p *Package) gccBaseCmd() []string {
  1521  	// Use $CC if set, since that's what the build uses.
  1522  	if ret := strings.Fields(os.Getenv("CC")); len(ret) > 0 {
  1523  		return ret
  1524  	}
  1525  	// Try $GCC if set, since that's what we used to use.
  1526  	if ret := strings.Fields(os.Getenv("GCC")); len(ret) > 0 {
  1527  		return ret
  1528  	}
  1529  	return strings.Fields(defaultCC(goos, goarch))
  1530  }
  1531  
  1532  // gccMachine returns the gcc -m flag to use, either "-m32", "-m64" or "-marm".
  1533  func (p *Package) gccMachine() []string {
  1534  	switch goarch {
  1535  	case "amd64":
  1536  		return []string{"-m64"}
  1537  	case "386":
  1538  		return []string{"-m32"}
  1539  	case "arm":
  1540  		return []string{"-marm"} // not thumb
  1541  	case "s390":
  1542  		return []string{"-m31"}
  1543  	case "s390x":
  1544  		return []string{"-m64"}
  1545  	case "mips64", "mips64le":
  1546  		return []string{"-mabi=64"}
  1547  	case "mips", "mipsle":
  1548  		return []string{"-mabi=32"}
  1549  	}
  1550  	return nil
  1551  }
  1552  
  1553  func gccTmp() string {
  1554  	return *objDir + "_cgo_.o"
  1555  }
  1556  
  1557  // gccCmd returns the gcc command line to use for compiling
  1558  // the input.
  1559  func (p *Package) gccCmd() []string {
  1560  	c := append(p.gccBaseCmd(),
  1561  		"-w",          // no warnings
  1562  		"-Wno-error",  // warnings are not errors
  1563  		"-o"+gccTmp(), // write object to tmp
  1564  		"-gdwarf-2",   // generate DWARF v2 debugging symbols
  1565  		"-c",          // do not link
  1566  		"-xc",         // input language is C
  1567  	)
  1568  	if p.GccIsClang {
  1569  		c = append(c,
  1570  			"-ferror-limit=0",
  1571  			// Apple clang version 1.7 (tags/Apple/clang-77) (based on LLVM 2.9svn)
  1572  			// doesn't have -Wno-unneeded-internal-declaration, so we need yet another
  1573  			// flag to disable the warning. Yes, really good diagnostics, clang.
  1574  			"-Wno-unknown-warning-option",
  1575  			"-Wno-unneeded-internal-declaration",
  1576  			"-Wno-unused-function",
  1577  			"-Qunused-arguments",
  1578  			// Clang embeds prototypes for some builtin functions,
  1579  			// like malloc and calloc, but all size_t parameters are
  1580  			// incorrectly typed unsigned long. We work around that
  1581  			// by disabling the builtin functions (this is safe as
  1582  			// it won't affect the actual compilation of the C code).
  1583  			// See: https://golang.org/issue/6506.
  1584  			"-fno-builtin",
  1585  		)
  1586  	}
  1587  
  1588  	c = append(c, p.GccOptions...)
  1589  	c = append(c, p.gccMachine()...)
  1590  	if goos == "aix" {
  1591  		c = append(c, "-maix64")
  1592  	}
  1593  	c = append(c, "-") //read input from standard input
  1594  	return c
  1595  }
  1596  
  1597  // gccDebug runs gcc -gdwarf-2 over the C program stdin and
  1598  // returns the corresponding DWARF data and, if present, debug data block.
  1599  func (p *Package) gccDebug(stdin []byte, nnames int) (d *dwarf.Data, ints []int64, floats []float64, strs []string) {
  1600  	runGcc(stdin, p.gccCmd())
  1601  
  1602  	isDebugInts := func(s string) bool {
  1603  		// Some systems use leading _ to denote non-assembly symbols.
  1604  		return s == "__cgodebug_ints" || s == "___cgodebug_ints"
  1605  	}
  1606  	isDebugFloats := func(s string) bool {
  1607  		// Some systems use leading _ to denote non-assembly symbols.
  1608  		return s == "__cgodebug_floats" || s == "___cgodebug_floats"
  1609  	}
  1610  	indexOfDebugStr := func(s string) int {
  1611  		// Some systems use leading _ to denote non-assembly symbols.
  1612  		if strings.HasPrefix(s, "___") {
  1613  			s = s[1:]
  1614  		}
  1615  		if strings.HasPrefix(s, "__cgodebug_str__") {
  1616  			if n, err := strconv.Atoi(s[len("__cgodebug_str__"):]); err == nil {
  1617  				return n
  1618  			}
  1619  		}
  1620  		return -1
  1621  	}
  1622  	indexOfDebugStrlen := func(s string) int {
  1623  		// Some systems use leading _ to denote non-assembly symbols.
  1624  		if strings.HasPrefix(s, "___") {
  1625  			s = s[1:]
  1626  		}
  1627  		if strings.HasPrefix(s, "__cgodebug_strlen__") {
  1628  			if n, err := strconv.Atoi(s[len("__cgodebug_strlen__"):]); err == nil {
  1629  				return n
  1630  			}
  1631  		}
  1632  		return -1
  1633  	}
  1634  
  1635  	strs = make([]string, nnames)
  1636  
  1637  	strdata := make(map[int]string, nnames)
  1638  	strlens := make(map[int]int, nnames)
  1639  
  1640  	buildStrings := func() {
  1641  		for n, strlen := range strlens {
  1642  			data := strdata[n]
  1643  			if len(data) <= strlen {
  1644  				fatalf("invalid string literal")
  1645  			}
  1646  			strs[n] = data[:strlen]
  1647  		}
  1648  	}
  1649  
  1650  	if f, err := macho.Open(gccTmp()); err == nil {
  1651  		defer f.Close()
  1652  		d, err := f.DWARF()
  1653  		if err != nil {
  1654  			fatalf("cannot load DWARF output from %s: %v", gccTmp(), err)
  1655  		}
  1656  		bo := f.ByteOrder
  1657  		if f.Symtab != nil {
  1658  			for i := range f.Symtab.Syms {
  1659  				s := &f.Symtab.Syms[i]
  1660  				switch {
  1661  				case isDebugInts(s.Name):
  1662  					// Found it. Now find data section.
  1663  					if i := int(s.Sect) - 1; 0 <= i && i < len(f.Sections) {
  1664  						sect := f.Sections[i]
  1665  						if sect.Addr <= s.Value && s.Value < sect.Addr+sect.Size {
  1666  							if sdat, err := sect.Data(); err == nil {
  1667  								data := sdat[s.Value-sect.Addr:]
  1668  								ints = make([]int64, len(data)/8)
  1669  								for i := range ints {
  1670  									ints[i] = int64(bo.Uint64(data[i*8:]))
  1671  								}
  1672  							}
  1673  						}
  1674  					}
  1675  				case isDebugFloats(s.Name):
  1676  					// Found it. Now find data section.
  1677  					if i := int(s.Sect) - 1; 0 <= i && i < len(f.Sections) {
  1678  						sect := f.Sections[i]
  1679  						if sect.Addr <= s.Value && s.Value < sect.Addr+sect.Size {
  1680  							if sdat, err := sect.Data(); err == nil {
  1681  								data := sdat[s.Value-sect.Addr:]
  1682  								floats = make([]float64, len(data)/8)
  1683  								for i := range floats {
  1684  									floats[i] = math.Float64frombits(bo.Uint64(data[i*8:]))
  1685  								}
  1686  							}
  1687  						}
  1688  					}
  1689  				default:
  1690  					if n := indexOfDebugStr(s.Name); n != -1 {
  1691  						// Found it. Now find data section.
  1692  						if i := int(s.Sect) - 1; 0 <= i && i < len(f.Sections) {
  1693  							sect := f.Sections[i]
  1694  							if sect.Addr <= s.Value && s.Value < sect.Addr+sect.Size {
  1695  								if sdat, err := sect.Data(); err == nil {
  1696  									data := sdat[s.Value-sect.Addr:]
  1697  									strdata[n] = string(data)
  1698  								}
  1699  							}
  1700  						}
  1701  						break
  1702  					}
  1703  					if n := indexOfDebugStrlen(s.Name); n != -1 {
  1704  						// Found it. Now find data section.
  1705  						if i := int(s.Sect) - 1; 0 <= i && i < len(f.Sections) {
  1706  							sect := f.Sections[i]
  1707  							if sect.Addr <= s.Value && s.Value < sect.Addr+sect.Size {
  1708  								if sdat, err := sect.Data(); err == nil {
  1709  									data := sdat[s.Value-sect.Addr:]
  1710  									strlen := bo.Uint64(data[:8])
  1711  									if strlen > (1<<(uint(p.IntSize*8)-1) - 1) { // greater than MaxInt?
  1712  										fatalf("string literal too big")
  1713  									}
  1714  									strlens[n] = int(strlen)
  1715  								}
  1716  							}
  1717  						}
  1718  						break
  1719  					}
  1720  				}
  1721  			}
  1722  
  1723  			buildStrings()
  1724  		}
  1725  		return d, ints, floats, strs
  1726  	}
  1727  
  1728  	if f, err := elf.Open(gccTmp()); err == nil {
  1729  		defer f.Close()
  1730  		d, err := f.DWARF()
  1731  		if err != nil {
  1732  			fatalf("cannot load DWARF output from %s: %v", gccTmp(), err)
  1733  		}
  1734  		bo := f.ByteOrder
  1735  		symtab, err := f.Symbols()
  1736  		if err == nil {
  1737  			for i := range symtab {
  1738  				s := &symtab[i]
  1739  				switch {
  1740  				case isDebugInts(s.Name):
  1741  					// Found it. Now find data section.
  1742  					if i := int(s.Section); 0 <= i && i < len(f.Sections) {
  1743  						sect := f.Sections[i]
  1744  						if sect.Addr <= s.Value && s.Value < sect.Addr+sect.Size {
  1745  							if sdat, err := sect.Data(); err == nil {
  1746  								data := sdat[s.Value-sect.Addr:]
  1747  								ints = make([]int64, len(data)/8)
  1748  								for i := range ints {
  1749  									ints[i] = int64(bo.Uint64(data[i*8:]))
  1750  								}
  1751  							}
  1752  						}
  1753  					}
  1754  				case isDebugFloats(s.Name):
  1755  					// Found it. Now find data section.
  1756  					if i := int(s.Section); 0 <= i && i < len(f.Sections) {
  1757  						sect := f.Sections[i]
  1758  						if sect.Addr <= s.Value && s.Value < sect.Addr+sect.Size {
  1759  							if sdat, err := sect.Data(); err == nil {
  1760  								data := sdat[s.Value-sect.Addr:]
  1761  								floats = make([]float64, len(data)/8)
  1762  								for i := range floats {
  1763  									floats[i] = math.Float64frombits(bo.Uint64(data[i*8:]))
  1764  								}
  1765  							}
  1766  						}
  1767  					}
  1768  				default:
  1769  					if n := indexOfDebugStr(s.Name); n != -1 {
  1770  						// Found it. Now find data section.
  1771  						if i := int(s.Section); 0 <= i && i < len(f.Sections) {
  1772  							sect := f.Sections[i]
  1773  							if sect.Addr <= s.Value && s.Value < sect.Addr+sect.Size {
  1774  								if sdat, err := sect.Data(); err == nil {
  1775  									data := sdat[s.Value-sect.Addr:]
  1776  									strdata[n] = string(data)
  1777  								}
  1778  							}
  1779  						}
  1780  						break
  1781  					}
  1782  					if n := indexOfDebugStrlen(s.Name); n != -1 {
  1783  						// Found it. Now find data section.
  1784  						if i := int(s.Section); 0 <= i && i < len(f.Sections) {
  1785  							sect := f.Sections[i]
  1786  							if sect.Addr <= s.Value && s.Value < sect.Addr+sect.Size {
  1787  								if sdat, err := sect.Data(); err == nil {
  1788  									data := sdat[s.Value-sect.Addr:]
  1789  									strlen := bo.Uint64(data[:8])
  1790  									if strlen > (1<<(uint(p.IntSize*8)-1) - 1) { // greater than MaxInt?
  1791  										fatalf("string literal too big")
  1792  									}
  1793  									strlens[n] = int(strlen)
  1794  								}
  1795  							}
  1796  						}
  1797  						break
  1798  					}
  1799  				}
  1800  			}
  1801  
  1802  			buildStrings()
  1803  		}
  1804  		return d, ints, floats, strs
  1805  	}
  1806  
  1807  	if f, err := pe.Open(gccTmp()); err == nil {
  1808  		defer f.Close()
  1809  		d, err := f.DWARF()
  1810  		if err != nil {
  1811  			fatalf("cannot load DWARF output from %s: %v", gccTmp(), err)
  1812  		}
  1813  		bo := binary.LittleEndian
  1814  		for _, s := range f.Symbols {
  1815  			switch {
  1816  			case isDebugInts(s.Name):
  1817  				if i := int(s.SectionNumber) - 1; 0 <= i && i < len(f.Sections) {
  1818  					sect := f.Sections[i]
  1819  					if s.Value < sect.Size {
  1820  						if sdat, err := sect.Data(); err == nil {
  1821  							data := sdat[s.Value:]
  1822  							ints = make([]int64, len(data)/8)
  1823  							for i := range ints {
  1824  								ints[i] = int64(bo.Uint64(data[i*8:]))
  1825  							}
  1826  						}
  1827  					}
  1828  				}
  1829  			case isDebugFloats(s.Name):
  1830  				if i := int(s.SectionNumber) - 1; 0 <= i && i < len(f.Sections) {
  1831  					sect := f.Sections[i]
  1832  					if s.Value < sect.Size {
  1833  						if sdat, err := sect.Data(); err == nil {
  1834  							data := sdat[s.Value:]
  1835  							floats = make([]float64, len(data)/8)
  1836  							for i := range floats {
  1837  								floats[i] = math.Float64frombits(bo.Uint64(data[i*8:]))
  1838  							}
  1839  						}
  1840  					}
  1841  				}
  1842  			default:
  1843  				if n := indexOfDebugStr(s.Name); n != -1 {
  1844  					if i := int(s.SectionNumber) - 1; 0 <= i && i < len(f.Sections) {
  1845  						sect := f.Sections[i]
  1846  						if s.Value < sect.Size {
  1847  							if sdat, err := sect.Data(); err == nil {
  1848  								data := sdat[s.Value:]
  1849  								strdata[n] = string(data)
  1850  							}
  1851  						}
  1852  					}
  1853  					break
  1854  				}
  1855  				if n := indexOfDebugStrlen(s.Name); n != -1 {
  1856  					if i := int(s.SectionNumber) - 1; 0 <= i && i < len(f.Sections) {
  1857  						sect := f.Sections[i]
  1858  						if s.Value < sect.Size {
  1859  							if sdat, err := sect.Data(); err == nil {
  1860  								data := sdat[s.Value:]
  1861  								strlen := bo.Uint64(data[:8])
  1862  								if strlen > (1<<(uint(p.IntSize*8)-1) - 1) { // greater than MaxInt?
  1863  									fatalf("string literal too big")
  1864  								}
  1865  								strlens[n] = int(strlen)
  1866  							}
  1867  						}
  1868  					}
  1869  					break
  1870  				}
  1871  			}
  1872  		}
  1873  
  1874  		buildStrings()
  1875  
  1876  		return d, ints, floats, strs
  1877  	}
  1878  
  1879  	if f, err := xcoff.Open(gccTmp()); err == nil {
  1880  		defer f.Close()
  1881  		d, err := f.DWARF()
  1882  		if err != nil {
  1883  			fatalf("cannot load DWARF output from %s: %v", gccTmp(), err)
  1884  		}
  1885  		bo := binary.BigEndian
  1886  		for _, s := range f.Symbols {
  1887  			switch {
  1888  			case isDebugInts(s.Name):
  1889  				if i := int(s.SectionNumber) - 1; 0 <= i && i < len(f.Sections) {
  1890  					sect := f.Sections[i]
  1891  					if s.Value < sect.Size {
  1892  						if sdat, err := sect.Data(); err == nil {
  1893  							data := sdat[s.Value:]
  1894  							ints = make([]int64, len(data)/8)
  1895  							for i := range ints {
  1896  								ints[i] = int64(bo.Uint64(data[i*8:]))
  1897  							}
  1898  						}
  1899  					}
  1900  				}
  1901  			case isDebugFloats(s.Name):
  1902  				if i := int(s.SectionNumber) - 1; 0 <= i && i < len(f.Sections) {
  1903  					sect := f.Sections[i]
  1904  					if s.Value < sect.Size {
  1905  						if sdat, err := sect.Data(); err == nil {
  1906  							data := sdat[s.Value:]
  1907  							floats = make([]float64, len(data)/8)
  1908  							for i := range floats {
  1909  								floats[i] = math.Float64frombits(bo.Uint64(data[i*8:]))
  1910  							}
  1911  						}
  1912  					}
  1913  				}
  1914  			default:
  1915  				if n := indexOfDebugStr(s.Name); n != -1 {
  1916  					if i := int(s.SectionNumber) - 1; 0 <= i && i < len(f.Sections) {
  1917  						sect := f.Sections[i]
  1918  						if s.Value < sect.Size {
  1919  							if sdat, err := sect.Data(); err == nil {
  1920  								data := sdat[s.Value:]
  1921  								strdata[n] = string(data)
  1922  							}
  1923  						}
  1924  					}
  1925  					break
  1926  				}
  1927  				if n := indexOfDebugStrlen(s.Name); n != -1 {
  1928  					if i := int(s.SectionNumber) - 1; 0 <= i && i < len(f.Sections) {
  1929  						sect := f.Sections[i]
  1930  						if s.Value < sect.Size {
  1931  							if sdat, err := sect.Data(); err == nil {
  1932  								data := sdat[s.Value:]
  1933  								strlen := bo.Uint64(data[:8])
  1934  								if strlen > (1<<(uint(p.IntSize*8)-1) - 1) { // greater than MaxInt?
  1935  									fatalf("string literal too big")
  1936  								}
  1937  								strlens[n] = int(strlen)
  1938  							}
  1939  						}
  1940  					}
  1941  					break
  1942  				}
  1943  			}
  1944  		}
  1945  
  1946  		buildStrings()
  1947  		return d, ints, floats, strs
  1948  	}
  1949  	fatalf("cannot parse gcc output %s as ELF, Mach-O, PE, XCOFF object", gccTmp())
  1950  	panic("not reached")
  1951  }
  1952  
  1953  // gccDefines runs gcc -E -dM -xc - over the C program stdin
  1954  // and returns the corresponding standard output, which is the
  1955  // #defines that gcc encountered while processing the input
  1956  // and its included files.
  1957  func (p *Package) gccDefines(stdin []byte) string {
  1958  	base := append(p.gccBaseCmd(), "-E", "-dM", "-xc")
  1959  	base = append(base, p.gccMachine()...)
  1960  	stdout, _ := runGcc(stdin, append(append(base, p.GccOptions...), "-"))
  1961  	return stdout
  1962  }
  1963  
  1964  // gccErrors runs gcc over the C program stdin and returns
  1965  // the errors that gcc prints. That is, this function expects
  1966  // gcc to fail.
  1967  func (p *Package) gccErrors(stdin []byte) string {
  1968  	// TODO(rsc): require failure
  1969  	args := p.gccCmd()
  1970  
  1971  	// Optimization options can confuse the error messages; remove them.
  1972  	nargs := make([]string, 0, len(args))
  1973  	for _, arg := range args {
  1974  		if !strings.HasPrefix(arg, "-O") {
  1975  			nargs = append(nargs, arg)
  1976  		}
  1977  	}
  1978  
  1979  	// Force -O0 optimization but keep the trailing "-" at the end.
  1980  	nargs = append(nargs, "-O0")
  1981  	nl := len(nargs)
  1982  	nargs[nl-2], nargs[nl-1] = nargs[nl-1], nargs[nl-2]
  1983  
  1984  	if *debugGcc {
  1985  		fmt.Fprintf(os.Stderr, "$ %s <<EOF\n", strings.Join(nargs, " "))
  1986  		os.Stderr.Write(stdin)
  1987  		fmt.Fprint(os.Stderr, "EOF\n")
  1988  	}
  1989  	stdout, stderr, _ := run(stdin, nargs)
  1990  	if *debugGcc {
  1991  		os.Stderr.Write(stdout)
  1992  		os.Stderr.Write(stderr)
  1993  	}
  1994  	return string(stderr)
  1995  }
  1996  
  1997  // runGcc runs the gcc command line args with stdin on standard input.
  1998  // If the command exits with a non-zero exit status, runGcc prints
  1999  // details about what was run and exits.
  2000  // Otherwise runGcc returns the data written to standard output and standard error.
  2001  // Note that for some of the uses we expect useful data back
  2002  // on standard error, but for those uses gcc must still exit 0.
  2003  func runGcc(stdin []byte, args []string) (string, string) {
  2004  	if *debugGcc {
  2005  		fmt.Fprintf(os.Stderr, "$ %s <<EOF\n", strings.Join(args, " "))
  2006  		os.Stderr.Write(stdin)
  2007  		fmt.Fprint(os.Stderr, "EOF\n")
  2008  	}
  2009  	stdout, stderr, ok := run(stdin, args)
  2010  	if *debugGcc {
  2011  		os.Stderr.Write(stdout)
  2012  		os.Stderr.Write(stderr)
  2013  	}
  2014  	if !ok {
  2015  		os.Stderr.Write(stderr)
  2016  		os.Exit(2)
  2017  	}
  2018  	return string(stdout), string(stderr)
  2019  }
  2020  
  2021  // A typeConv is a translator from dwarf types to Go types
  2022  // with equivalent memory layout.
  2023  type typeConv struct {
  2024  	// Cache of already-translated or in-progress types.
  2025  	m map[string]*Type
  2026  
  2027  	// Map from types to incomplete pointers to those types.
  2028  	ptrs map[string][]*Type
  2029  	// Keys of ptrs in insertion order (deterministic worklist)
  2030  	// ptrKeys contains exactly the keys in ptrs.
  2031  	ptrKeys []dwarf.Type
  2032  
  2033  	// Type names X for which there exists an XGetTypeID function with type func() CFTypeID.
  2034  	getTypeIDs map[string]bool
  2035  
  2036  	// Predeclared types.
  2037  	bool                                   ast.Expr
  2038  	byte                                   ast.Expr // denotes padding
  2039  	int8, int16, int32, int64              ast.Expr
  2040  	uint8, uint16, uint32, uint64, uintptr ast.Expr
  2041  	float32, float64                       ast.Expr
  2042  	complex64, complex128                  ast.Expr
  2043  	void                                   ast.Expr
  2044  	string                                 ast.Expr
  2045  	goVoid                                 ast.Expr // _Ctype_void, denotes C's void
  2046  	goVoidPtr                              ast.Expr // unsafe.Pointer or *byte
  2047  
  2048  	ptrSize int64
  2049  	intSize int64
  2050  }
  2051  
  2052  var tagGen int
  2053  var typedef = make(map[string]*Type)
  2054  var goIdent = make(map[string]*ast.Ident)
  2055  
  2056  // unionWithPointer is true for a Go type that represents a C union (or class)
  2057  // that may contain a pointer. This is used for cgo pointer checking.
  2058  var unionWithPointer = make(map[ast.Expr]bool)
  2059  
  2060  func (c *typeConv) Init(ptrSize, intSize int64) {
  2061  	c.ptrSize = ptrSize
  2062  	c.intSize = intSize
  2063  	c.m = make(map[string]*Type)
  2064  	c.ptrs = make(map[string][]*Type)
  2065  	c.getTypeIDs = make(map[string]bool)
  2066  	c.bool = c.Ident("bool")
  2067  	c.byte = c.Ident("byte")
  2068  	c.int8 = c.Ident("int8")
  2069  	c.int16 = c.Ident("int16")
  2070  	c.int32 = c.Ident("int32")
  2071  	c.int64 = c.Ident("int64")
  2072  	c.uint8 = c.Ident("uint8")
  2073  	c.uint16 = c.Ident("uint16")
  2074  	c.uint32 = c.Ident("uint32")
  2075  	c.uint64 = c.Ident("uint64")
  2076  	c.uintptr = c.Ident("uintptr")
  2077  	c.float32 = c.Ident("float32")
  2078  	c.float64 = c.Ident("float64")
  2079  	c.complex64 = c.Ident("complex64")
  2080  	c.complex128 = c.Ident("complex128")
  2081  	c.void = c.Ident("void")
  2082  	c.string = c.Ident("string")
  2083  	c.goVoid = c.Ident("_Ctype_void")
  2084  
  2085  	// Normally cgo translates void* to unsafe.Pointer,
  2086  	// but for historical reasons -godefs uses *byte instead.
  2087  	if *godefs {
  2088  		c.goVoidPtr = &ast.StarExpr{X: c.byte}
  2089  	} else {
  2090  		c.goVoidPtr = c.Ident("unsafe.Pointer")
  2091  	}
  2092  }
  2093  
  2094  // base strips away qualifiers and typedefs to get the underlying type
  2095  func base(dt dwarf.Type) dwarf.Type {
  2096  	for {
  2097  		if d, ok := dt.(*dwarf.QualType); ok {
  2098  			dt = d.Type
  2099  			continue
  2100  		}
  2101  		if d, ok := dt.(*dwarf.TypedefType); ok {
  2102  			dt = d.Type
  2103  			continue
  2104  		}
  2105  		break
  2106  	}
  2107  	return dt
  2108  }
  2109  
  2110  // unqual strips away qualifiers from a DWARF type.
  2111  // In general we don't care about top-level qualifiers.
  2112  func unqual(dt dwarf.Type) dwarf.Type {
  2113  	for {
  2114  		if d, ok := dt.(*dwarf.QualType); ok {
  2115  			dt = d.Type
  2116  		} else {
  2117  			break
  2118  		}
  2119  	}
  2120  	return dt
  2121  }
  2122  
  2123  // Map from dwarf text names to aliases we use in package "C".
  2124  var dwarfToName = map[string]string{
  2125  	"long int":               "long",
  2126  	"long unsigned int":      "ulong",
  2127  	"unsigned int":           "uint",
  2128  	"short unsigned int":     "ushort",
  2129  	"unsigned short":         "ushort", // Used by Clang; issue 13129.
  2130  	"short int":              "short",
  2131  	"long long int":          "longlong",
  2132  	"long long unsigned int": "ulonglong",
  2133  	"signed char":            "schar",
  2134  	"unsigned char":          "uchar",
  2135  }
  2136  
  2137  const signedDelta = 64
  2138  
  2139  // String returns the current type representation. Format arguments
  2140  // are assembled within this method so that any changes in mutable
  2141  // values are taken into account.
  2142  func (tr *TypeRepr) String() string {
  2143  	if len(tr.Repr) == 0 {
  2144  		return ""
  2145  	}
  2146  	if len(tr.FormatArgs) == 0 {
  2147  		return tr.Repr
  2148  	}
  2149  	return fmt.Sprintf(tr.Repr, tr.FormatArgs...)
  2150  }
  2151  
  2152  // Empty reports whether the result of String would be "".
  2153  func (tr *TypeRepr) Empty() bool {
  2154  	return len(tr.Repr) == 0
  2155  }
  2156  
  2157  // Set modifies the type representation.
  2158  // If fargs are provided, repr is used as a format for fmt.Sprintf.
  2159  // Otherwise, repr is used unprocessed as the type representation.
  2160  func (tr *TypeRepr) Set(repr string, fargs ...interface{}) {
  2161  	tr.Repr = repr
  2162  	tr.FormatArgs = fargs
  2163  }
  2164  
  2165  // FinishType completes any outstanding type mapping work.
  2166  // In particular, it resolves incomplete pointer types.
  2167  func (c *typeConv) FinishType(pos token.Pos) {
  2168  	// Completing one pointer type might produce more to complete.
  2169  	// Keep looping until they're all done.
  2170  	for len(c.ptrKeys) > 0 {
  2171  		dtype := c.ptrKeys[0]
  2172  		dtypeKey := dtype.String()
  2173  		c.ptrKeys = c.ptrKeys[1:]
  2174  		ptrs := c.ptrs[dtypeKey]
  2175  		delete(c.ptrs, dtypeKey)
  2176  
  2177  		// Note Type might invalidate c.ptrs[dtypeKey].
  2178  		t := c.Type(dtype, pos)
  2179  		for _, ptr := range ptrs {
  2180  			ptr.Go.(*ast.StarExpr).X = t.Go
  2181  			ptr.C.Set("%s*", t.C)
  2182  		}
  2183  	}
  2184  }
  2185  
  2186  // Type returns a *Type with the same memory layout as
  2187  // dtype when used as the type of a variable or a struct field.
  2188  func (c *typeConv) Type(dtype dwarf.Type, pos token.Pos) *Type {
  2189  	// Always recompute bad pointer typedefs, as the set of such
  2190  	// typedefs changes as we see more types.
  2191  	checkCache := true
  2192  	if dtt, ok := dtype.(*dwarf.TypedefType); ok && c.badPointerTypedef(dtt) {
  2193  		checkCache = false
  2194  	}
  2195  
  2196  	key := dtype.String()
  2197  
  2198  	if checkCache {
  2199  		if t, ok := c.m[key]; ok {
  2200  			if t.Go == nil {
  2201  				fatalf("%s: type conversion loop at %s", lineno(pos), dtype)
  2202  			}
  2203  			return t
  2204  		}
  2205  	}
  2206  
  2207  	t := new(Type)
  2208  	t.Size = dtype.Size() // note: wrong for array of pointers, corrected below
  2209  	t.Align = -1
  2210  	t.C = &TypeRepr{Repr: dtype.Common().Name}
  2211  	c.m[key] = t
  2212  
  2213  	switch dt := dtype.(type) {
  2214  	default:
  2215  		fatalf("%s: unexpected type: %s", lineno(pos), dtype)
  2216  
  2217  	case *dwarf.AddrType:
  2218  		if t.Size != c.ptrSize {
  2219  			fatalf("%s: unexpected: %d-byte address type - %s", lineno(pos), t.Size, dtype)
  2220  		}
  2221  		t.Go = c.uintptr
  2222  		t.Align = t.Size
  2223  
  2224  	case *dwarf.ArrayType:
  2225  		if dt.StrideBitSize > 0 {
  2226  			// Cannot represent bit-sized elements in Go.
  2227  			t.Go = c.Opaque(t.Size)
  2228  			break
  2229  		}
  2230  		count := dt.Count
  2231  		if count == -1 {
  2232  			// Indicates flexible array member, which Go doesn't support.
  2233  			// Translate to zero-length array instead.
  2234  			count = 0
  2235  		}
  2236  		sub := c.Type(dt.Type, pos)
  2237  		t.Align = sub.Align
  2238  		t.Go = &ast.ArrayType{
  2239  			Len: c.intExpr(count),
  2240  			Elt: sub.Go,
  2241  		}
  2242  		// Recalculate t.Size now that we know sub.Size.
  2243  		t.Size = count * sub.Size
  2244  		t.C.Set("__typeof__(%s[%d])", sub.C, dt.Count)
  2245  
  2246  	case *dwarf.BoolType:
  2247  		t.Go = c.bool
  2248  		t.Align = 1
  2249  
  2250  	case *dwarf.CharType:
  2251  		if t.Size != 1 {
  2252  			fatalf("%s: unexpected: %d-byte char type - %s", lineno(pos), t.Size, dtype)
  2253  		}
  2254  		t.Go = c.int8
  2255  		t.Align = 1
  2256  
  2257  	case *dwarf.EnumType:
  2258  		if t.Align = t.Size; t.Align >= c.ptrSize {
  2259  			t.Align = c.ptrSize
  2260  		}
  2261  		t.C.Set("enum " + dt.EnumName)
  2262  		signed := 0
  2263  		t.EnumValues = make(map[string]int64)
  2264  		for _, ev := range dt.Val {
  2265  			t.EnumValues[ev.Name] = ev.Val
  2266  			if ev.Val < 0 {
  2267  				signed = signedDelta
  2268  			}
  2269  		}
  2270  		switch t.Size + int64(signed) {
  2271  		default:
  2272  			fatalf("%s: unexpected: %d-byte enum type - %s", lineno(pos), t.Size, dtype)
  2273  		case 1:
  2274  			t.Go = c.uint8
  2275  		case 2:
  2276  			t.Go = c.uint16
  2277  		case 4:
  2278  			t.Go = c.uint32
  2279  		case 8:
  2280  			t.Go = c.uint64
  2281  		case 1 + signedDelta:
  2282  			t.Go = c.int8
  2283  		case 2 + signedDelta:
  2284  			t.Go = c.int16
  2285  		case 4 + signedDelta:
  2286  			t.Go = c.int32
  2287  		case 8 + signedDelta:
  2288  			t.Go = c.int64
  2289  		}
  2290  
  2291  	case *dwarf.FloatType:
  2292  		switch t.Size {
  2293  		default:
  2294  			fatalf("%s: unexpected: %d-byte float type - %s", lineno(pos), t.Size, dtype)
  2295  		case 4:
  2296  			t.Go = c.float32
  2297  		case 8:
  2298  			t.Go = c.float64
  2299  		}
  2300  		if t.Align = t.Size; t.Align >= c.ptrSize {
  2301  			t.Align = c.ptrSize
  2302  		}
  2303  
  2304  	case *dwarf.ComplexType:
  2305  		switch t.Size {
  2306  		default:
  2307  			fatalf("%s: unexpected: %d-byte complex type - %s", lineno(pos), t.Size, dtype)
  2308  		case 8:
  2309  			t.Go = c.complex64
  2310  		case 16:
  2311  			t.Go = c.complex128
  2312  		}
  2313  		if t.Align = t.Size / 2; t.Align >= c.ptrSize {
  2314  			t.Align = c.ptrSize
  2315  		}
  2316  
  2317  	case *dwarf.FuncType:
  2318  		// No attempt at translation: would enable calls
  2319  		// directly between worlds, but we need to moderate those.
  2320  		t.Go = c.uintptr
  2321  		t.Align = c.ptrSize
  2322  
  2323  	case *dwarf.IntType:
  2324  		if dt.BitSize > 0 {
  2325  			fatalf("%s: unexpected: %d-bit int type - %s", lineno(pos), dt.BitSize, dtype)
  2326  		}
  2327  		switch t.Size {
  2328  		default:
  2329  			fatalf("%s: unexpected: %d-byte int type - %s", lineno(pos), t.Size, dtype)
  2330  		case 1:
  2331  			t.Go = c.int8
  2332  		case 2:
  2333  			t.Go = c.int16
  2334  		case 4:
  2335  			t.Go = c.int32
  2336  		case 8:
  2337  			t.Go = c.int64
  2338  		case 16:
  2339  			t.Go = &ast.ArrayType{
  2340  				Len: c.intExpr(t.Size),
  2341  				Elt: c.uint8,
  2342  			}
  2343  		}
  2344  		if t.Align = t.Size; t.Align >= c.ptrSize {
  2345  			t.Align = c.ptrSize
  2346  		}
  2347  
  2348  	case *dwarf.PtrType:
  2349  		// Clang doesn't emit DW_AT_byte_size for pointer types.
  2350  		if t.Size != c.ptrSize && t.Size != -1 {
  2351  			fatalf("%s: unexpected: %d-byte pointer type - %s", lineno(pos), t.Size, dtype)
  2352  		}
  2353  		t.Size = c.ptrSize
  2354  		t.Align = c.ptrSize
  2355  
  2356  		if _, ok := base(dt.Type).(*dwarf.VoidType); ok {
  2357  			t.Go = c.goVoidPtr
  2358  			t.C.Set("void*")
  2359  			dq := dt.Type
  2360  			for {
  2361  				if d, ok := dq.(*dwarf.QualType); ok {
  2362  					t.C.Set(d.Qual + " " + t.C.String())
  2363  					dq = d.Type
  2364  				} else {
  2365  					break
  2366  				}
  2367  			}
  2368  			break
  2369  		}
  2370  
  2371  		// Placeholder initialization; completed in FinishType.
  2372  		t.Go = &ast.StarExpr{}
  2373  		t.C.Set("<incomplete>*")
  2374  		key := dt.Type.String()
  2375  		if _, ok := c.ptrs[key]; !ok {
  2376  			c.ptrKeys = append(c.ptrKeys, dt.Type)
  2377  		}
  2378  		c.ptrs[key] = append(c.ptrs[key], t)
  2379  
  2380  	case *dwarf.QualType:
  2381  		t1 := c.Type(dt.Type, pos)
  2382  		t.Size = t1.Size
  2383  		t.Align = t1.Align
  2384  		t.Go = t1.Go
  2385  		if unionWithPointer[t1.Go] {
  2386  			unionWithPointer[t.Go] = true
  2387  		}
  2388  		t.EnumValues = nil
  2389  		t.Typedef = ""
  2390  		t.C.Set("%s "+dt.Qual, t1.C)
  2391  		return t
  2392  
  2393  	case *dwarf.StructType:
  2394  		// Convert to Go struct, being careful about alignment.
  2395  		// Have to give it a name to simulate C "struct foo" references.
  2396  		tag := dt.StructName
  2397  		if dt.ByteSize < 0 && tag == "" { // opaque unnamed struct - should not be possible
  2398  			break
  2399  		}
  2400  		if tag == "" {
  2401  			tag = "__" + strconv.Itoa(tagGen)
  2402  			tagGen++
  2403  		} else if t.C.Empty() {
  2404  			t.C.Set(dt.Kind + " " + tag)
  2405  		}
  2406  		name := c.Ident("_Ctype_" + dt.Kind + "_" + tag)
  2407  		t.Go = name // publish before recursive calls
  2408  		goIdent[name.Name] = name
  2409  		if dt.ByteSize < 0 {
  2410  			// Size calculation in c.Struct/c.Opaque will die with size=-1 (unknown),
  2411  			// so execute the basic things that the struct case would do
  2412  			// other than try to determine a Go representation.
  2413  			tt := *t
  2414  			tt.C = &TypeRepr{"%s %s", []interface{}{dt.Kind, tag}}
  2415  			tt.Go = c.Ident("struct{}")
  2416  			typedef[name.Name] = &tt
  2417  			break
  2418  		}
  2419  		switch dt.Kind {
  2420  		case "class", "union":
  2421  			t.Go = c.Opaque(t.Size)
  2422  			if c.dwarfHasPointer(dt, pos) {
  2423  				unionWithPointer[t.Go] = true
  2424  			}
  2425  			if t.C.Empty() {
  2426  				t.C.Set("__typeof__(unsigned char[%d])", t.Size)
  2427  			}
  2428  			t.Align = 1 // TODO: should probably base this on field alignment.
  2429  			typedef[name.Name] = t
  2430  		case "struct":
  2431  			g, csyntax, align := c.Struct(dt, pos)
  2432  			if t.C.Empty() {
  2433  				t.C.Set(csyntax)
  2434  			}
  2435  			t.Align = align
  2436  			tt := *t
  2437  			if tag != "" {
  2438  				tt.C = &TypeRepr{"struct %s", []interface{}{tag}}
  2439  			}
  2440  			tt.Go = g
  2441  			typedef[name.Name] = &tt
  2442  		}
  2443  
  2444  	case *dwarf.TypedefType:
  2445  		// Record typedef for printing.
  2446  		if dt.Name == "_GoString_" {
  2447  			// Special C name for Go string type.
  2448  			// Knows string layout used by compilers: pointer plus length,
  2449  			// which rounds up to 2 pointers after alignment.
  2450  			t.Go = c.string
  2451  			t.Size = c.ptrSize * 2
  2452  			t.Align = c.ptrSize
  2453  			break
  2454  		}
  2455  		if dt.Name == "_GoBytes_" {
  2456  			// Special C name for Go []byte type.
  2457  			// Knows slice layout used by compilers: pointer, length, cap.
  2458  			t.Go = c.Ident("[]byte")
  2459  			t.Size = c.ptrSize + 4 + 4
  2460  			t.Align = c.ptrSize
  2461  			break
  2462  		}
  2463  		name := c.Ident("_Ctype_" + dt.Name)
  2464  		goIdent[name.Name] = name
  2465  		sub := c.Type(dt.Type, pos)
  2466  		if c.badPointerTypedef(dt) {
  2467  			// Treat this typedef as a uintptr.
  2468  			s := *sub
  2469  			s.Go = c.uintptr
  2470  			s.BadPointer = true
  2471  			sub = &s
  2472  			// Make sure we update any previously computed type.
  2473  			if oldType := typedef[name.Name]; oldType != nil {
  2474  				oldType.Go = sub.Go
  2475  				oldType.BadPointer = true
  2476  			}
  2477  		}
  2478  		t.Go = name
  2479  		t.BadPointer = sub.BadPointer
  2480  		if unionWithPointer[sub.Go] {
  2481  			unionWithPointer[t.Go] = true
  2482  		}
  2483  		t.Size = sub.Size
  2484  		t.Align = sub.Align
  2485  		oldType := typedef[name.Name]
  2486  		if oldType == nil {
  2487  			tt := *t
  2488  			tt.Go = sub.Go
  2489  			tt.BadPointer = sub.BadPointer
  2490  			typedef[name.Name] = &tt
  2491  		}
  2492  
  2493  		// If sub.Go.Name is "_Ctype_struct_foo" or "_Ctype_union_foo" or "_Ctype_class_foo",
  2494  		// use that as the Go form for this typedef too, so that the typedef will be interchangeable
  2495  		// with the base type.
  2496  		// In -godefs mode, do this for all typedefs.
  2497  		if isStructUnionClass(sub.Go) || *godefs {
  2498  			t.Go = sub.Go
  2499  
  2500  			if isStructUnionClass(sub.Go) {
  2501  				// Use the typedef name for C code.
  2502  				typedef[sub.Go.(*ast.Ident).Name].C = t.C
  2503  			}
  2504  
  2505  			// If we've seen this typedef before, and it
  2506  			// was an anonymous struct/union/class before
  2507  			// too, use the old definition.
  2508  			// TODO: it would be safer to only do this if
  2509  			// we verify that the types are the same.
  2510  			if oldType != nil && isStructUnionClass(oldType.Go) {
  2511  				t.Go = oldType.Go
  2512  			}
  2513  		}
  2514  
  2515  	case *dwarf.UcharType:
  2516  		if t.Size != 1 {
  2517  			fatalf("%s: unexpected: %d-byte uchar type - %s", lineno(pos), t.Size, dtype)
  2518  		}
  2519  		t.Go = c.uint8
  2520  		t.Align = 1
  2521  
  2522  	case *dwarf.UintType:
  2523  		if dt.BitSize > 0 {
  2524  			fatalf("%s: unexpected: %d-bit uint type - %s", lineno(pos), dt.BitSize, dtype)
  2525  		}
  2526  		switch t.Size {
  2527  		default:
  2528  			fatalf("%s: unexpected: %d-byte uint type - %s", lineno(pos), t.Size, dtype)
  2529  		case 1:
  2530  			t.Go = c.uint8
  2531  		case 2:
  2532  			t.Go = c.uint16
  2533  		case 4:
  2534  			t.Go = c.uint32
  2535  		case 8:
  2536  			t.Go = c.uint64
  2537  		case 16:
  2538  			t.Go = &ast.ArrayType{
  2539  				Len: c.intExpr(t.Size),
  2540  				Elt: c.uint8,
  2541  			}
  2542  		}
  2543  		if t.Align = t.Size; t.Align >= c.ptrSize {
  2544  			t.Align = c.ptrSize
  2545  		}
  2546  
  2547  	case *dwarf.VoidType:
  2548  		t.Go = c.goVoid
  2549  		t.C.Set("void")
  2550  		t.Align = 1
  2551  	}
  2552  
  2553  	switch dtype.(type) {
  2554  	case *dwarf.AddrType, *dwarf.BoolType, *dwarf.CharType, *dwarf.ComplexType, *dwarf.IntType, *dwarf.FloatType, *dwarf.UcharType, *dwarf.UintType:
  2555  		s := dtype.Common().Name
  2556  		if s != "" {
  2557  			if ss, ok := dwarfToName[s]; ok {
  2558  				s = ss
  2559  			}
  2560  			s = strings.Replace(s, " ", "", -1)
  2561  			name := c.Ident("_Ctype_" + s)
  2562  			tt := *t
  2563  			typedef[name.Name] = &tt
  2564  			if !*godefs {
  2565  				t.Go = name
  2566  			}
  2567  		}
  2568  	}
  2569  
  2570  	if t.Size < 0 {
  2571  		// Unsized types are [0]byte, unless they're typedefs of other types
  2572  		// or structs with tags.
  2573  		// if so, use the name we've already defined.
  2574  		t.Size = 0
  2575  		switch dt := dtype.(type) {
  2576  		case *dwarf.TypedefType:
  2577  			// ok
  2578  		case *dwarf.StructType:
  2579  			if dt.StructName != "" {
  2580  				break
  2581  			}
  2582  			t.Go = c.Opaque(0)
  2583  		default:
  2584  			t.Go = c.Opaque(0)
  2585  		}
  2586  		if t.C.Empty() {
  2587  			t.C.Set("void")
  2588  		}
  2589  	}
  2590  
  2591  	if t.C.Empty() {
  2592  		fatalf("%s: internal error: did not create C name for %s", lineno(pos), dtype)
  2593  	}
  2594  
  2595  	return t
  2596  }
  2597  
  2598  // isStructUnionClass reports whether the type described by the Go syntax x
  2599  // is a struct, union, or class with a tag.
  2600  func isStructUnionClass(x ast.Expr) bool {
  2601  	id, ok := x.(*ast.Ident)
  2602  	if !ok {
  2603  		return false
  2604  	}
  2605  	name := id.Name
  2606  	return strings.HasPrefix(name, "_Ctype_struct_") ||
  2607  		strings.HasPrefix(name, "_Ctype_union_") ||
  2608  		strings.HasPrefix(name, "_Ctype_class_")
  2609  }
  2610  
  2611  // FuncArg returns a Go type with the same memory layout as
  2612  // dtype when used as the type of a C function argument.
  2613  func (c *typeConv) FuncArg(dtype dwarf.Type, pos token.Pos) *Type {
  2614  	t := c.Type(unqual(dtype), pos)
  2615  	switch dt := dtype.(type) {
  2616  	case *dwarf.ArrayType:
  2617  		// Arrays are passed implicitly as pointers in C.
  2618  		// In Go, we must be explicit.
  2619  		tr := &TypeRepr{}
  2620  		tr.Set("%s*", t.C)
  2621  		return &Type{
  2622  			Size:  c.ptrSize,
  2623  			Align: c.ptrSize,
  2624  			Go:    &ast.StarExpr{X: t.Go},
  2625  			C:     tr,
  2626  		}
  2627  	case *dwarf.TypedefType:
  2628  		// C has much more relaxed rules than Go for
  2629  		// implicit type conversions. When the parameter
  2630  		// is type T defined as *X, simulate a little of the
  2631  		// laxness of C by making the argument *X instead of T.
  2632  		if ptr, ok := base(dt.Type).(*dwarf.PtrType); ok {
  2633  			// Unless the typedef happens to point to void* since
  2634  			// Go has special rules around using unsafe.Pointer.
  2635  			if _, void := base(ptr.Type).(*dwarf.VoidType); void {
  2636  				break
  2637  			}
  2638  			// ...or the typedef is one in which we expect bad pointers.
  2639  			// It will be a uintptr instead of *X.
  2640  			if c.baseBadPointerTypedef(dt) {
  2641  				break
  2642  			}
  2643  
  2644  			t = c.Type(ptr, pos)
  2645  			if t == nil {
  2646  				return nil
  2647  			}
  2648  
  2649  			// For a struct/union/class, remember the C spelling,
  2650  			// in case it has __attribute__((unavailable)).
  2651  			// See issue 2888.
  2652  			if isStructUnionClass(t.Go) {
  2653  				t.Typedef = dt.Name
  2654  			}
  2655  		}
  2656  	}
  2657  	return t
  2658  }
  2659  
  2660  // FuncType returns the Go type analogous to dtype.
  2661  // There is no guarantee about matching memory layout.
  2662  func (c *typeConv) FuncType(dtype *dwarf.FuncType, pos token.Pos) *FuncType {
  2663  	p := make([]*Type, len(dtype.ParamType))
  2664  	gp := make([]*ast.Field, len(dtype.ParamType))
  2665  	for i, f := range dtype.ParamType {
  2666  		// gcc's DWARF generator outputs a single DotDotDotType parameter for
  2667  		// function pointers that specify no parameters (e.g. void
  2668  		// (*__cgo_0)()).  Treat this special case as void. This case is
  2669  		// invalid according to ISO C anyway (i.e. void (*__cgo_1)(...) is not
  2670  		// legal).
  2671  		if _, ok := f.(*dwarf.DotDotDotType); ok && i == 0 {
  2672  			p, gp = nil, nil
  2673  			break
  2674  		}
  2675  		p[i] = c.FuncArg(f, pos)
  2676  		gp[i] = &ast.Field{Type: p[i].Go}
  2677  	}
  2678  	var r *Type
  2679  	var gr []*ast.Field
  2680  	if _, ok := base(dtype.ReturnType).(*dwarf.VoidType); ok {
  2681  		gr = []*ast.Field{{Type: c.goVoid}}
  2682  	} else if dtype.ReturnType != nil {
  2683  		r = c.Type(unqual(dtype.ReturnType), pos)
  2684  		gr = []*ast.Field{{Type: r.Go}}
  2685  	}
  2686  	return &FuncType{
  2687  		Params: p,
  2688  		Result: r,
  2689  		Go: &ast.FuncType{
  2690  			Params:  &ast.FieldList{List: gp},
  2691  			Results: &ast.FieldList{List: gr},
  2692  		},
  2693  	}
  2694  }
  2695  
  2696  // Identifier
  2697  func (c *typeConv) Ident(s string) *ast.Ident {
  2698  	return ast.NewIdent(s)
  2699  }
  2700  
  2701  // Opaque type of n bytes.
  2702  func (c *typeConv) Opaque(n int64) ast.Expr {
  2703  	return &ast.ArrayType{
  2704  		Len: c.intExpr(n),
  2705  		Elt: c.byte,
  2706  	}
  2707  }
  2708  
  2709  // Expr for integer n.
  2710  func (c *typeConv) intExpr(n int64) ast.Expr {
  2711  	return &ast.BasicLit{
  2712  		Kind:  token.INT,
  2713  		Value: strconv.FormatInt(n, 10),
  2714  	}
  2715  }
  2716  
  2717  // Add padding of given size to fld.
  2718  func (c *typeConv) pad(fld []*ast.Field, sizes []int64, size int64) ([]*ast.Field, []int64) {
  2719  	n := len(fld)
  2720  	fld = fld[0 : n+1]
  2721  	fld[n] = &ast.Field{Names: []*ast.Ident{c.Ident("_")}, Type: c.Opaque(size)}
  2722  	sizes = sizes[0 : n+1]
  2723  	sizes[n] = size
  2724  	return fld, sizes
  2725  }
  2726  
  2727  // Struct conversion: return Go and (gc) C syntax for type.
  2728  func (c *typeConv) Struct(dt *dwarf.StructType, pos token.Pos) (expr *ast.StructType, csyntax string, align int64) {
  2729  	// Minimum alignment for a struct is 1 byte.
  2730  	align = 1
  2731  
  2732  	var buf bytes.Buffer
  2733  	buf.WriteString("struct {")
  2734  	fld := make([]*ast.Field, 0, 2*len(dt.Field)+1) // enough for padding around every field
  2735  	sizes := make([]int64, 0, 2*len(dt.Field)+1)
  2736  	off := int64(0)
  2737  
  2738  	// Rename struct fields that happen to be named Go keywords into
  2739  	// _{keyword}.  Create a map from C ident -> Go ident. The Go ident will
  2740  	// be mangled. Any existing identifier that already has the same name on
  2741  	// the C-side will cause the Go-mangled version to be prefixed with _.
  2742  	// (e.g. in a struct with fields '_type' and 'type', the latter would be
  2743  	// rendered as '__type' in Go).
  2744  	ident := make(map[string]string)
  2745  	used := make(map[string]bool)
  2746  	for _, f := range dt.Field {
  2747  		ident[f.Name] = f.Name
  2748  		used[f.Name] = true
  2749  	}
  2750  
  2751  	if !*godefs {
  2752  		for cid, goid := range ident {
  2753  			if token.Lookup(goid).IsKeyword() {
  2754  				// Avoid keyword
  2755  				goid = "_" + goid
  2756  
  2757  				// Also avoid existing fields
  2758  				for _, exist := used[goid]; exist; _, exist = used[goid] {
  2759  					goid = "_" + goid
  2760  				}
  2761  
  2762  				used[goid] = true
  2763  				ident[cid] = goid
  2764  			}
  2765  		}
  2766  	}
  2767  
  2768  	anon := 0
  2769  	for _, f := range dt.Field {
  2770  		name := f.Name
  2771  		ft := f.Type
  2772  
  2773  		// In godefs mode, if this field is a C11
  2774  		// anonymous union then treat the first field in the
  2775  		// union as the field in the struct. This handles
  2776  		// cases like the glibc <sys/resource.h> file; see
  2777  		// issue 6677.
  2778  		if *godefs {
  2779  			if st, ok := f.Type.(*dwarf.StructType); ok && name == "" && st.Kind == "union" && len(st.Field) > 0 && !used[st.Field[0].Name] {
  2780  				name = st.Field[0].Name
  2781  				ident[name] = name
  2782  				ft = st.Field[0].Type
  2783  			}
  2784  		}
  2785  
  2786  		// TODO: Handle fields that are anonymous structs by
  2787  		// promoting the fields of the inner struct.
  2788  
  2789  		t := c.Type(ft, pos)
  2790  		tgo := t.Go
  2791  		size := t.Size
  2792  		talign := t.Align
  2793  		if f.BitSize > 0 {
  2794  			switch f.BitSize {
  2795  			case 8, 16, 32, 64:
  2796  			default:
  2797  				continue
  2798  			}
  2799  			size = f.BitSize / 8
  2800  			name := tgo.(*ast.Ident).String()
  2801  			if strings.HasPrefix(name, "int") {
  2802  				name = "int"
  2803  			} else {
  2804  				name = "uint"
  2805  			}
  2806  			tgo = ast.NewIdent(name + fmt.Sprint(f.BitSize))
  2807  			talign = size
  2808  		}
  2809  
  2810  		if talign > 0 && f.ByteOffset%talign != 0 {
  2811  			// Drop misaligned fields, the same way we drop integer bit fields.
  2812  			// The goal is to make available what can be made available.
  2813  			// Otherwise one bad and unneeded field in an otherwise okay struct
  2814  			// makes the whole program not compile. Much of the time these
  2815  			// structs are in system headers that cannot be corrected.
  2816  			continue
  2817  		}
  2818  
  2819  		// Round off up to talign, assumed to be a power of 2.
  2820  		off = (off + talign - 1) &^ (talign - 1)
  2821  
  2822  		if f.ByteOffset > off {
  2823  			fld, sizes = c.pad(fld, sizes, f.ByteOffset-off)
  2824  			off = f.ByteOffset
  2825  		}
  2826  		if f.ByteOffset < off {
  2827  			// Drop a packed field that we can't represent.
  2828  			continue
  2829  		}
  2830  
  2831  		n := len(fld)
  2832  		fld = fld[0 : n+1]
  2833  		if name == "" {
  2834  			name = fmt.Sprintf("anon%d", anon)
  2835  			anon++
  2836  			ident[name] = name
  2837  		}
  2838  		fld[n] = &ast.Field{Names: []*ast.Ident{c.Ident(ident[name])}, Type: tgo}
  2839  		sizes = sizes[0 : n+1]
  2840  		sizes[n] = size
  2841  		off += size
  2842  		buf.WriteString(t.C.String())
  2843  		buf.WriteString(" ")
  2844  		buf.WriteString(name)
  2845  		buf.WriteString("; ")
  2846  		if talign > align {
  2847  			align = talign
  2848  		}
  2849  	}
  2850  	if off < dt.ByteSize {
  2851  		fld, sizes = c.pad(fld, sizes, dt.ByteSize-off)
  2852  		off = dt.ByteSize
  2853  	}
  2854  
  2855  	// If the last field in a non-zero-sized struct is zero-sized
  2856  	// the compiler is going to pad it by one (see issue 9401).
  2857  	// We can't permit that, because then the size of the Go
  2858  	// struct will not be the same as the size of the C struct.
  2859  	// Our only option in such a case is to remove the field,
  2860  	// which means that it cannot be referenced from Go.
  2861  	for off > 0 && sizes[len(sizes)-1] == 0 {
  2862  		n := len(sizes)
  2863  		fld = fld[0 : n-1]
  2864  		sizes = sizes[0 : n-1]
  2865  	}
  2866  
  2867  	if off != dt.ByteSize {
  2868  		fatalf("%s: struct size calculation error off=%d bytesize=%d", lineno(pos), off, dt.ByteSize)
  2869  	}
  2870  	buf.WriteString("}")
  2871  	csyntax = buf.String()
  2872  
  2873  	if *godefs {
  2874  		godefsFields(fld)
  2875  	}
  2876  	expr = &ast.StructType{Fields: &ast.FieldList{List: fld}}
  2877  	return
  2878  }
  2879  
  2880  // dwarfHasPointer reports whether the DWARF type dt contains a pointer.
  2881  func (c *typeConv) dwarfHasPointer(dt dwarf.Type, pos token.Pos) bool {
  2882  	switch dt := dt.(type) {
  2883  	default:
  2884  		fatalf("%s: unexpected type: %s", lineno(pos), dt)
  2885  		return false
  2886  
  2887  	case *dwarf.AddrType, *dwarf.BoolType, *dwarf.CharType, *dwarf.EnumType,
  2888  		*dwarf.FloatType, *dwarf.ComplexType, *dwarf.FuncType,
  2889  		*dwarf.IntType, *dwarf.UcharType, *dwarf.UintType, *dwarf.VoidType:
  2890  
  2891  		return false
  2892  
  2893  	case *dwarf.ArrayType:
  2894  		return c.dwarfHasPointer(dt.Type, pos)
  2895  
  2896  	case *dwarf.PtrType:
  2897  		return true
  2898  
  2899  	case *dwarf.QualType:
  2900  		return c.dwarfHasPointer(dt.Type, pos)
  2901  
  2902  	case *dwarf.StructType:
  2903  		for _, f := range dt.Field {
  2904  			if c.dwarfHasPointer(f.Type, pos) {
  2905  				return true
  2906  			}
  2907  		}
  2908  		return false
  2909  
  2910  	case *dwarf.TypedefType:
  2911  		if dt.Name == "_GoString_" || dt.Name == "_GoBytes_" {
  2912  			return true
  2913  		}
  2914  		return c.dwarfHasPointer(dt.Type, pos)
  2915  	}
  2916  }
  2917  
  2918  func upper(s string) string {
  2919  	if s == "" {
  2920  		return ""
  2921  	}
  2922  	r, size := utf8.DecodeRuneInString(s)
  2923  	if r == '_' {
  2924  		return "X" + s
  2925  	}
  2926  	return string(unicode.ToUpper(r)) + s[size:]
  2927  }
  2928  
  2929  // godefsFields rewrites field names for use in Go or C definitions.
  2930  // It strips leading common prefixes (like tv_ in tv_sec, tv_usec)
  2931  // converts names to upper case, and rewrites _ into Pad_godefs_n,
  2932  // so that all fields are exported.
  2933  func godefsFields(fld []*ast.Field) {
  2934  	prefix := fieldPrefix(fld)
  2935  	npad := 0
  2936  	for _, f := range fld {
  2937  		for _, n := range f.Names {
  2938  			if n.Name != prefix {
  2939  				n.Name = strings.TrimPrefix(n.Name, prefix)
  2940  			}
  2941  			if n.Name == "_" {
  2942  				// Use exported name instead.
  2943  				n.Name = "Pad_cgo_" + strconv.Itoa(npad)
  2944  				npad++
  2945  			}
  2946  			n.Name = upper(n.Name)
  2947  		}
  2948  	}
  2949  }
  2950  
  2951  // fieldPrefix returns the prefix that should be removed from all the
  2952  // field names when generating the C or Go code. For generated
  2953  // C, we leave the names as is (tv_sec, tv_usec), since that's what
  2954  // people are used to seeing in C.  For generated Go code, such as
  2955  // package syscall's data structures, we drop a common prefix
  2956  // (so sec, usec, which will get turned into Sec, Usec for exporting).
  2957  func fieldPrefix(fld []*ast.Field) string {
  2958  	prefix := ""
  2959  	for _, f := range fld {
  2960  		for _, n := range f.Names {
  2961  			// Ignore field names that don't have the prefix we're
  2962  			// looking for. It is common in C headers to have fields
  2963  			// named, say, _pad in an otherwise prefixed header.
  2964  			// If the struct has 3 fields tv_sec, tv_usec, _pad1, then we
  2965  			// still want to remove the tv_ prefix.
  2966  			// The check for "orig_" here handles orig_eax in the
  2967  			// x86 ptrace register sets, which otherwise have all fields
  2968  			// with reg_ prefixes.
  2969  			if strings.HasPrefix(n.Name, "orig_") || strings.HasPrefix(n.Name, "_") {
  2970  				continue
  2971  			}
  2972  			i := strings.Index(n.Name, "_")
  2973  			if i < 0 {
  2974  				continue
  2975  			}
  2976  			if prefix == "" {
  2977  				prefix = n.Name[:i+1]
  2978  			} else if prefix != n.Name[:i+1] {
  2979  				return ""
  2980  			}
  2981  		}
  2982  	}
  2983  	return prefix
  2984  }
  2985  
  2986  // badPointerTypedef reports whether t is a C typedef that should not be considered a pointer in Go.
  2987  // A typedef is bad if C code sometimes stores non-pointers in this type.
  2988  // TODO: Currently our best solution is to find these manually and list them as
  2989  // they come up. A better solution is desired.
  2990  func (c *typeConv) badPointerTypedef(dt *dwarf.TypedefType) bool {
  2991  	if c.badCFType(dt) {
  2992  		return true
  2993  	}
  2994  	if c.badJNI(dt) {
  2995  		return true
  2996  	}
  2997  	if c.badEGLDisplay(dt) {
  2998  		return true
  2999  	}
  3000  	return false
  3001  }
  3002  
  3003  // baseBadPointerTypedef reports whether the base of a chain of typedefs is a bad typedef
  3004  // as badPointerTypedef reports.
  3005  func (c *typeConv) baseBadPointerTypedef(dt *dwarf.TypedefType) bool {
  3006  	for {
  3007  		if t, ok := dt.Type.(*dwarf.TypedefType); ok {
  3008  			dt = t
  3009  			continue
  3010  		}
  3011  		break
  3012  	}
  3013  	return c.badPointerTypedef(dt)
  3014  }
  3015  
  3016  func (c *typeConv) badCFType(dt *dwarf.TypedefType) bool {
  3017  	// The real bad types are CFNumberRef and CFDateRef.
  3018  	// Sometimes non-pointers are stored in these types.
  3019  	// CFTypeRef is a supertype of those, so it can have bad pointers in it as well.
  3020  	// We return true for the other *Ref types just so casting between them is easier.
  3021  	// We identify the correct set of types as those ending in Ref and for which
  3022  	// there exists a corresponding GetTypeID function.
  3023  	// See comment below for details about the bad pointers.
  3024  	if goos != "darwin" {
  3025  		return false
  3026  	}
  3027  	s := dt.Name
  3028  	if !strings.HasSuffix(s, "Ref") {
  3029  		return false
  3030  	}
  3031  	s = s[:len(s)-3]
  3032  	if s == "CFType" {
  3033  		return true
  3034  	}
  3035  	if c.getTypeIDs[s] {
  3036  		return true
  3037  	}
  3038  	if i := strings.Index(s, "Mutable"); i >= 0 && c.getTypeIDs[s[:i]+s[i+7:]] {
  3039  		// Mutable and immutable variants share a type ID.
  3040  		return true
  3041  	}
  3042  	return false
  3043  }
  3044  
  3045  // Comment from Darwin's CFInternal.h
  3046  /*
  3047  // Tagged pointer support
  3048  // Low-bit set means tagged object, next 3 bits (currently)
  3049  // define the tagged object class, next 4 bits are for type
  3050  // information for the specific tagged object class.  Thus,
  3051  // the low byte is for type info, and the rest of a pointer
  3052  // (32 or 64-bit) is for payload, whatever the tagged class.
  3053  //
  3054  // Note that the specific integers used to identify the
  3055  // specific tagged classes can and will change from release
  3056  // to release (that's why this stuff is in CF*Internal*.h),
  3057  // as can the definition of type info vs payload above.
  3058  //
  3059  #if __LP64__
  3060  #define CF_IS_TAGGED_OBJ(PTR)	((uintptr_t)(PTR) & 0x1)
  3061  #define CF_TAGGED_OBJ_TYPE(PTR)	((uintptr_t)(PTR) & 0xF)
  3062  #else
  3063  #define CF_IS_TAGGED_OBJ(PTR)	0
  3064  #define CF_TAGGED_OBJ_TYPE(PTR)	0
  3065  #endif
  3066  
  3067  enum {
  3068      kCFTaggedObjectID_Invalid = 0,
  3069      kCFTaggedObjectID_Atom = (0 << 1) + 1,
  3070      kCFTaggedObjectID_Undefined3 = (1 << 1) + 1,
  3071      kCFTaggedObjectID_Undefined2 = (2 << 1) + 1,
  3072      kCFTaggedObjectID_Integer = (3 << 1) + 1,
  3073      kCFTaggedObjectID_DateTS = (4 << 1) + 1,
  3074      kCFTaggedObjectID_ManagedObjectID = (5 << 1) + 1, // Core Data
  3075      kCFTaggedObjectID_Date = (6 << 1) + 1,
  3076      kCFTaggedObjectID_Undefined7 = (7 << 1) + 1,
  3077  };
  3078  */
  3079  
  3080  func (c *typeConv) badJNI(dt *dwarf.TypedefType) bool {
  3081  	// In Dalvik and ART, the jobject type in the JNI interface of the JVM has the
  3082  	// property that it is sometimes (always?) a small integer instead of a real pointer.
  3083  	// Note: although only the android JVMs are bad in this respect, we declare the JNI types
  3084  	// bad regardless of platform, so the same Go code compiles on both android and non-android.
  3085  	if parent, ok := jniTypes[dt.Name]; ok {
  3086  		// Try to make sure we're talking about a JNI type, not just some random user's
  3087  		// type that happens to use the same name.
  3088  		// C doesn't have the notion of a package, so it's hard to be certain.
  3089  
  3090  		// Walk up to jobject, checking each typedef on the way.
  3091  		w := dt
  3092  		for parent != "" {
  3093  			t, ok := w.Type.(*dwarf.TypedefType)
  3094  			if !ok || t.Name != parent {
  3095  				return false
  3096  			}
  3097  			w = t
  3098  			parent, ok = jniTypes[w.Name]
  3099  			if !ok {
  3100  				return false
  3101  			}
  3102  		}
  3103  
  3104  		// Check that the typedef is either:
  3105  		// 1:
  3106  		//     	struct _jobject;
  3107  		//     	typedef struct _jobject *jobject;
  3108  		// 2: (in NDK16 in C++)
  3109  		//     	class _jobject {};
  3110  		//     	typedef _jobject* jobject;
  3111  		// 3: (in NDK16 in C)
  3112  		//     	typedef void* jobject;
  3113  		if ptr, ok := w.Type.(*dwarf.PtrType); ok {
  3114  			switch v := ptr.Type.(type) {
  3115  			case *dwarf.VoidType:
  3116  				return true
  3117  			case *dwarf.StructType:
  3118  				if v.StructName == "_jobject" && len(v.Field) == 0 {
  3119  					switch v.Kind {
  3120  					case "struct":
  3121  						if v.Incomplete {
  3122  							return true
  3123  						}
  3124  					case "class":
  3125  						if !v.Incomplete {
  3126  							return true
  3127  						}
  3128  					}
  3129  				}
  3130  			}
  3131  		}
  3132  	}
  3133  	return false
  3134  }
  3135  
  3136  func (c *typeConv) badEGLDisplay(dt *dwarf.TypedefType) bool {
  3137  	if dt.Name != "EGLDisplay" {
  3138  		return false
  3139  	}
  3140  	// Check that the typedef is "typedef void *EGLDisplay".
  3141  	if ptr, ok := dt.Type.(*dwarf.PtrType); ok {
  3142  		if _, ok := ptr.Type.(*dwarf.VoidType); ok {
  3143  			return true
  3144  		}
  3145  	}
  3146  	return false
  3147  }
  3148  
  3149  // jniTypes maps from JNI types that we want to be uintptrs, to the underlying type to which
  3150  // they are mapped. The base "jobject" maps to the empty string.
  3151  var jniTypes = map[string]string{
  3152  	"jobject":       "",
  3153  	"jclass":        "jobject",
  3154  	"jthrowable":    "jobject",
  3155  	"jstring":       "jobject",
  3156  	"jarray":        "jobject",
  3157  	"jbooleanArray": "jarray",
  3158  	"jbyteArray":    "jarray",
  3159  	"jcharArray":    "jarray",
  3160  	"jshortArray":   "jarray",
  3161  	"jintArray":     "jarray",
  3162  	"jlongArray":    "jarray",
  3163  	"jfloatArray":   "jarray",
  3164  	"jdoubleArray":  "jarray",
  3165  	"jobjectArray":  "jarray",
  3166  	"jweak":         "jobject",
  3167  }