LEFT | RIGHT |
(no file at all) | |
1 // Copyright 2009 The Go Authors. All rights reserved. | 1 // Copyright 2009 The Go Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style | 2 // Use of this source code is governed by a BSD-style |
3 // license that can be found in the LICENSE file. | 3 // license that can be found in the LICENSE file. |
4 | 4 |
5 // Annotate Ref in Prog with C types by parsing gcc debug output. | 5 // Annotate Ref in Prog with C types by parsing gcc debug output. |
6 // Conversion of debug output to Go types. | 6 // Conversion of debug output to Go types. |
7 | 7 |
8 package main | 8 package main |
9 | 9 |
10 import ( | 10 import ( |
(...skipping 628 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
639 } | 639 } |
640 if id.Name == r.Name.Mangle && r.Name.Const != "
" { | 640 if id.Name == r.Name.Mangle && r.Name.Const != "
" { |
641 expr = ast.NewIdent(r.Name.Const) | 641 expr = ast.NewIdent(r.Name.Const) |
642 } | 642 } |
643 } | 643 } |
644 } | 644 } |
645 *r.Expr = expr | 645 *r.Expr = expr |
646 } | 646 } |
647 } | 647 } |
648 | 648 |
649 // gccName returns the name of the compiler to run. Use $CC if set in | 649 // gccBaseCmd returns the start of the compiler command line. |
650 // the environment, otherwise just "gcc". | 650 // It uses $CC if set, or else $GCC, or else the compiler recorded |
651 | 651 // during the initial build as defaultCC. |
652 func (p *Package) gccName() string { | 652 // defaultCC is defined in zdefaultcc.go, written by cmd/dist. |
| 653 func (p *Package) gccBaseCmd() []string { |
653 // Use $CC if set, since that's what the build uses. | 654 // Use $CC if set, since that's what the build uses. |
654 » if ret := os.Getenv("CC"); ret != "" { | 655 » if ret := strings.Fields(os.Getenv("CC")); len(ret) > 0 { |
655 return ret | 656 return ret |
656 } | 657 } |
657 » // Fall back to $GCC if set, since that's what we used to use. | 658 » // Try $GCC if set, since that's what we used to use. |
658 » if ret := os.Getenv("GCC"); ret != "" { | 659 » if ret := strings.Fields(os.Getenv("GCC")); len(ret) > 0 { |
659 return ret | 660 return ret |
660 } | 661 } |
661 » return "gcc" | 662 » return strings.Fields(defaultCC) |
662 } | 663 } |
663 | 664 |
664 // gccMachine returns the gcc -m flag to use, either "-m32", "-m64" or "-marm". | 665 // gccMachine returns the gcc -m flag to use, either "-m32", "-m64" or "-marm". |
665 func (p *Package) gccMachine() []string { | 666 func (p *Package) gccMachine() []string { |
666 switch goarch { | 667 switch goarch { |
667 case "amd64": | 668 case "amd64": |
668 return []string{"-m64"} | 669 return []string{"-m64"} |
669 case "386": | 670 case "386": |
670 return []string{"-m32"} | 671 return []string{"-m32"} |
671 case "arm": | 672 case "arm": |
672 return []string{"-marm"} // not thumb | 673 return []string{"-marm"} // not thumb |
673 } | 674 } |
674 return nil | 675 return nil |
675 } | 676 } |
676 | 677 |
677 func gccTmp() string { | 678 func gccTmp() string { |
678 return *objDir + "_cgo_.o" | 679 return *objDir + "_cgo_.o" |
679 } | 680 } |
680 | 681 |
681 // gccCmd returns the gcc command line to use for compiling | 682 // gccCmd returns the gcc command line to use for compiling |
682 // the input. | 683 // the input. |
683 func (p *Package) gccCmd() []string { | 684 func (p *Package) gccCmd() []string { |
684 » c := []string{ | 685 » c := append(p.gccBaseCmd(), |
685 » » p.gccName(), | |
686 "-Wall", // many warnings | 686 "-Wall", // many warnings |
687 "-Werror", // warnings are errors | 687 "-Werror", // warnings are errors |
688 » » "-o" + gccTmp(), // write object to tmp | 688 » » "-o"+gccTmp(), // write object to tmp |
689 "-gdwarf-2", // generate DWARF v2 debugg
ing symbols | 689 "-gdwarf-2", // generate DWARF v2 debugg
ing symbols |
690 "-fno-eliminate-unused-debug-types", // gets rid of e.g. untyped
enum otherwise | 690 "-fno-eliminate-unused-debug-types", // gets rid of e.g. untyped
enum otherwise |
691 "-c", // do not link | 691 "-c", // do not link |
692 "-xc", // input language is C | 692 "-xc", // input language is C |
693 » } | 693 » ) |
694 » if strings.Contains(p.gccName(), "clang") { | 694 » if strings.Contains(c[0], "clang") { |
695 c = append(c, | 695 c = append(c, |
696 "-ferror-limit=0", | 696 "-ferror-limit=0", |
697 // Apple clang version 1.7 (tags/Apple/clang-77) (based
on LLVM 2.9svn) | 697 // Apple clang version 1.7 (tags/Apple/clang-77) (based
on LLVM 2.9svn) |
698 // doesn't have -Wno-unneeded-internal-declaration, so w
e need yet another | 698 // doesn't have -Wno-unneeded-internal-declaration, so w
e need yet another |
699 // flag to disable the warning. Yes, really good diagnos
tics, clang. | 699 // flag to disable the warning. Yes, really good diagnos
tics, clang. |
700 "-Wno-unknown-warning-option", | 700 "-Wno-unknown-warning-option", |
701 "-Wno-unneeded-internal-declaration", | 701 "-Wno-unneeded-internal-declaration", |
702 "-Wno-unused-function", | 702 "-Wno-unused-function", |
703 "-Qunused-arguments", | 703 "-Qunused-arguments", |
704 ) | 704 ) |
(...skipping 88 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
793 | 793 |
794 fatalf("cannot parse gcc output %s as ELF, Mach-O, PE object", gccTmp()) | 794 fatalf("cannot parse gcc output %s as ELF, Mach-O, PE object", gccTmp()) |
795 panic("not reached") | 795 panic("not reached") |
796 } | 796 } |
797 | 797 |
798 // gccDefines runs gcc -E -dM -xc - over the C program stdin | 798 // gccDefines runs gcc -E -dM -xc - over the C program stdin |
799 // and returns the corresponding standard output, which is the | 799 // and returns the corresponding standard output, which is the |
800 // #defines that gcc encountered while processing the input | 800 // #defines that gcc encountered while processing the input |
801 // and its included files. | 801 // and its included files. |
802 func (p *Package) gccDefines(stdin []byte) string { | 802 func (p *Package) gccDefines(stdin []byte) string { |
803 » base := []string{p.gccName(), "-E", "-dM", "-xc"} | 803 » base := append(p.gccBaseCmd(), "-E", "-dM", "-xc") |
804 base = append(base, p.gccMachine()...) | 804 base = append(base, p.gccMachine()...) |
805 stdout, _ := runGcc(stdin, append(append(base, p.GccOptions...), "-")) | 805 stdout, _ := runGcc(stdin, append(append(base, p.GccOptions...), "-")) |
806 return stdout | 806 return stdout |
807 } | 807 } |
808 | 808 |
809 // gccErrors runs gcc over the C program stdin and returns | 809 // gccErrors runs gcc over the C program stdin and returns |
810 // the errors that gcc prints. That is, this function expects | 810 // the errors that gcc prints. That is, this function expects |
811 // gcc to fail. | 811 // gcc to fail. |
812 func (p *Package) gccErrors(stdin []byte) string { | 812 func (p *Package) gccErrors(stdin []byte) string { |
813 // TODO(rsc): require failure | 813 // TODO(rsc): require failure |
(...skipping 737 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1551 } | 1551 } |
1552 if prefix == "" { | 1552 if prefix == "" { |
1553 prefix = n.Name[:i+1] | 1553 prefix = n.Name[:i+1] |
1554 } else if prefix != n.Name[:i+1] { | 1554 } else if prefix != n.Name[:i+1] { |
1555 return "" | 1555 return "" |
1556 } | 1556 } |
1557 } | 1557 } |
1558 } | 1558 } |
1559 return prefix | 1559 return prefix |
1560 } | 1560 } |
LEFT | RIGHT |