PATCH: PR14137

Steven Bosscher stevenb@suse.de
Sun Mar 21 22:39:00 GMT 2004


I've bootstrapped this patch on i686 and x86_64 with multilib, tested
it on x86_64 and i686, and verified that it fixes the bug:

cc1plus: warning:
/opt/experimental/bin/../lib/gcc/i686-pc-linux-gnu/3.4.0/../../../../include/c++/3.4.0/i686-pc-linux-gnu/bits/stdc++.h.gch/O0g:
created using different flags
cc1plus: warning:
/opt/experimental/bin/../lib/gcc/i686-pc-linux-gnu/3.4.0/../../../../include/c++/3.4.0/i686-pc-linux-gnu/bits/stdc++.h.gch/O2g:
not used because `__OPTIMIZE__' not defined
cc1plus: bits/stdc++.h: No such file or directory
cc1plus: one or more PCH files were found, but they were invalid

Which doesn't mean it's the correct fix.  I don't know the PCH system
well enough to tell if there isn't already a way to verify that some
flag settings match.  And perhaps we want a builtin define when we're
compiling with -funit-at-a-time (though perhaps long-term not ideal,
it could be convenient??).  Or perhaps there are other flags we want
to check for?

Anyway, how does this look?

Gr.
Steven



<date>  Steven Bosscher  <stevenb@suse.de>

	PR pch/14137
	* c-pch.c (struct c_pch_validity): New flags_info field.
	(FLAG_UNIT_AT_A_TIME_SET): New definition.
	(pch_init): Write out the flags_info field to the PCH.  Set the
	FLAG_UNIT_AT_A_TIME_SET bit of the field if flag_unit_at_a_time
	is set.
	(c_common_valid_pch): Make sure the flag settings used for compiling
	the PCH are the same as those used in the current compilation.

Index: c-pch.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/c-pch.c,v
retrieving revision 1.21
diff -c -3 -p -r1.21 c-pch.c
*** c-pch.c	15 Mar 2004 18:20:39 -0000	1.21
--- c-pch.c	21 Mar 2004 20:56:59 -0000
*************** Boston, MA 02111-1307, USA.  */
*** 44,50 ****
     the version number in get_ident().  
  
     There are a bunch of fields named *_length; those are lengths of data that
!    follows this structure in the same order as the fields in the structure.  */
  
  struct c_pch_validity
  {
--- 44,54 ----
     the version number in get_ident().  
  
     There are a bunch of fields named *_length; those are lengths of data that
!    follows this structure in the same order as the fields in the structure.
! 
!    The flags_info field is used to verify that certain flags settings that
!    have to be the same during the compilation of the PCH and a compilation
!    using the PCH are indeed the same.  */
  
  struct c_pch_validity
  {
*************** struct c_pch_validity
*** 52,61 ****
--- 56,70 ----
    unsigned char target_machine_length;
    unsigned char version_length;
    unsigned char debug_info_type;
+   unsigned int flags_info;
    void (*pch_init) (void);
    size_t target_data_length;
  };
  
+ /* If -funit-at-a-time is set, we require that it was also set during the
+    compilation of the PCH we may be using.  */
+ #define FLAG_UNIT_AT_A_TIME_SET 1 << 0
+ 
  struct c_pch_header 
  {
    unsigned long asm_size;
*************** pch_init (void)
*** 103,112 ****
    struct c_pch_validity v;
    void *target_validity;
    static const char partial_pch[IDENT_LENGTH] = "gpcWrite";
    
    if (! pch_file)
      return;
!   
    f = fopen (pch_file, "w+b");
    if (f == NULL)
      fatal_error ("can't create precompiled header %s: %m", pch_file);
--- 112,125 ----
    struct c_pch_validity v;
    void *target_validity;
    static const char partial_pch[IDENT_LENGTH] = "gpcWrite";
+   unsigned int current_flags_info = 0;
    
    if (! pch_file)
      return;
! 
!   if (flag_unit_at_a_time)
!     current_flags_info |= FLAG_UNIT_AT_A_TIME_SET;
! 
    f = fopen (pch_file, "w+b");
    if (f == NULL)
      fatal_error ("can't create precompiled header %s: %m", pch_file);
*************** pch_init (void)
*** 120,125 ****
--- 133,139 ----
    v.target_machine_length = strlen (target_machine);
    v.version_length = strlen (version_string);
    v.debug_info_type = write_symbols;
+   v.flags_info = current_flags_info;
    v.pch_init = &pch_init;
    target_validity = targetm.get_pch_validity (&v.target_data_length);
    
*************** c_common_valid_pch (cpp_reader *pfile, c
*** 212,220 ****
    int strings_length;
    const char *pch_ident;
    struct c_pch_validity v;
  
    /* Perform a quick test of whether this is a valid
!      precompiled header for the current language.  */
  
    sizeread = read (fd, ident, IDENT_LENGTH);
    if (sizeread == -1)
--- 226,239 ----
    int strings_length;
    const char *pch_ident;
    struct c_pch_validity v;
+   unsigned int current_flags_info = 0;
+ 
+   if (flag_unit_at_a_time)
+     current_flags_info |= FLAG_UNIT_AT_A_TIME_SET;
  
    /* Perform a quick test of whether this is a valid
!      precompiled header for the current language
!      and with the current flag settings.  */
  
    sizeread = read (fd, ident, IDENT_LENGTH);
    if (sizeread == -1)
*************** c_common_valid_pch (cpp_reader *pfile, c
*** 285,290 ****
--- 304,317 ----
  		   (short_strings + v.host_machine_length 
  		    + v.target_machine_length), 
  		   version_string);
+       return 2;
+     }
+   if (v.flags_info != current_flags_info)
+     {
+       if (cpp_get_options (pfile)->warn_invalid_pch)
+ 	cpp_error (pfile, CPP_DL_WARNING,
+ 		   "%s: created using different flags",
+ 		   name);
        return 2;
      }
  



More information about the Gcc-patches mailing list