Mercurial > hg > CbC > CbC_gcc
comparison gcc/config/darwin-c.c @ 111:04ced10e8804
gcc 7
author | kono |
---|---|
date | Fri, 27 Oct 2017 22:46:09 +0900 |
parents | f6334be47118 |
children | 84e7813d76e9 |
comparison
equal
deleted
inserted
replaced
68:561a7518be6b | 111:04ced10e8804 |
---|---|
1 /* Darwin support needed only by C/C++ frontends. | 1 /* Darwin support needed only by C/C++ frontends. |
2 Copyright (C) 2001, 2003, 2004, 2005, 2007, 2008, 2010 | 2 Copyright (C) 2001-2017 Free Software Foundation, Inc. |
3 Free Software Foundation, Inc. | |
4 Contributed by Apple Computer Inc. | 3 Contributed by Apple Computer Inc. |
5 | 4 |
6 This file is part of GCC. | 5 This file is part of GCC. |
7 | 6 |
8 GCC is free software; you can redistribute it and/or modify | 7 GCC is free software; you can redistribute it and/or modify |
20 <http://www.gnu.org/licenses/>. */ | 19 <http://www.gnu.org/licenses/>. */ |
21 | 20 |
22 #include "config.h" | 21 #include "config.h" |
23 #include "system.h" | 22 #include "system.h" |
24 #include "coretypes.h" | 23 #include "coretypes.h" |
25 #include "tm.h" | 24 #include "target.h" |
26 #include "cpplib.h" | 25 #include "c-family/c-target.h" |
27 #include "tree.h" | 26 #include "c-family/c-target-def.h" |
27 #include "memmodel.h" | |
28 #include "tm_p.h" | |
29 #include "cgraph.h" | |
28 #include "incpath.h" | 30 #include "incpath.h" |
29 #include "c-family/c-common.h" | |
30 #include "c-family/c-pragma.h" | 31 #include "c-family/c-pragma.h" |
31 #include "c-family/c-format.h" | 32 #include "c-family/c-format.h" |
32 #include "diagnostic-core.h" | |
33 #include "flags.h" | |
34 #include "tm_p.h" | |
35 #include "cppdefault.h" | 33 #include "cppdefault.h" |
36 #include "prefix.h" | 34 #include "prefix.h" |
37 #include "target.h" | 35 #include "../../libcpp/internal.h" |
38 #include "target-def.h" | |
39 | 36 |
40 /* Pragmas. */ | 37 /* Pragmas. */ |
41 | 38 |
42 #define BAD(gmsgid) do { warning (OPT_Wpragmas, gmsgid); return; } while (0) | 39 #define BAD(gmsgid) do { warning (OPT_Wpragmas, gmsgid); return; } while (0) |
43 #define BAD2(msgid, arg) do { warning (OPT_Wpragmas, msgid, arg); return; } while (0) | 40 #define BAD2(msgid, arg) do { warning (OPT_Wpragmas, msgid, arg); return; } while (0) |
263 to the file, given the base name and the name. */ | 260 to the file, given the base name and the name. */ |
264 | 261 |
265 static char * | 262 static char * |
266 framework_construct_pathname (const char *fname, cpp_dir *dir) | 263 framework_construct_pathname (const char *fname, cpp_dir *dir) |
267 { | 264 { |
268 char *buf; | 265 const char *buf; |
269 size_t fname_len, frname_len; | 266 size_t fname_len, frname_len; |
270 cpp_dir *fast_dir; | 267 cpp_dir *fast_dir; |
271 char *frname; | 268 char *frname; |
272 struct stat st; | 269 struct stat st; |
273 int i; | 270 int i; |
340 static const char* | 337 static const char* |
341 find_subframework_file (const char *fname, const char *pname) | 338 find_subframework_file (const char *fname, const char *pname) |
342 { | 339 { |
343 char *sfrname; | 340 char *sfrname; |
344 const char *dot_framework = ".framework/"; | 341 const char *dot_framework = ".framework/"; |
345 char *bufptr; | 342 const char *bufptr; |
346 int sfrname_len, i, fname_len; | 343 int sfrname_len, i, fname_len; |
347 struct cpp_dir *fast_dir; | 344 struct cpp_dir *fast_dir; |
348 static struct cpp_dir subframe_dir; | 345 static struct cpp_dir subframe_dir; |
349 struct stat st; | 346 struct stat st; |
350 | 347 |
434 p->name = path; | 431 p->name = path; |
435 p->sysp = 1 + !cxx_aware; | 432 p->sysp = 1 + !cxx_aware; |
436 p->construct = framework_construct_pathname; | 433 p->construct = framework_construct_pathname; |
437 using_frameworks = 1; | 434 using_frameworks = 1; |
438 | 435 |
439 add_cpp_dir_path (p, SYSTEM); | 436 add_cpp_dir_path (p, INC_SYSTEM); |
440 } | 437 } |
441 | 438 |
442 /* Add PATH to the bracket includes. PATH must be malloc-ed and | 439 /* Add PATH to the bracket includes. PATH must be malloc-ed and |
443 NUL-terminated. */ | 440 NUL-terminated. */ |
444 | 441 |
452 p->name = path; | 449 p->name = path; |
453 p->sysp = 0; | 450 p->sysp = 0; |
454 p->construct = framework_construct_pathname; | 451 p->construct = framework_construct_pathname; |
455 using_frameworks = 1; | 452 using_frameworks = 1; |
456 | 453 |
457 add_cpp_dir_path (p, BRACKET); | 454 add_cpp_dir_path (p, INC_BRACKET); |
458 } | 455 } |
459 | 456 |
460 static const char *framework_defaults [] = | 457 static const char *framework_defaults [] = |
461 { | 458 { |
462 "/System/Library/Frameworks", | 459 "/System/Library/Frameworks", |
489 if (iprefix && (len = cpp_GCC_INCLUDE_DIR_len) != 0 && !sysroot | 486 if (iprefix && (len = cpp_GCC_INCLUDE_DIR_len) != 0 && !sysroot |
490 && !strncmp (fname, cpp_GCC_INCLUDE_DIR, len)) | 487 && !strncmp (fname, cpp_GCC_INCLUDE_DIR, len)) |
491 { | 488 { |
492 str = concat (iprefix, fname + len, NULL); | 489 str = concat (iprefix, fname + len, NULL); |
493 /* FIXME: wrap the headers for C++awareness. */ | 490 /* FIXME: wrap the headers for C++awareness. */ |
494 add_path (str, SYSTEM, /*c++aware=*/false, false); | 491 add_path (str, INC_SYSTEM, /*c++aware=*/false, false); |
495 } | 492 } |
496 | 493 |
497 /* Should this directory start with the sysroot? */ | 494 /* Should this directory start with the sysroot? */ |
498 if (sysroot) | 495 if (sysroot) |
499 str = concat (sysroot, fname, NULL); | 496 str = concat (sysroot, fname, NULL); |
500 else | 497 else |
501 str = update_path (fname, ""); | 498 str = update_path (fname, ""); |
502 | 499 |
503 add_path (str, SYSTEM, /*c++aware=*/false, false); | 500 add_path (str, INC_SYSTEM, /*c++aware=*/false, false); |
504 } | 501 } |
505 } | 502 } |
506 | 503 |
507 | 504 |
508 /* Register all the system framework paths if STDINC is true and setup | 505 /* Register all the system framework paths if STDINC is true and setup |
566 } | 563 } |
567 | 564 |
568 return 0; | 565 return 0; |
569 } | 566 } |
570 | 567 |
571 /* Return the value of darwin_macosx_version_min suitable for the | 568 /* Given an OS X version VERSION_STR, return it as a statically-allocated array |
572 __ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__ macro, | 569 of three integers. If VERSION_STR is invalid, return NULL. |
573 so '10.4.2' becomes 1040. The lowest digit is always zero. | 570 |
574 Print a warning if the version number can't be understood. */ | 571 VERSION_STR must consist of one, two, or three tokens, each separated by |
572 a single period. Each token must contain only the characters '0' through | |
573 '9' and is converted to an equivalent non-negative decimal integer. Omitted | |
574 tokens become zeros. For example: | |
575 | |
576 "10" becomes {10,0,0} | |
577 "10.10" becomes {10,10,0} | |
578 "10.10.1" becomes {10,10,1} | |
579 "10.000010.1" becomes {10,10,1} | |
580 "10.010.001" becomes {10,10,1} | |
581 "000010.10.00001" becomes {10,10,1} | |
582 ".9.1" is invalid | |
583 "10..9" is invalid | |
584 "10.10." is invalid */ | |
585 | |
586 enum version_components { MAJOR, MINOR, TINY }; | |
587 | |
588 static const unsigned long * | |
589 parse_version (const char *version_str) | |
590 { | |
591 size_t version_len; | |
592 char *end; | |
593 static unsigned long version_array[3]; | |
594 | |
595 version_len = strlen (version_str); | |
596 if (version_len < 1) | |
597 return NULL; | |
598 | |
599 /* Version string must consist of digits and periods only. */ | |
600 if (strspn (version_str, "0123456789.") != version_len) | |
601 return NULL; | |
602 | |
603 if (!ISDIGIT (version_str[0]) || !ISDIGIT (version_str[version_len - 1])) | |
604 return NULL; | |
605 | |
606 version_array[MAJOR] = strtoul (version_str, &end, 10); | |
607 version_str = end + ((*end == '.') ? 1 : 0); | |
608 | |
609 /* Version string must not contain adjacent periods. */ | |
610 if (*version_str == '.') | |
611 return NULL; | |
612 | |
613 version_array[MINOR] = strtoul (version_str, &end, 10); | |
614 version_str = end + ((*end == '.') ? 1 : 0); | |
615 | |
616 version_array[TINY] = strtoul (version_str, &end, 10); | |
617 | |
618 /* Version string must contain no more than three tokens. */ | |
619 if (*end != '\0') | |
620 return NULL; | |
621 | |
622 return version_array; | |
623 } | |
624 | |
625 /* Given VERSION -- a three-component OS X version represented as an array of | |
626 non-negative integers -- return a statically-allocated string suitable for | |
627 the legacy __ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__ macro. If VERSION | |
628 is invalid and cannot be coerced into a valid form, return NULL. | |
629 | |
630 The legacy format is a four-character string -- two chars for the major | |
631 number and one each for the minor and tiny numbers. Minor and tiny numbers | |
632 from 10 through 99 are permitted but are clamped to 9 (for example, {10,9,10} | |
633 produces "1099"). If VERSION contains numbers greater than 99, it is | |
634 rejected. */ | |
635 | |
575 static const char * | 636 static const char * |
576 version_as_macro (void) | 637 version_as_legacy_macro (const unsigned long *version) |
577 { | 638 { |
578 static char result[] = "1000"; | 639 unsigned long major, minor, tiny; |
579 | 640 static char result[5]; |
580 if (strncmp (darwin_macosx_version_min, "10.", 3) != 0) | 641 |
642 major = version[MAJOR]; | |
643 minor = version[MINOR]; | |
644 tiny = version[TINY]; | |
645 | |
646 if (major > 99 || minor > 99 || tiny > 99) | |
647 return NULL; | |
648 | |
649 minor = ((minor > 9) ? 9 : minor); | |
650 tiny = ((tiny > 9) ? 9 : tiny); | |
651 | |
652 if (sprintf (result, "%lu%lu%lu", major, minor, tiny) != 4) | |
653 return NULL; | |
654 | |
655 return result; | |
656 } | |
657 | |
658 /* Given VERSION -- a three-component OS X version represented as an array of | |
659 non-negative integers -- return a statically-allocated string suitable for | |
660 the modern __ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__ macro. If VERSION | |
661 is invalid, return NULL. | |
662 | |
663 The modern format is a six-character string -- two chars for each component, | |
664 with zero-padding if necessary (for example, {10,10,1} produces "101001"). If | |
665 VERSION contains numbers greater than 99, it is rejected. */ | |
666 | |
667 static const char * | |
668 version_as_modern_macro (const unsigned long *version) | |
669 { | |
670 unsigned long major, minor, tiny; | |
671 static char result[7]; | |
672 | |
673 major = version[MAJOR]; | |
674 minor = version[MINOR]; | |
675 tiny = version[TINY]; | |
676 | |
677 if (major > 99 || minor > 99 || tiny > 99) | |
678 return NULL; | |
679 | |
680 if (sprintf (result, "%02lu%02lu%02lu", major, minor, tiny) != 6) | |
681 return NULL; | |
682 | |
683 return result; | |
684 } | |
685 | |
686 /* Return the value of darwin_macosx_version_min, suitably formatted for the | |
687 __ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__ macro. Values representing | |
688 OS X 10.9 and earlier are encoded using the legacy four-character format, | |
689 while 10.10 and later use a modern six-character format. (For example, | |
690 "10.9" produces "1090", and "10.10.1" produces "101001".) If | |
691 darwin_macosx_version_min is invalid and cannot be coerced into a valid | |
692 form, print a warning and return "1000". */ | |
693 | |
694 static const char * | |
695 macosx_version_as_macro (void) | |
696 { | |
697 const unsigned long *version_array; | |
698 const char *version_macro; | |
699 | |
700 version_array = parse_version (darwin_macosx_version_min); | |
701 if (!version_array) | |
581 goto fail; | 702 goto fail; |
582 if (! ISDIGIT (darwin_macosx_version_min[3])) | 703 |
704 if (version_array[MAJOR] != 10) | |
583 goto fail; | 705 goto fail; |
584 result[2] = darwin_macosx_version_min[3]; | 706 |
585 if (darwin_macosx_version_min[4] != '\0' | 707 if (version_array[MINOR] < 10) |
586 && darwin_macosx_version_min[4] != '.') | 708 version_macro = version_as_legacy_macro (version_array); |
709 else | |
710 version_macro = version_as_modern_macro (version_array); | |
711 | |
712 if (!version_macro) | |
587 goto fail; | 713 goto fail; |
588 | 714 |
589 return result; | 715 return version_macro; |
590 | 716 |
591 fail: | 717 fail: |
592 error ("unknown value %qs of -mmacosx-version-min", | 718 error ("unknown value %qs of -mmacosx-version-min", |
593 darwin_macosx_version_min); | 719 darwin_macosx_version_min); |
594 return "1000"; | 720 return "1000"; |
595 } | 721 } |
596 | 722 |
597 /* Define additional CPP flags for Darwin. */ | 723 /* Define additional CPP flags for Darwin. */ |
598 | 724 |
610 | 736 |
611 if (darwin_constant_cfstrings) | 737 if (darwin_constant_cfstrings) |
612 builtin_define ("__CONSTANT_CFSTRINGS__"); | 738 builtin_define ("__CONSTANT_CFSTRINGS__"); |
613 | 739 |
614 builtin_define_with_value ("__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__", | 740 builtin_define_with_value ("__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__", |
615 version_as_macro(), false); | 741 macosx_version_as_macro(), false); |
616 | 742 |
617 /* Since we do not (at 4.6) support ObjC gc for the NeXT runtime, the | 743 /* Since we do not (at 4.6) support ObjC gc for the NeXT runtime, the |
618 following will cause a syntax error if one tries to compile gc attributed | 744 following will cause a syntax error if one tries to compile gc attributed |
619 items. However, without this, NeXT system headers cannot be parsed | 745 items. However, without this, NeXT system headers cannot be parsed |
620 properly (on systems >= darwin 9). */ | 746 properly (on systems >= darwin 9). */ |
628 { | 754 { |
629 builtin_define ("__strong="); | 755 builtin_define ("__strong="); |
630 builtin_define ("__weak="); | 756 builtin_define ("__weak="); |
631 } | 757 } |
632 | 758 |
633 if (flag_objc_abi == 2) | 759 if (CPP_OPTION (pfile, objc) && flag_objc_abi == 2) |
634 builtin_define ("__OBJC2__"); | 760 builtin_define ("__OBJC2__"); |
635 } | 761 } |
636 | 762 |
637 /* Handle C family front-end options. */ | 763 /* Handle C family front-end options. */ |
638 | 764 |
658 | 784 |
659 /* We recognized the option. */ | 785 /* We recognized the option. */ |
660 return true; | 786 return true; |
661 } | 787 } |
662 | 788 |
663 #undef TARGET_HANDLE_C_OPTION | |
664 #define TARGET_HANDLE_C_OPTION handle_c_option | |
665 | |
666 struct gcc_targetcm targetcm = TARGETCM_INITIALIZER; | |
667 | |
668 /* Allow ObjC* access to CFStrings. */ | 789 /* Allow ObjC* access to CFStrings. */ |
669 tree | 790 static tree |
670 darwin_objc_construct_string (tree str) | 791 darwin_objc_construct_string (tree str) |
671 { | 792 { |
672 if (!darwin_constant_cfstrings) | 793 if (!darwin_constant_cfstrings) |
673 { | 794 { |
674 /* Even though we are not using CFStrings, place our literal | 795 /* Even though we are not using CFStrings, place our literal |
683 } | 804 } |
684 | 805 |
685 /* The string ref type is created as CFStringRef by <CFBase.h> therefore, we | 806 /* The string ref type is created as CFStringRef by <CFBase.h> therefore, we |
686 must match for it explicitly, since it's outside the gcc code. */ | 807 must match for it explicitly, since it's outside the gcc code. */ |
687 | 808 |
688 bool | 809 static bool |
689 darwin_cfstring_ref_p (const_tree strp) | 810 darwin_cfstring_ref_p (const_tree strp) |
690 { | 811 { |
691 tree tn; | 812 tree tn; |
692 if (!strp || TREE_CODE (strp) != POINTER_TYPE) | 813 if (!strp || TREE_CODE (strp) != POINTER_TYPE) |
693 return false; | 814 return false; |
699 && IDENTIFIER_POINTER (tn) | 820 && IDENTIFIER_POINTER (tn) |
700 && !strncmp (IDENTIFIER_POINTER (tn), "CFStringRef", 8)); | 821 && !strncmp (IDENTIFIER_POINTER (tn), "CFStringRef", 8)); |
701 } | 822 } |
702 | 823 |
703 /* At present the behavior of this is undefined and it does nothing. */ | 824 /* At present the behavior of this is undefined and it does nothing. */ |
704 void | 825 static void |
705 darwin_check_cfstring_format_arg (tree ARG_UNUSED (format_arg), | 826 darwin_check_cfstring_format_arg (tree ARG_UNUSED (format_arg), |
706 tree ARG_UNUSED (args_list)) | 827 tree ARG_UNUSED (args_list)) |
707 { | 828 { |
708 } | 829 } |
709 | 830 |
713 NULL, NULL, | 834 NULL, NULL, |
714 FMT_FLAG_ARG_CONVERT|FMT_FLAG_PARSE_ARG_CONVERT_EXTERNAL, 0, 0, 0, 0, 0, 0, | 835 FMT_FLAG_ARG_CONVERT|FMT_FLAG_PARSE_ARG_CONVERT_EXTERNAL, 0, 0, 0, 0, 0, 0, |
715 NULL, NULL | 836 NULL, NULL |
716 } | 837 } |
717 }; | 838 }; |
839 | |
840 | |
841 /* Support routines to dump the class references for NeXT ABI v1, aka | |
842 32-bits ObjC-2.0, as top-level asms. | |
843 The following two functions should only be called from | |
844 objc/objc-next-runtime-abi-01.c. */ | |
845 | |
846 static void | |
847 darwin_objc_declare_unresolved_class_reference (const char *name) | |
848 { | |
849 const char *lazy_reference = ".lazy_reference\t"; | |
850 const char *hard_reference = ".reference\t"; | |
851 const char *reference = MACHOPIC_INDIRECT ? lazy_reference : hard_reference; | |
852 size_t len = strlen (reference) + strlen(name) + 2; | |
853 char *buf = (char *) alloca (len); | |
854 | |
855 gcc_checking_assert (!strncmp (name, ".objc_class_name_", 17)); | |
856 | |
857 snprintf (buf, len, "%s%s", reference, name); | |
858 symtab->finalize_toplevel_asm (build_string (strlen (buf), buf)); | |
859 } | |
860 | |
861 static void | |
862 darwin_objc_declare_class_definition (const char *name) | |
863 { | |
864 const char *xname = targetm.strip_name_encoding (name); | |
865 size_t len = strlen (xname) + 7 + 5; | |
866 char *buf = (char *) alloca (len); | |
867 | |
868 gcc_checking_assert (!strncmp (name, ".objc_class_name_", 17) | |
869 || !strncmp (name, "*.objc_category_name_", 21)); | |
870 | |
871 /* Mimic default_globalize_label. */ | |
872 snprintf (buf, len, ".globl\t%s", xname); | |
873 symtab->finalize_toplevel_asm (build_string (strlen (buf), buf)); | |
874 | |
875 snprintf (buf, len, "%s = 0", xname); | |
876 symtab->finalize_toplevel_asm (build_string (strlen (buf), buf)); | |
877 } | |
878 | |
879 #undef TARGET_HANDLE_C_OPTION | |
880 #define TARGET_HANDLE_C_OPTION handle_c_option | |
881 | |
882 #undef TARGET_OBJC_CONSTRUCT_STRING_OBJECT | |
883 #define TARGET_OBJC_CONSTRUCT_STRING_OBJECT darwin_objc_construct_string | |
884 | |
885 #undef TARGET_OBJC_DECLARE_UNRESOLVED_CLASS_REFERENCE | |
886 #define TARGET_OBJC_DECLARE_UNRESOLVED_CLASS_REFERENCE \ | |
887 darwin_objc_declare_unresolved_class_reference | |
888 | |
889 #undef TARGET_OBJC_DECLARE_CLASS_DEFINITION | |
890 #define TARGET_OBJC_DECLARE_CLASS_DEFINITION \ | |
891 darwin_objc_declare_class_definition | |
892 | |
893 #undef TARGET_STRING_OBJECT_REF_TYPE_P | |
894 #define TARGET_STRING_OBJECT_REF_TYPE_P darwin_cfstring_ref_p | |
895 | |
896 #undef TARGET_CHECK_STRING_OBJECT_FORMAT_ARG | |
897 #define TARGET_CHECK_STRING_OBJECT_FORMAT_ARG darwin_check_cfstring_format_arg | |
898 | |
899 struct gcc_targetcm targetcm = TARGETCM_INITIALIZER; |