This is the mail archive of the binutils@sourceware.org mailing list for the binutils project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: [PATCH] Sync libiberty/ & include/ with GCC


Forgot to tweak subject to say that I've pushed this already...

BTW, I found merging include/ a real pain, because we don't sync
the whole directory, and our include/ChangeLog is different
from gcc's include/ChangeLog.  It's hard to determine which
patches are missing on either end.
Maybe we could come up with some alternative source layout that
would avoid this.  Like maybe moving gcc-owned files to include/gcc/.

Thanks,
Pedro Alves

On 09/15/2017 05:46 PM, Pedro Alves wrote:
> Note this brings in the interface files for libcc1/G++ as well, which
> we will be needing in GDB soon anyway.  That commit renamed a method
> in the C interface and that required a small update to GDB's compile/
> code, which I've included that in this patch to keep the tree
> building.
> 
> include/ChangeLog:
> 2017-09-15  Pedro Alves  <palves@redhat.com>
> 
> 	* ansidecl.h (DISABLE_COPY_AND_ASSIGN): New macro.
> 
> 	2017-09-12  Jiong Wang  <jiong.wang@arm.com>
> 
> 	* dwarf2.def (DW_CFA_AARCH64_negate_ra_state): New DW_CFA_DUP.
> 	* dwarf2.h (DW_CFA_DUP): New define.
> 
> 	2017-08-21  Richard Biener  <rguenther@suse.de>
> 
> 	* simple-object.h (simple_object_copy_lto_debug_sections): New
> 	function.
> 
> 	2017-05-18  Martin Liska  <mliska@suse.cz>
> 
> 	* ansidecl.h: Define CONSTEXPR macro.
> 
> 	2017-05-24  Nathan Sidwell  <nathan@acm.org>
> 
> 	* libiberty.h (ASTRDUP): Adjust cast to avoid warning.
> 
> 	2017-01-30  Alexandre Oliva <aoliva@redhat.com>
> 
> 	Introduce C++ support in libcc1.
> 	* gcc-c-fe.def (int_type_v0): Rename from...
> 	(int_type): ... this.  Introduce new version.
> 	(float_type_v0): Rename from...
> 	(float_type): ... this.  Introduce new version.
> 	(char_type): New.
> 	* gcc-c-interface.h (gcc_c_api_version): Add GCC_C_FE_VERSION_1.
> 	(gcc_type_array): Move...
> 	* gcc-interface.h: ... here.
> 	* gcc-cp-fe.def: New.
> 	* gcc-cp-interface.h: New.
> 
> 	2016-04-29  Oleg Endo  <olegendo@gcc.gnu.org>
> 
> 	* longlong.h (umul_ppmm): Remove SHMEDIA checks.
> 	(__umulsidi3, count_leading_zeros): Remove SHMEDIA implementations.
> 
> 	2017-09-15  Yao Qi  <yao.qi@linaro.org>
> 	    Pedro Alves  <palves@redhat.com>
> 
> 	* ansidecl.h (DISABLE_COPY_AND_ASSIGN): New macro.
> 
> 	2017-09-12  Jiong Wang  <jiong.wang@arm.com>
> 
> 	* dwarf2.def (DW_CFA_AARCH64_negate_ra_state): New DW_CFA_DUP.
> 	* dwarf2.h (DW_CFA_DUP): New define.
> 
> 	2017-08-21  Richard Biener  <rguenther@suse.de>
> 
> 	* simple-object.h (simple_object_copy_lto_debug_sections): New
> 	function.
> 
> 	2017-05-18  Martin Liska  <mliska@suse.cz>
> 
> 	* ansidecl.h: Define CONSTEXPR macro.
> 
> 	2017-05-24  Nathan Sidwell  <nathan@acm.org>
> 
> 	* libiberty.h (ASTRDUP): Adjust cast to avoid warning.
> 
> 	2017-01-30  Alexandre Oliva <aoliva@redhat.com>
> 
> 	Introduce C++ support in libcc1.
> 	* gcc-c-fe.def (int_type_v0): Rename from...
> 	(int_type): ... this.  Introduce new version.
> 	(float_type_v0): Rename from...
> 	(float_type): ... this.  Introduce new version.
> 	(char_type): New.
> 	* gcc-c-interface.h (gcc_c_api_version): Add GCC_C_FE_VERSION_1.
> 	(gcc_type_array): Move...
> 	* gcc-interface.h: ... here.
> 	* gcc-cp-fe.def: New.
> 	* gcc-cp-interface.h: New.
> 
> 	2016-04-29  Oleg Endo  <olegendo@gcc.gnu.org>
> 
> 	* longlong.h (umul_ppmm): Remove SHMEDIA checks.
> 	(__umulsidi3, count_leading_zeros): Remove SHMEDIA implementations.
> 
> libiberty/ChangeLog:
> 2017-09-15  Nathan Sidwell  <nathan@acm.org>
> 
> 	PR demangler/82195
> 	* cp-demangle.c (d_name): Add 'toplevel' parm.  Pass to	...
> 	(d_local_name): ... here.  Parse trailing function args on nested
> 	local_name.
> 	(d_encoding, d_special_name, d_class_enum_type): Adjust d_name calls.
> 	* testsuite/demangle-expected: Add tests.
> 
> 2017-09-15  Richard Biener  <rguenther@suse.de>
> 
> 	PR lto/81968
> 	* simple-object-elf.c (simple_object_elf_copy_lto_debug_sections):
> 	Iterate marking dependent sections necessary.
> 
> 2017-09-15  Nathan Sidwell  <nathan@acm.org>
> 
> 	* cp-demangle.c (is_fnqual_component_type): Reimplement using
> 	FNQUAL_COMPONENT_CASE.
> 	(d_encoding): Hold bare_function_type in local var.
> 	(d_local_name): Build name in both cases and build result once.
> 	Collapse switch-if to single conditional.
> 	(d_local_name):
> 
> 	* testsuite/demangle-expected: Realign blank lines with tests.
> 
> 2017-09-12  Jiong Wang  <jiong.wang@arm.com>
> 
> 	* dwarfnames.c (DW_CFA_DUP): New define.
> 
> gdb/ChangeLog:
> 2017-09-15  Pedro Alves  <palves@redhat.com>
> 
> 	* compile/compile-c-types.c (convert_enum, convert_int)
> 	(convert_float): Adjust to refer to int_type_v0 and float_type_v0.
> ---
>  gdb/ChangeLog                         |    5 +
>  include/ChangeLog                     |   88 +++
>  libiberty/ChangeLog                   |   30 +
>  gdb/compile/compile-c-types.c         |   16 +-
>  include/ansidecl.h                    |   34 +-
>  include/dwarf2.def                    |    1 +
>  include/dwarf2.h                      |    2 +
>  include/gcc-c-fe.def                  |   35 +-
>  include/gcc-c-interface.h             |   21 +-
>  include/gcc-cp-fe.def                 | 1050 +++++++++++++++++++++++++++++++++
>  include/gcc-cp-interface.h            |  496 ++++++++++++++++
>  include/gcc-interface.h               |   14 +
>  include/libiberty.h                   |    4 +-
>  include/longlong.h                    |   65 +-
>  include/simple-object.h               |    8 +
>  libiberty/cp-demangle.c               |  110 ++--
>  libiberty/dwarfnames.c                |    2 +
>  libiberty/simple-object-elf.c         |  122 ++--
>  libiberty/testsuite/demangle-expected |   21 +-
>  19 files changed, 1929 insertions(+), 195 deletions(-)
>  create mode 100644 include/gcc-cp-fe.def
>  create mode 100644 include/gcc-cp-interface.h
> 
> diff --git a/gdb/ChangeLog b/gdb/ChangeLog
> index 86f1fb8..c4f55a8 100644
> --- a/gdb/ChangeLog
> +++ b/gdb/ChangeLog
> @@ -1,3 +1,8 @@
> +2017-09-15  Pedro Alves  <palves@redhat.com>
> +
> +	* compile/compile-c-types.c (convert_enum, convert_int)
> +	(convert_float): Adjust to refer to int_type_v0 and float_type_v0.
> +
>  2017-09-15  Simon Marchi  <simon.marchi@ericsson.com>
>  
>  	* dwarf2read.c (copy_string): Remove.
> diff --git a/include/ChangeLog b/include/ChangeLog
> index 3b6cea9..1ba7de3 100644
> --- a/include/ChangeLog
> +++ b/include/ChangeLog
> @@ -1,3 +1,91 @@
> +2017-09-15  Pedro Alves  <palves@redhat.com>
> +
> +	Sync with mainline gcc sources (r252823)
> +
> +	2017-09-15  Yao Qi  <yao.qi@linaro.org>
> +		    Pedro Alves  <palves@redhat.com>
> +
> +	* ansidecl.h (DISABLE_COPY_AND_ASSIGN): New macro.
> +
> +	2017-09-12  Jiong Wang  <jiong.wang@arm.com>
> +
> +	* dwarf2.def (DW_CFA_AARCH64_negate_ra_state): New DW_CFA_DUP.
> +	* dwarf2.h (DW_CFA_DUP): New define.
> +
> +	2017-08-21  Richard Biener  <rguenther@suse.de>
> +
> +	* simple-object.h (simple_object_copy_lto_debug_sections): New
> +	function.
> +
> +	2017-05-18  Martin Liska  <mliska@suse.cz>
> +
> +	* ansidecl.h: Define CONSTEXPR macro.
> +
> +	2017-05-24  Nathan Sidwell  <nathan@acm.org>
> +
> +	* libiberty.h (ASTRDUP): Adjust cast to avoid warning.
> +
> +	2017-01-30  Alexandre Oliva <aoliva@redhat.com>
> +
> +	Introduce C++ support in libcc1.
> +	* gcc-c-fe.def (int_type_v0): Rename from...
> +	(int_type): ... this.  Introduce new version.
> +	(float_type_v0): Rename from...
> +	(float_type): ... this.  Introduce new version.
> +	(char_type): New.
> +	* gcc-c-interface.h (gcc_c_api_version): Add GCC_C_FE_VERSION_1.
> +	(gcc_type_array): Move...
> +	* gcc-interface.h: ... here.
> +	* gcc-cp-fe.def: New.
> +	* gcc-cp-interface.h: New.
> +
> +	2016-04-29  Oleg Endo  <olegendo@gcc.gnu.org>
> +
> +	* longlong.h (umul_ppmm): Remove SHMEDIA checks.
> +	(__umulsidi3, count_leading_zeros): Remove SHMEDIA implementations.
> +
> +	2017-09-15  Yao Qi  <yao.qi@linaro.org>
> +	    Pedro Alves  <palves@redhat.com>
> +
> +	* ansidecl.h (DISABLE_COPY_AND_ASSIGN): New macro.
> +
> +	2017-09-12  Jiong Wang  <jiong.wang@arm.com>
> +
> +	* dwarf2.def (DW_CFA_AARCH64_negate_ra_state): New DW_CFA_DUP.
> +	* dwarf2.h (DW_CFA_DUP): New define.
> +
> +	2017-08-21  Richard Biener  <rguenther@suse.de>
> +
> +	* simple-object.h (simple_object_copy_lto_debug_sections): New
> +	function.
> +
> +	2017-05-18  Martin Liska  <mliska@suse.cz>
> +
> +	* ansidecl.h: Define CONSTEXPR macro.
> +
> +	2017-05-24  Nathan Sidwell  <nathan@acm.org>
> +
> +	* libiberty.h (ASTRDUP): Adjust cast to avoid warning.
> +
> +	2017-01-30  Alexandre Oliva <aoliva@redhat.com>
> +
> +	Introduce C++ support in libcc1.
> +	* gcc-c-fe.def (int_type_v0): Rename from...
> +	(int_type): ... this.  Introduce new version.
> +	(float_type_v0): Rename from...
> +	(float_type): ... this.  Introduce new version.
> +	(char_type): New.
> +	* gcc-c-interface.h (gcc_c_api_version): Add GCC_C_FE_VERSION_1.
> +	(gcc_type_array): Move...
> +	* gcc-interface.h: ... here.
> +	* gcc-cp-fe.def: New.
> +	* gcc-cp-interface.h: New.
> +
> +	2016-04-29  Oleg Endo  <olegendo@gcc.gnu.org>
> +
> +	* longlong.h (umul_ppmm): Remove SHMEDIA checks.
> +	(__umulsidi3, count_leading_zeros): Remove SHMEDIA implementations.
> +
>  2017-09-06  Kamil Rytarowski  <n54@gmx.com>
>  
>  	* opcode/nds32.h: Rename __BIT() to N32_BIT().
> diff --git a/libiberty/ChangeLog b/libiberty/ChangeLog
> index 8c46971..7a49a6a 100644
> --- a/libiberty/ChangeLog
> +++ b/libiberty/ChangeLog
> @@ -1,3 +1,33 @@
> +2017-09-15  Nathan Sidwell  <nathan@acm.org>
> +
> +	PR demangler/82195
> +	* cp-demangle.c (d_name): Add 'toplevel' parm.  Pass to	...
> +	(d_local_name): ... here.  Parse trailing function args on nested
> +	local_name.
> +	(d_encoding, d_special_name, d_class_enum_type): Adjust d_name calls.
> +	* testsuite/demangle-expected: Add tests.
> +
> +2017-09-15  Richard Biener  <rguenther@suse.de>
> +
> +	PR lto/81968
> +	* simple-object-elf.c (simple_object_elf_copy_lto_debug_sections):
> +	Iterate marking dependent sections necessary.
> +
> +2017-09-15  Nathan Sidwell  <nathan@acm.org>
> +
> +	* cp-demangle.c (is_fnqual_component_type): Reimplement using
> +	FNQUAL_COMPONENT_CASE.
> +	(d_encoding): Hold bare_function_type in local var.
> +	(d_local_name): Build name in both cases and build result once.
> +	Collapse switch-if to single conditional.
> +	(d_local_name): 
> +
> +	* testsuite/demangle-expected: Realign blank lines with tests.
> +
> +2017-09-12  Jiong Wang  <jiong.wang@arm.com>
> +
> +	* dwarfnames.c (DW_CFA_DUP): New define.
> +
>  2017-09-01  Martin Liska  <mliska@suse.cz>
>  
>  	* simple-object-elf.c (simple_object_elf_copy_lto_debug_sections):
> diff --git a/gdb/compile/compile-c-types.c b/gdb/compile/compile-c-types.c
> index b53a3c4..8533429 100644
> --- a/gdb/compile/compile-c-types.c
> +++ b/gdb/compile/compile-c-types.c
> @@ -207,9 +207,9 @@ convert_enum (struct compile_c_instance *context, struct type *type)
>    int i;
>    struct gcc_c_context *ctx = C_CTX (context);
>  
> -  int_type = ctx->c_ops->int_type (ctx,
> -				   TYPE_UNSIGNED (type),
> -				   TYPE_LENGTH (type));
> +  int_type = ctx->c_ops->int_type_v0 (ctx,
> +				      TYPE_UNSIGNED (type),
> +				      TYPE_LENGTH (type));
>  
>    result = ctx->c_ops->build_enum_type (ctx, int_type);
>    for (i = 0; i < TYPE_NFIELDS (type); ++i)
> @@ -273,9 +273,9 @@ convert_func (struct compile_c_instance *context, struct type *type)
>  static gcc_type
>  convert_int (struct compile_c_instance *context, struct type *type)
>  {
> -  return C_CTX (context)->c_ops->int_type (C_CTX (context),
> -					   TYPE_UNSIGNED (type),
> -					   TYPE_LENGTH (type));
> +  return C_CTX (context)->c_ops->int_type_v0 (C_CTX (context),
> +					      TYPE_UNSIGNED (type),
> +					      TYPE_LENGTH (type));
>  }
>  
>  /* Convert a floating-point type to its gcc representation.  */
> @@ -283,8 +283,8 @@ convert_int (struct compile_c_instance *context, struct type *type)
>  static gcc_type
>  convert_float (struct compile_c_instance *context, struct type *type)
>  {
> -  return C_CTX (context)->c_ops->float_type (C_CTX (context),
> -					     TYPE_LENGTH (type));
> +  return C_CTX (context)->c_ops->float_type_v0 (C_CTX (context),
> +						TYPE_LENGTH (type));
>  }
>  
>  /* Convert the 'void' type to its gcc representation.  */
> diff --git a/include/ansidecl.h b/include/ansidecl.h
> index 0a74098..450ce35 100644
> --- a/include/ansidecl.h
> +++ b/include/ansidecl.h
> @@ -252,7 +252,7 @@ So instead we use the macro below and test it against specific values.  */
>  # endif /* GNUC >= 3.0 */
>  #endif /* ATTRIBUTE_ALIGNED_ALIGNOF */
>  
> -/* Useful for structures whose layout must much some binary specification
> +/* Useful for structures whose layout must match some binary specification
>     regardless of the alignment and padding qualities of the compiler.  */
>  #ifndef ATTRIBUTE_PACKED
>  # define ATTRIBUTE_PACKED __attribute__ ((packed))
> @@ -313,6 +313,12 @@ So instead we use the macro below and test it against specific values.  */
>  #define ENUM_BITFIELD(TYPE) unsigned int
>  #endif
>  
> +#if __cpp_constexpr >= 200704
> +#define CONSTEXPR constexpr
> +#else
> +#define CONSTEXPR
> +#endif
> +
>  /* C++11 adds the ability to add "override" after an implementation of a
>     virtual function in a subclass, to:
>       (A) document that this is an override of a virtual function
> @@ -354,6 +360,32 @@ So instead we use the macro below and test it against specific values.  */
>  # define FINAL
>  #endif
>  
> +/* A macro to disable the copy constructor and assignment operator.
> +   When building with C++11 and above, the methods are explicitly
> +   deleted, causing a compile-time error if something tries to copy.
> +   For C++03, this just declares the methods, causing a link-time
> +   error if the methods end up called (assuming you don't
> +   define them).  For C++03, for best results, place the macro
> +   under the private: access specifier, like this,
> +
> +   class name_lookup
> +   {
> +     private:
> +       DISABLE_COPY_AND_ASSIGN (name_lookup);
> +   };
> +
> +   so that most attempts at copy are caught at compile-time.  */
> +
> +#if __cplusplus >= 201103
> +#define DISABLE_COPY_AND_ASSIGN(TYPE)		\
> +  TYPE (const TYPE&) = delete;			\
> +  void operator= (const TYPE &) = delete
> +  #else
> +#define DISABLE_COPY_AND_ASSIGN(TYPE)		\
> +  TYPE (const TYPE&);				\
> +  void operator= (const TYPE &)
> +#endif /* __cplusplus >= 201103 */
> +
>  #ifdef __cplusplus
>  }
>  #endif
> diff --git a/include/dwarf2.def b/include/dwarf2.def
> index a91e943..2a3b23f 100644
> --- a/include/dwarf2.def
> +++ b/include/dwarf2.def
> @@ -778,6 +778,7 @@ DW_CFA (DW_CFA_MIPS_advance_loc8, 0x1d)
>  /* GNU extensions.
>     NOTE: DW_CFA_GNU_window_save is multiplexed on Sparc and AArch64.  */
>  DW_CFA (DW_CFA_GNU_window_save, 0x2d)
> +DW_CFA_DUP (DW_CFA_AARCH64_negate_ra_state, 0x2d)
>  DW_CFA (DW_CFA_GNU_args_size, 0x2e)
>  DW_CFA (DW_CFA_GNU_negative_offset_extended, 0x2f)
>  
> diff --git a/include/dwarf2.h b/include/dwarf2.h
> index 14b6f22..a2e022d 100644
> --- a/include/dwarf2.h
> +++ b/include/dwarf2.h
> @@ -52,6 +52,7 @@
>  #define DW_ATE(name, value) , name = value
>  #define DW_ATE_DUP(name, value) , name = value
>  #define DW_CFA(name, value) , name = value
> +#define DW_CFA_DUP(name, value) , name = value
>  #define DW_IDX(name, value) , name = value
>  #define DW_IDX_DUP(name, value) , name = value
>  
> @@ -104,6 +105,7 @@
>  #undef DW_ATE
>  #undef DW_ATE_DUP
>  #undef DW_CFA
> +#undef DW_CFA_DUP
>  #undef DW_IDX
>  #undef DW_IDX_DUP
>  
> diff --git a/include/gcc-c-fe.def b/include/gcc-c-fe.def
> index 09998ba..acf1940 100644
> --- a/include/gcc-c-fe.def
> +++ b/include/gcc-c-fe.def
> @@ -125,16 +125,18 @@ GCC_METHOD3 (gcc_type, build_function_type,
>  	     const struct gcc_type_array *, /* Argument ARGUMENT_TYPES.  */
>  	     int /* bool */)               /* Argument IS_VARARGS.  */
>  
> -/* Return an integer type with the given properties.  */
> +/* Return an integer type with the given properties.
> +   Deprecated in v1, use int_type instead.  */
>  
> -GCC_METHOD2 (gcc_type, int_type,
> +GCC_METHOD2 (gcc_type, int_type_v0,
>  	     int /* bool */,               /* Argument IS_UNSIGNED.  */
>  	     unsigned long)                /* Argument SIZE_IN_BYTES.  */
>  
> -/* Return a floating point type with the given properties.  */
> +/* Return a floating point type with the given properties.
> +   Deprecated in v1, use float_type instead.  */
>  
> -GCC_METHOD1 (gcc_type, float_type,
> -	     unsigned long)			/* Argument SIZE_IN_BYTES.  */
> +GCC_METHOD1 (gcc_type, float_type_v0,
> +	     unsigned long)                /* Argument SIZE_IN_BYTES.  */
>  
>  /* Return the 'void' type.  */
>  
> @@ -195,3 +197,26 @@ GCC_METHOD5 (int /* bool */, build_constant,
>  
>  GCC_METHOD1 (gcc_type, error,
>  	     const char *)		 /* Argument MESSAGE.  */
> +
> +/* Return an integer type with the given properties.  If BUILTIN_NAME
> +   is non-NULL, it must name a builtin integral type with the given
> +   signedness and size, and that is the type that will be returned.  */
> +
> +GCC_METHOD3 (gcc_type, int_type,
> +	     int /* bool */,               /* Argument IS_UNSIGNED.  */
> +	     unsigned long,                /* Argument SIZE_IN_BYTES.  */
> +	     const char *)		   /* Argument BUILTIN_NAME.  */
> +
> +/* Return the 'char' type, a distinct type from both 'signed char' and
> +   'unsigned char' returned by int_type.  */
> +
> +GCC_METHOD0 (gcc_type, char_type)
> +
> +/* Return a floating point type with the given properties.  If BUILTIN_NAME
> +   is non-NULL, it must name a builtin integral type with the given
> +   signedness and size, and that is the type that will be returned.  */
> +
> +GCC_METHOD2 (gcc_type, float_type,
> +	     unsigned long,                /* Argument SIZE_IN_BYTES.  */
> +	     const char *)		   /* Argument BUILTIN_NAME.  */
> +
> diff --git a/include/gcc-c-interface.h b/include/gcc-c-interface.h
> index 00ccbfb..e048c86 100644
> --- a/include/gcc-c-interface.h
> +++ b/include/gcc-c-interface.h
> @@ -41,7 +41,11 @@ struct gcc_c_context;
>  
>  enum gcc_c_api_version
>  {
> -  GCC_C_FE_VERSION_0 = 0
> +  GCC_C_FE_VERSION_0 = 0,
> +
> +  /* Added char_type.  Added new version of int_type and float_type,
> +     deprecated int_type_v0 and float_type_v0.  */
> +  GCC_C_FE_VERSION_1 = 1
>  };
>  
>  /* Qualifiers.  */
> @@ -111,19 +115,6 @@ typedef gcc_address gcc_c_symbol_address_function (void *datum,
>  						   struct gcc_c_context *ctxt,
>  						   const char *identifier);
>  
> -/* An array of types used for creating a function type.  */
> -
> -struct gcc_type_array
> -{
> -  /* Number of elements.  */
> -
> -  int n_elements;
> -
> -  /* The elements.  */
> -
> -  gcc_type *elements;
> -};
> -
>  /* The vtable used by the C front end.  */
>  
>  struct gcc_c_fe_vtable
> @@ -146,7 +137,7 @@ struct gcc_c_fe_vtable
>       provides the declaration.
>  
>       DATUM is an arbitrary piece of data that is passed back verbatim
> -     to the callbakcs in requests.  */
> +     to the callbacks in requests.  */
>  
>    void (*set_callbacks) (struct gcc_c_context *self,
>  			 gcc_c_oracle_function *binding_oracle,
> diff --git a/include/gcc-cp-fe.def b/include/gcc-cp-fe.def
> new file mode 100644
> index 0000000..c367c1d
> --- /dev/null
> +++ b/include/gcc-cp-fe.def
> @@ -0,0 +1,1050 @@
> +/* Interface between GCC C++ FE and GDB  -*- c -*-
> +
> +   Copyright (C) 2014-2017 Free Software Foundation, Inc.
> +
> +   This file is part of GCC.
> +
> +   This program is free software; you can redistribute it and/or modify
> +   it under the terms of the GNU General Public License as published by
> +   the Free Software Foundation; either version 3 of the License, or
> +   (at your option) any later version.
> +
> +   This program is distributed in the hope that it will be useful,
> +   but WITHOUT ANY WARRANTY; without even the implied warranty of
> +   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
> +   GNU General Public License for more details.
> +
> +   You should have received a copy of the GNU General Public License
> +   along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
> +
> +
> +
> +/* Push namespace NAME as the current binding level, to which
> +   newly-introduced decls will be bound.  An empty string identifies
> +   the global namespace, whereas NULL identifies an anonymous
> +   namespace.  A namespace named NAME is created in the current scope,
> +   if needed.
> +
> +   If the newly-created namespace is to be an inline namespace, see
> +   make_namespace_inline.  */
> +
> +GCC_METHOD1 (int /* bool */, push_namespace,
> +	     const char *)	      /* Argument NAME.  */
> +
> +/* Push TYPE as the current binding level, making its members visible
> +   for name lookup.  The current scope before the call must be the
> +   scope in which the class was declared.  This should be used if the
> +   definition of a class is already finished, but one wishes to define
> +   a nested class, or to enter the scope of one of its member
> +   functions.  */
> +
> +GCC_METHOD1 (int /* bool */, push_class,
> +	     gcc_type)		/* Argument TYPE.  */
> +
> +/* Push FUNCTION_DECL as the current (empty) binding level (see
> +   reactivate_decl).  The current enclosing scope before the call must
> +   be the scope in which the function was declared.  */
> +
> +GCC_METHOD1 (int /* bool */, push_function,
> +	     gcc_decl)	     /* Argument FUNCTION_DECL.  */
> +
> +/* Make DECL visible (again?) within SCOPE.  When SCOPE is NULL, it
> +   means the current scope; if it is not NULL, it must name a function
> +   that is currently active, even if not at the top of the binding
> +   chain.
> +
> +   This function can be used to make e.g. a global function or
> +   variable visible in a namespace or local scope (overriding another
> +   enclosing definition of the same name), but its most common
> +   expected use of this primitive, that gives it its name, is to make
> +   declarations visible again after reentering a function scope,
> +   because when a function is entered with push_function, that does
> +   NOT make any of the declarations nested in it visible for name
> +   lookup.
> +
> +   There is a reason/excuse for that: unlike namespaces and classes,
> +   G++ doesn't ever have to reenter function scopes, so its name
> +   resolution infrastructure is not prepared to do that.  But wait,
> +   there is also a good use for this apparent limitation: a function
> +   may contain multiple scopes (blocks), and the name may be bound to
> +   different symbols in each of these scopes.  With this interface, as
> +   we reenter a function scope, we may choose which symbols to make
> +   visible for the code snippet, or, if there could be template
> +   functions in local scopes, for unresolved names in nested template
> +   class default arguments, or in nested template function signatures.
> +
> +   As for making a local declaration visible for the code snippet,
> +   there are two possibilities: a) introduce it upfront, while
> +   entering the scope for the user expression (see the enter_scope
> +   callback, called by g++ when encountering the push_user_expression
> +   pragma), which might save some scope switching and reactivate_decl
> +   (though this can't be helped if some declarations have to be
> +   introduced and discarded, because of multiple definitions of the
> +   same name in different scopes within a function: they have to be
> +   defined in discriminator order); or b) introduce it when its name
> +   is looked up, entering the scope, introducing the declaration,
> +   leaving the scope, and then reactivating the declaration in its
> +   local scope.
> +
> +   Here's some more detail on how reactivate_decl works.  Say there's
> +   a function foo whose body looks like this:
> +
> +   {
> +     {
> +// point 1
> +       class c {} o __attribute__ ((__used__)); // c  , o
> +     }
> +     struct c {
> +       void f() {
> +// point 2
> +       }
> +     } o __attribute__ ((__used__));            // c_0, o_0
> +     {
> +       class c {} p __attribute__ ((__used__)); // c_1, p
> +// point 3
> +       o.f();
> +     }
> +   }
> +
> +   When we are about to define class c at point 1, we enter the
> +   function foo scope, and since no symbols are visible at point 1, we
> +   proceed to declare class c.  We may then define the class right
> +   away, or, if we leave the function scope, and we later wish to
> +   define it, or to define object o, we can reenter the scope and just
> +   use the previously-obtained gcc_decl to define the class, without
> +   having to reactivate the declaration.
> +
> +   Now, if we are to set up the binding context for point 2, we have
> +   to define c_0::f, and in order to do so, we have to declare and
> +   define c_0.  Before we can declare c_0, we MUST at least declare c.
> +
> +     As a general rule, before we can declare or define any local name
> +     with a discriminator, we have to at least declare any other
> +     occurrences of the same name in the same enclosing entity with
> +     lower or absent discriminator.
> +
> +   So, we declare c, then we leave the function scope and reenter it
> +   so as to declare c_0 (also with name "c", which is why we have to
> +   leave and reenter the function scope, otherwise we would get an
> +   error because of the duplicate definition; g++ will assign a
> +   discriminator because it still remembers there was an earlier
> +   declaration of c_0 within the function, it's just no longer in
> +   scope), then we can define c_0, including its member function f.
> +
> +   Likewise, if we wish to define o_0, we have to define o first.  If
> +   we wish to declare (and maybe then define) c_1, we have to at least
> +   declare (c and then) c_0 first.
> +
> +   Then, as we set up the binding context to compile a code snippet at
> +   point 3, we may choose to activate c_1, o_0 and p upfront,
> +   declaring and discarding c, c_0 and o, and then reentering the
> +   funciton scope to declare c_1, o_0 and p; or we can wait for oracle
> +   lookups of c, o or p.  If c is looked up, and the debugger resolves
> +   c in the scope to c_1, it is expected to enter the function scope
> +   from the top level, declare c, leave it, reenter it, declare c_0,
> +   leave it, reenter it, declare c_1, leave it, and then reactivate
> +   c_1 in the function scope.  If c_1 is needed as a complete type,
> +   the definition may be given right after the declaration, or the
> +   scope will have to be reentered in order to define the class.
> +
> +.  If the code snippet is at point 2, we don't need to (re)activate
> +   any declaration: nothing from any local scope is visible.  Just
> +   entering the scope of the class containing member function f
> +   reactivates the names of its members, including the class name
> +   itself.  */
> +
> +GCC_METHOD2 (int /* bool */, reactivate_decl,
> +	     gcc_decl,		/* Argument DECL.  */
> +	     gcc_decl)		/* Argument SCOPE.  */
> +
> +/* Pop the namespace last entered with push_namespace, or class last
> +   entered with push_class, or function last entered with
> +   push_function, restoring the binding level in effect before the
> +   matching push_* call.  */
> +
> +GCC_METHOD0 (int /* bool */, pop_binding_level)
> +
> +/* Return the NAMESPACE_DECL, TYPE_DECL or FUNCTION_DECL of the
> +   binding level that would be popped by pop_scope.  */
> +
> +GCC_METHOD0 (gcc_decl, get_current_binding_level_decl)
> +
> +/* Make the current binding level an inline namespace.  It must be a
> +   namespace to begin with.  It is safe to call this more than once
> +   for the same namespace, but after the first call, subsequent ones
> +   will not return a success status.  */
> +
> +GCC_METHOD0 (int /* bool */, make_namespace_inline)
> +
> +/* Add USED_NS to the namespaces used by the current binding level.
> +   Use get_current_binding_level_decl to obtain USED_NS's
> +   gcc_decl.  */
> +
> +GCC_METHOD1 (int /* bool */, add_using_namespace,
> +	     gcc_decl)			/* Argument USED_NS.  */
> +
> +/* Introduce a namespace alias declaration, as in:
> +
> +   namespace foo = [... ::] bar;
> +
> +   After this call, namespace TARGET will be visible as ALIAS within
> +   the current namespace.  Get the declaration for TARGET by calling
> +   get_current_binding_level_decl after pushing into it.  */
> +
> +GCC_METHOD2 (int /* bool */, add_namespace_alias,
> +	     const char *,		/* Argument ALIAS.  */
> +	     gcc_decl)			/* Argument TARGET.  */
> +
> +/* Introduce a using declaration, as in:
> +
> +   using foo::bar;
> +
> +   The TARGET decl names the qualifying scope (foo:: above) and the
> +   identifier (bar), but that does not mean that only TARGET will be
> +   brought into the current scope: all bindings of TARGET's identifier
> +   in the qualifying scope will be brought in.
> +
> +   FLAGS should specify GCC_CP_SYMBOL_USING.  If the current scope is
> +   a class scope, visibility flags must be supplied.
> +
> +   Even when TARGET is template dependent, we don't need to specify
> +   whether or not it is a typename: the supplied declaration (that
> +   could be a template-dependent type converted to declaration by
> +   get_type_decl) indicates so.  */
> +
> +GCC_METHOD2 (int /* bool */, add_using_decl,
> +	     enum gcc_cp_symbol_kind, /* Argument FLAGS.  */
> +	     gcc_decl)		      /* Argument TARGET.  */
> +
> +/* Create a new "decl" in GCC, and bind it in the current binding
> +   level.  A decl is a declaration, basically a kind of symbol.
> +
> +   NAME is the name of the new symbol.  SYM_KIND is the kind of
> +   symbol being requested.  SYM_TYPE is the new symbol's C++ type;
> +   except for labels, where this is not meaningful and should be
> +   zero.  If SUBSTITUTION_NAME is not NULL, then a reference to this
> +   decl in the source will later be substituted with a dereference
> +   of a variable of the given name.  Otherwise, for symbols having
> +   an address (e.g., functions), ADDRESS is the address.  FILENAME
> +   and LINE_NUMBER refer to the symbol's source location.  If this
> +   is not known, FILENAME can be NULL and LINE_NUMBER can be 0.
> +   This function returns the new decl.
> +
> +   Use this function to register typedefs, functions and variables to
> +   namespace and local binding levels, and typedefs, member functions
> +   (static or not), and static data members to class binding levels.
> +   Class members must have their access controls specified with
> +   GCC_CP_ACCESS_* flags in SYM_KIND.
> +
> +   Note that, since access controls are disabled, we have no means to
> +   express private, protected and public.
> +
> +   There are various flags that can be set in SYM_KIND to specify
> +   additional semantics.  Look for GCC_CP_FLAGs in the definition of
> +   enum gcc_cp_symbol_kind in gcc-cp-interface.h.
> +
> +   In order to define member functions, pass GCC_CP_SYMBOL_FUNCTION in
> +   SYM_KIND, and a function_type for static member functions or a
> +   method type for non-static member functions, including constructors
> +   and destructors.  Use build_function_type to create a function
> +   type; for a method type, start by creating a function type without
> +   any compiler-introduced artificial arguments (the implicit this
> +   pointer, and the __in_chrg added to constructors and destructors,
> +   and __vtt_parm added to the former), and then use build_method_type
> +   to create the method type out of the class type and the function
> +   type.
> +
> +   For operator functions, set GCC_CP_FLAG_SPECIAL_FUNCTION in
> +   SYM_KIND, in addition to any other applicable flags, and pass as
> +   NAME a string starting with the two-character mangling for operator
> +   name: "ps" for unary plus, "mL" for multiply and assign, *=; etc.
> +   Use "cv" for type converstion operators (the target type portion
> +   may be omitted, as it is taken from the return type in SYM_TYPE).
> +   For operator"", use "li" followed by the identifier (the mangled
> +   name mandates digits specifying the length of the identifier; if
> +   present, they determine the end of the identifier, otherwise, the
> +   identifier extents to the end of the string, so that "li3_Kme" and
> +   "li_Km" are equivalent).
> +
> +   Constructors and destructors need special care, because for each
> +   constructor and destructor there may be multiple clones defined
> +   internally by the compiler.  With build_decl, you can introduce the
> +   base declaration of a constructor or a destructor, setting
> +   GCC_CP_FLAG_SPECIAL_FUNCTION the flag and using names starting with
> +   capital "C" or "D", respectively, followed by a digit (see below),
> +   a blank, or NUL ('\0').  DO NOT supply an ADDRESS or a
> +   SUBSTITUTION_NAME to build_decl, it would be meaningless (and
> +   rejected) for the base declaration; use define_cdtor_clone to
> +   introduce the address of each clone.  For constructor templates,
> +   declare the template with build_decl, and then, for each
> +   specialization, introduce it with
> +   build_function_template_specialization, and then define the
> +   addresses of each of its clones with define_cdtor_clone.
> +
> +   NAMEs for GCC_CP_FLAG_SPECIAL_FUNCTION:
> +
> +     NAME    meaning
> +     C?      constructor base declaration (? may be 1, 2, 4, blank or NUL)
> +     D?      destructor base declaration (? may be 0, 1, 2, 4, blank or NUL)
> +     nw      operator new
> +     na      operator new[]
> +     dl      operator delete
> +     da      operator delete[]
> +     ps      operator + (unary)
> +     ng      operator - (unary)
> +     ad      operator & (unary)
> +     de      operator * (unary)
> +     co      operator ~
> +     pl      operator +
> +     mi      operator -
> +     ml      operator *
> +     dv      operator /
> +     rm      operator %
> +     an      operator &
> +     or      operator |
> +     eo      operator ^
> +     aS      operator =
> +     pL      operator +=
> +     mI      operator -=
> +     mL      operator *=
> +     dV      operator /=
> +     rM      operator %=
> +     aN      operator &=
> +     oR      operator |=
> +     eO      operator ^=
> +     ls      operator <<
> +     rs      operator >>
> +     lS      operator <<=
> +     rS      operator >>=
> +     eq      operator ==
> +     ne      operator !=
> +     lt      operator <
> +     gt      operator >
> +     le      operator <=
> +     ge      operator >=
> +     nt      operator !
> +     aa      operator &&
> +     oo      operator ||
> +     pp      operator ++
> +     mm      operator --
> +     cm      operator ,
> +     pm      operator ->*
> +     pt      operator ->
> +     cl      operator ()
> +     ix      operator []
> +     qu      operator ?
> +     cv      operator <T> (conversion operator)
> +     li<id>  operator "" <id>
> +
> +   FIXME: How about attributes?  */
> +
> +GCC_METHOD7 (gcc_decl, build_decl,
> +	     const char *,	      /* Argument NAME.  */
> +	     enum gcc_cp_symbol_kind, /* Argument SYM_KIND.  */
> +	     gcc_type,		      /* Argument SYM_TYPE.  */
> +	     const char *,	      /* Argument SUBSTITUTION_NAME.  */
> +	     gcc_address,	      /* Argument ADDRESS.  */
> +	     const char *,	      /* Argument FILENAME.  */
> +	     unsigned int)	      /* Argument LINE_NUMBER.  */
> +
> +/* Supply the ADDRESS of one of the multiple clones of constructor or
> +   destructor CDTOR.  The clone is specified by NAME, using the
> +   following name mangling conventions:
> +
> +     C1      in-charge constructor
> +     C2      not-in-charge constructor
> +     C4      unified constructor
> +     D0      deleting destructor
> +     D1      in-charge destructor
> +     D2      not-in-charge destructor
> +     D4      unified destructor
> +
> +   The following information is not necessary to use the API.
> +
> +   C1 initializes an instance of the class (rather than of derived
> +   classes), including virtual base classes, whereas C2 initializes a
> +   sub-object (of the given class type) of an instance of some derived
> +   class (or a full object that doesn't have any virtual base
> +   classes).
> +
> +   D0 and D1 destruct an instance of the class, including virtual base
> +   classes, but only the former calls operator delete to release the
> +   object's storage at the end; D2 destructs a sub-object (of the
> +   given class type) of an instance of a derived class (or a full
> +   object that doesn't have any virtual base classes).
> +
> +   The [CD]4 manglings (and symbol definitions) are non-standard, but
> +   GCC uses them in some cases: rather than assuming they are
> +   in-charge or not-in-charge, they test the implicit argument that
> +   the others ignore to tell how to behave.  These are used instead of
> +   cloning when we just can't use aliases.  */
> +
> +GCC_METHOD3 (gcc_decl, define_cdtor_clone,
> +	     const char *,	      /* Argument NAME.  */
> +	     gcc_decl,		      /* Argument CDTOR.  */
> +	     gcc_address)	      /* Argument ADDRESS.  */
> +
> +/* Return the type associated with the given declaration.  This is
> +   most useful to obtain the type associated with a forward-declared
> +   class, because it is the gcc_type, rather than the gcc_decl, that
> +   has to be used to build other types, but build_decl returns a
> +   gcc_decl rather than a gcc_type.  This call can in theory be used
> +   to obtain the type from any other declaration; it is supposed to
> +   return the same type that was supplied when the declaration was
> +   created.  */
> +
> +GCC_METHOD1 (gcc_type, get_decl_type,
> +	     gcc_decl)            /* Argument DECL.  */
> +
> +/* Return the declaration for a type.  */
> +
> +GCC_METHOD1 (gcc_decl, get_type_decl,
> +	     gcc_type)            /* Argument TYPE.  */
> +
> +/* Declare DECL as a friend of the current class scope, if TYPE is
> +   NULL, or of TYPE itself otherwise.  DECL may be a function or a
> +   class, be they template generics, template specializations or not
> +   templates.  TYPE must be a class type (not a template generic).
> +
> +   The add_friend call cannot introduce a declaration; even if the
> +   friend is first declared as a friend in the source code, the
> +   declaration belongs in the enclosing namespace, so it must be
> +   introduced in that namespace, and the resulting declaration can
> +   then be made a friend.
> +
> +   DECL cannot, however, be a member of a template class generic,
> +   because we have no means to introduce their declarations.  This
> +   interface has no notion of definitions for template generics.  As a
> +   consequence, users of this interface must introduce each friend
> +   template member specialization separately, i.e., instead of:
> +
> +     template <typename T> friend struct X<T>::M;
> +
> +   they must be declared as if they were:
> +
> +     friend struct X<onetype>::M;
> +     friend struct X<anothertype>::M;
> +     ... for each specialization of X.
> +
> +
> +   Specializations of a template can have each others' members as
> +   friends:
> +
> +     template <typename T> class foo {
> +       int f();
> +       template <typename U> friend int foo<U>::f();
> +     };
> +
> +   It wouldn't always be possible to define all specializations of a
> +   template class before introducing the friend declarations in their
> +   expanded, per-specialization form.
> +
> +   In order to simplify such friend declarations, and to enable
> +   incremental friend declarations as template specializations are
> +   introduced, add_friend can be called after the befriending class is
> +   fully defined, passing it a non-NULL TYPE argument naming the
> +   befriending class type.  */
> +
> +GCC_METHOD2 (int /* bool */, add_friend,
> +	     gcc_decl,		      /* Argument DECL.  */
> +	     gcc_type)		      /* Argument TYPE.  */
> +
> +/* Return the type of a pointer to a given base type.  */
> +
> +GCC_METHOD1 (gcc_type, build_pointer_type,
> +	     gcc_type)			/* Argument BASE_TYPE.  */
> +
> +/* Return the type of a reference to a given base type.  */
> +
> +GCC_METHOD2 (gcc_type, build_reference_type,
> +	     gcc_type,			/* Argument BASE_TYPE.  */
> +	     enum gcc_cp_ref_qualifiers)   /* Argument RQUALS.  */
> +
> +/* Create a new pointer-to-member type.  MEMBER_TYPE is the data
> +   member type, while CLASS_TYPE is the class type containing the data
> +   member.  For pointers to member functions, MEMBER_TYPE must be a
> +   method type, and CLASS_TYPE must be specified even though it might
> +   be possible to extract it from the method type.  */
> +
> +GCC_METHOD2 (gcc_type, build_pointer_to_member_type,
> +	     gcc_type,			   /* Argument CLASS_TYPE.  */
> +	     gcc_type) 			   /* Argument MEMBER_TYPE.  */
> +
> +/* Start a template parameter list scope and enters it, so that
> +   subsequent build_type_template_parameter and
> +   build_value_template_parameter calls create template parameters in
> +   the list.  The list is closed by a build_decl call with
> +   GCC_CP_SYMBOL_FUNCTION or GCC_CP_SYMBOL_CLASS, that, when the scope
> +   is a template parameter list, declares a template function or a
> +   template class with the then-closed parameter list.  The scope in
> +   which the new declaration is to be introduced by build_decl must be
> +   entered before calling start_template_decl, and build_decl returns
> +   to that scope, from the template parameter list scope, before
> +   introducing the declaration.  */
> +
> +GCC_METHOD0 (int /* bool */, start_template_decl)
> +
> +/* Build a typename template-parameter (e.g., the T in template
> +   <typename T = X>).  Either PACK_P should be nonzero, to indicate an
> +   argument pack (the last argument in a variadic template argument
> +   list, as in template <typename... T>), or DEFAULT_TYPE may be
> +   non-NULL to set the default type argument (e.g. X) for the template
> +   parameter.  FILENAME and LINE_NUMBER may specify the source
> +   location in which the template parameter was declared.  */
> +
> +GCC_METHOD5 (gcc_type, build_type_template_parameter,
> +	     const char *,			      /* Argument ID.  */
> +	     int /* bool */,			  /* Argument PACK_P.  */
> +	     gcc_type,			    /* Argument DEFAULT_TYPE.  */
> +	     const char *,			/* Argument FILENAME.  */
> +	     unsigned int)		     /* Argument LINE_NUMBER.  */
> +
> +/* Build a template template-parameter (e.g., the T in template
> +   <template <[...]> class T = X>).  DEFAULT_TEMPL may be non-NULL to
> +   set the default type-template argument (e.g. X) for the template
> +   template parameter.  FILENAME and LINE_NUMBER may specify the
> +   source location in which the template parameter was declared.  */
> +
> +GCC_METHOD5 (gcc_utempl, build_template_template_parameter,
> +	     const char *,			      /* Argument ID.  */
> +	     int /* bool */,			  /* Argument PACK_P.  */
> +	     gcc_utempl,		   /* Argument DEFAULT_TEMPL.  */
> +	     const char *,			/* Argument FILENAME.  */
> +	     unsigned int)		     /* Argument LINE_NUMBER.  */
> +
> +/* Build a value template-parameter (e.g., the V in template <typename
> +   T, T V> or in template <int V = X>).  DEFAULT_VALUE may be non-NULL
> +   to set the default value argument for the template parameter (e.g.,
> +   X).  FILENAME and LINE_NUMBER may specify the source location in
> +   which the template parameter was declared.  */
> +
> +GCC_METHOD5 (gcc_decl, build_value_template_parameter,
> +	     gcc_type,			  	    /* Argument TYPE.  */
> +	     const char *,			      /* Argument ID.  */
> +	     gcc_expr,			   /* Argument DEFAULT_VALUE.  */
> +	     const char *,			/* Argument FILENAME.  */
> +	     unsigned int)		     /* Argument LINE_NUMBER.  */
> +
> +/* Build a template-dependent typename (e.g., typename T::bar or
> +   typename T::template bart<X>).  ENCLOSING_TYPE should be the
> +   template-dependent nested name specifier (e.g., T), ID should be
> +   the name of the member of the ENCLOSING_TYPE (e.g., bar or bart),
> +   and TARGS should be non-NULL and specify the template arguments
> +   (e.g. <X>) iff ID is to name a class template.
> +
> +   In this and other calls, a template-dependent nested name specifier
> +   may be a template class parameter (build_type_template_parameter),
> +   a specialization (returned by build_dependent_type_template_id) of
> +   a template template parameter (returned by
> +   build_template_template_parameter) or a member type thereof
> +   (returned by build_dependent_typename itself).  */
> +
> +GCC_METHOD3 (gcc_type, build_dependent_typename,
> +	     gcc_type,			  /* Argument ENCLOSING_TYPE.  */
> +	     const char *,			      /* Argument ID.  */
> +	     const struct gcc_cp_template_args *)  /* Argument TARGS.  */
> +
> +/* Build a template-dependent class template (e.g., T::template bart).
> +   ENCLOSING_TYPE should be the template-dependent nested name
> +   specifier (e.g., T), ID should be the name of the class template
> +   member of the ENCLOSING_TYPE (e.g., bart).  */
> +
> +GCC_METHOD2 (gcc_utempl, build_dependent_class_template,
> +	     gcc_type,			  /* Argument ENCLOSING_TYPE.  */
> +	     const char *)			      /* Argument ID.  */
> +
> +/* Build a template-dependent type template-id (e.g., T<A>).
> +   TEMPLATE_DECL should be a template template parameter (e.g., the T
> +   in template <template <[...]> class T = X>), and TARGS should
> +   specify the template arguments (e.g. <A>).  */
> +
> +GCC_METHOD2 (gcc_type, build_dependent_type_template_id,
> +	     gcc_utempl,		   /* Argument TEMPLATE_DECL.  */
> +	     const struct gcc_cp_template_args *)  /* Argument TARGS.  */
> +
> +/* Build a template-dependent expression (e.g., S::val or S::template
> +   mtf<X>, or unqualified f or template tf<X>).
> +
> +   ENCLOSING_SCOPE should be a template-dependent nested name
> +   specifier (e.g., T), a resolved namespace or class decl, or NULL
> +   for unqualified names; ID should be the name of the member of the
> +   ENCLOSING_SCOPE (e.g., val or mtf) or unqualified overloaded
> +   function; and TARGS should list template arguments (e.g. <X>) when
> +   mtf or tf are to name a template function, or be NULL otherwise.
> +
> +   Unqualified names and namespace- or class-qualified names can only
> +   resolve to overloaded functions, to be used in contexts that
> +   involve overload resolution that cannot be resolved because of
> +   template-dependent argument or return types, such as call
> +   expressions with template-dependent arguments, conversion
> +   expressions to function types with template-dependent argument
> +   types or the like.  Other cases of unqualified or
> +   non-template-dependent-qualified names should NOT use this
> +   function, and use decl_expr to convert the appropriate function or
> +   object declaration to an expression.
> +
> +   If ID is the name of a special member function, FLAGS should be
> +   GCC_CP_SYMBOL_FUNCTION|GCC_CP_FLAG_SPECIAL_FUNCTION, and ID should
> +   be one of the encodings for special member functions documented in
> +   build_decl.  Otherwise, FLAGS should be GCC_CP_SYMBOL_MASK, which
> +   suggests the symbol kind is not known (though we know it is not a
> +   type).
> +
> +   If ID denotes a conversion operator, CONV_TYPE should name the
> +   target type of the conversion.  Otherwise, CONV_TYPE must be
> +   NULL.  */
> +
> +GCC_METHOD5 (gcc_expr, build_dependent_expr,
> +	     gcc_decl,			 /* Argument ENCLOSING_SCOPE.  */
> +	     enum gcc_cp_symbol_kind,		   /* Argument FLAGS.  */
> +	     const char *,			    /* Argument NAME.  */
> +	     gcc_type,			       /* Argument CONV_TYPE.  */
> +	     const struct gcc_cp_template_args *)  /* Argument TARGS.  */
> +
> +/* Build a gcc_expr for the value VALUE in type TYPE.  */
> +
> +GCC_METHOD2 (gcc_expr, build_literal_expr,
> +	     gcc_type,		  /* Argument TYPE.  */
> +	     unsigned long)	  /* Argument VALUE.  */
> +
> +/* Build a gcc_expr that denotes DECL, the declaration of a variable
> +   or function in namespace scope, or of a static member variable or
> +   function.  Use QUALIFIED_P to build the operand of unary & so as to
> +   compute a pointer-to-member, rather than a regular pointer.  */
> +
> +GCC_METHOD2 (gcc_expr, build_decl_expr,
> +	     gcc_decl,			/* Argument DECL.  */
> +	     int /* bool */)		/* Argument QUALIFIED_P.  */
> +
> +/* Build a gcc_expr that denotes the unary operation UNARY_OP applied
> +   to the gcc_expr OPERAND.  For non-expr operands, see
> +   unary_type_expr.  Besides the UNARY_OP encodings used for operator
> +   names, we support "pp_" for preincrement, and "mm_" for
> +   predecrement, "nx" for noexcept, "tw" for throw, "tr" for rethrow
> +   (pass NULL as the operand), "te" for typeid, "sz" for sizeof, "az"
> +   for alignof, "dl" for delete, "gsdl" for ::delete, "da" for
> +   delete[], "gsda" for ::delete[], "sp" for pack expansion, "sZ" for
> +   sizeof...(function argument pack).  */
> +
> +GCC_METHOD2 (gcc_expr, build_unary_expr,
> +	     const char *,	  /* Argument UNARY_OP.  */
> +	     gcc_expr)		  /* Argument OPERAND.  */
> +
> +/* Build a gcc_expr that denotes the binary operation BINARY_OP
> +   applied to gcc_exprs OPERAND1 and OPERAND2.  Besides the BINARY_OP
> +   encodings used for operator names, we support "ds" for the operator
> +   token ".*" and "dt" for the operator token ".".  When using
> +   operators that take a name as their second operand ("." and "->")
> +   use decl_expr to convert the gcc_decl of the member name to a
> +   gcc_expr, if the member name wasn't created with
> +   e.g. build_dependent_expr.  */
> +
> +GCC_METHOD3 (gcc_expr, build_binary_expr,
> +	     const char *,	  /* Argument BINARY_OP.  */
> +	     gcc_expr,		  /* Argument OPERAND1.  */
> +	     gcc_expr)		  /* Argument OPERAND2.  */
> +
> +/* Build a gcc_expr that denotes the ternary operation TERNARY_OP
> +   applied to gcc_exprs OPERAND1, OPERAND2 and OPERAND3.  The only
> +   supported TERNARY_OP is "qu", for the "?:" operator.  */
> +
> +GCC_METHOD4 (gcc_expr, build_ternary_expr,
> +	     const char *,	  /* Argument TERNARY_OP.  */
> +	     gcc_expr,		  /* Argument OPERAND1.  */
> +	     gcc_expr,		  /* Argument OPERAND2.  */
> +	     gcc_expr)		  /* Argument OPERAND3.  */
> +
> +/* Build a gcc_expr that denotes the unary operation UNARY_OP applied
> +   to the gcc_type OPERAND.  Supported unary operations taking types
> +   are "ti" for typeid, "st" for sizeof, "at" for alignof, and "sZ"
> +   for sizeof...(template argument pack).  */
> +
> +GCC_METHOD2 (gcc_expr, build_unary_type_expr,
> +	     const char *,	  /* Argument UNARY_OP.  */
> +	     gcc_type)		  /* Argument OPERAND.  */
> +
> +/* Build a gcc_expr that denotes the binary operation BINARY_OP
> +   applied to gcc_type OPERAND1 and gcc_expr OPERAND2.  Use this for
> +   all kinds of (single-argument) type casts ("dc", "sc", "cc", "rc"
> +   for dynamic, static, const and reinterpret casts, respectively;
> +   "cv" for functional or C-style casts).  */
> +
> +GCC_METHOD3 (gcc_expr, build_cast_expr,
> +	     const char *,	  /* Argument BINARY_OP.  */
> +	     gcc_type,		  /* Argument OPERAND1.  */
> +	     gcc_expr)		  /* Argument OPERAND2.  */
> +
> +/* Build a gcc_expr that denotes the conversion of an expression list
> +   VALUES to TYPE, with ("tl") or without ("cv") braces, or a braced
> +   initializer list of unspecified type (e.g., a component of another
> +   braced initializer list; pass "il" for CONV_OP, and NULL for
> +   TYPE).  */
> +
> +GCC_METHOD3 (gcc_expr, build_expression_list_expr,
> +	     const char *,			 /* Argument CONV_OP.  */
> +	     gcc_type,				    /* Argument TYPE.  */
> +	     const struct gcc_cp_function_args *) /* Argument VALUES.  */
> +
> +/* Build a gcc_expr that denotes a new ("nw") or new[] ("na")
> +   expression of TYPE, with or without a GLOBAL_NS qualifier (prefix
> +   the NEW_OP with "gs"), with or without PLACEMENT, with or without
> +   INITIALIZER.  If it's not a placement new, PLACEMENT must be NULL
> +   (rather than a zero-length placement arg list).  If there's no
> +   specified initializer, INITIALIZER must be NULL; a zero-length arg
> +   list stands for a default initializer.  */
> +
> +GCC_METHOD4 (gcc_expr, build_new_expr,
> +	     const char *,			       /* Argument NEW_OP.  */
> +	     const struct gcc_cp_function_args *,   /* Argument PLACEMENT.  */
> +	     gcc_type,					 /* Argument TYPE.  */
> +	     const struct gcc_cp_function_args *) /* Argument INITIALIZER.  */
> +
> +/* Return a call expression that calls CALLABLE with arguments ARGS.
> +   CALLABLE may be a function, a callable object, a pointer to
> +   function, an unresolved expression, an unresolved overload set, an
> +   object expression combined with a member function overload set or a
> +   pointer-to-member.  If QUALIFIED_P, CALLABLE will be interpreted as
> +   a qualified name, preventing virtual function dispatch.  */
> +
> +GCC_METHOD3 (gcc_expr, build_call_expr,
> +	     gcc_expr,			      /* Argument CALLABLE.  */
> +	     int /* bool */,		   /* Argument QUALIFIED_P.  */
> +	     const struct gcc_cp_function_args *) /* Argument ARGS.  */
> +
> +/* Return the type of the gcc_expr OPERAND.
> +   Use this for decltype.
> +   For decltype (auto), pass a NULL OPERAND.
> +
> +   Note: for template-dependent expressions, the result is NULL,
> +   because the type is only computed when template argument
> +   substitution is performed.  */
> +
> +GCC_METHOD1 (gcc_type, get_expr_type,
> +	     gcc_expr)		  /* Argument OPERAND.  */
> +
> +/* Introduce a specialization of a template function.
> +
> +   TEMPLATE_DECL is the template function, and TARGS are the arguments
> +   for the specialization.  ADDRESS is the address of the
> +   specialization.  FILENAME and LINE_NUMBER specify the source
> +   location associated with the template function specialization.  */
> +
> +GCC_METHOD5 (gcc_decl, build_function_template_specialization,
> +	     gcc_decl,			   /* Argument TEMPLATE_DECL.  */
> +	     const struct gcc_cp_template_args *,  /* Argument TARGS.  */
> +	     gcc_address,			 /* Argument ADDRESS.  */
> +	     const char *,	      /* Argument FILENAME.  */
> +	     unsigned int)	      /* Argument LINE_NUMBER.  */
> +
> +/* Specialize a template class as an incomplete type.  A definition
> +   can be supplied later, with start_class_type.
> +
> +   TEMPLATE_DECL is the template class, and TARGS are the arguments
> +   for the specialization.  FILENAME and LINE_NUMBER specify the
> +   source location associated with the template class
> +   specialization.  */
> +
> +GCC_METHOD4 (gcc_decl, build_class_template_specialization,
> +	     gcc_decl,			   /* Argument TEMPLATE_DECL.  */
> +	     const struct gcc_cp_template_args *,  /* Argument TARGS.  */
> +	     const char *,	      /* Argument FILENAME.  */
> +	     unsigned int)	      /* Argument LINE_NUMBER.  */
> +
> +/* Start defining a 'class', 'struct' or 'union' type, entering its
> +   own binding level.  Initially it has no fields.
> +
> +   TYPEDECL is the forward-declaration of the type, returned by
> +   build_decl.  BASE_CLASSES indicate the base classes of class NAME.
> +   FILENAME and LINE_NUMBER specify the source location associated
> +   with the class definition, should they be different from those of
> +   the forward declaration.  */
> +
> +GCC_METHOD4 (gcc_type, start_class_type,
> +	     gcc_decl,		      /* Argument TYPEDECL.  */
> +	     const struct gcc_vbase_array *,/* Argument BASE_CLASSES.  */
> +	     const char *,	      /* Argument FILENAME.  */
> +	     unsigned int)	      /* Argument LINE_NUMBER.  */
> +
> +/* Create a new closure class type, record it as the
> +   DISCRIMINATOR-numbered closure type in the current scope (or
> +   associated with EXTRA_SCOPE, if non-NULL), and enter the closure
> +   type's own binding level.  This primitive would sort of combine
> +   build_decl and start_class_type, if they could be used to introduce
> +   a closure type.  Initially it has no fields.
> +
> +   FILENAME and LINE_NUMBER specify the source location associated
> +   with the class.  EXTRA_SCOPE, if non-NULL, must be a PARM_DECL of
> +   the current function, or a FIELD_DECL of the current class.  If it
> +   is NULL, the current scope must be a function.  */
> +
> +GCC_METHOD5 (gcc_type, start_closure_class_type,
> +	     int,		      /* Argument DISCRIMINATOR.  */
> +	     gcc_decl,		      /* Argument EXTRA_SCOPE.  */
> +	     enum gcc_cp_symbol_kind, /* Argument FLAGS.  */
> +	     const char *,	      /* Argument FILENAME.  */
> +	     unsigned int)	      /* Argument LINE_NUMBER.  */
> +
> +/* Add a non-static data member to the most-recently-started
> +   unfinished struct or union type.  FIELD_NAME is the field's name.
> +   FIELD_TYPE is the type of the field.  BITSIZE and BITPOS indicate
> +   where in the struct the field occurs.  */
> +
> +GCC_METHOD5 (gcc_decl, build_field,
> +	     const char *,		   /* Argument FIELD_NAME.  */
> +	     gcc_type,			   /* Argument FIELD_TYPE.  */
> +	     enum gcc_cp_symbol_kind,	   /* Argument FIELD_FLAGS.  */
> +	     unsigned long,		   /* Argument BITSIZE.  */
> +	     unsigned long)		   /* Argument BITPOS.  */
> +
> +/* After all the fields have been added to a struct, class or union,
> +   the struct or union type must be "finished".  This does some final
> +   cleanups in GCC, and pops to the binding level that was in effect
> +   before the matching start_class_type or
> +   start_closure_class_type.  */
> +
> +GCC_METHOD1 (int /* bool */, finish_class_type,
> +	     unsigned long)		   /* Argument SIZE_IN_BYTES.  */
> +
> +/* Create a new 'enum' type, and record it in the current binding
> +   level.  The new type initially has no associated constants.
> +
> +   NAME is the enum name.  FILENAME and LINE_NUMBER specify its source
> +   location.  */
> +
> +GCC_METHOD5 (gcc_type, start_enum_type,
> +	     const char *,	      /* Argument NAME.  */
> +	     gcc_type,		      /* Argument UNDERLYING_INT_TYPE. */
> +	     enum gcc_cp_symbol_kind, /* Argument FLAGS.  */
> +	     const char *,	      /* Argument FILENAME.  */
> +	     unsigned int)	      /* Argument LINE_NUMBER.  */
> +
> +/* Add a new constant to an enum type.  NAME is the constant's name
> +   and VALUE is its value.  Returns a gcc_decl for the constant.  */
> +
> +GCC_METHOD3 (gcc_decl, build_enum_constant,
> +	     gcc_type,		       /* Argument ENUM_TYPE.  */
> +	     const char *,	       /* Argument NAME.  */
> +	     unsigned long)	       /* Argument VALUE.  */
> +
> +/* After all the constants have been added to an enum, the type must
> +   be "finished".  This does some final cleanups in GCC.  */
> +
> +GCC_METHOD1 (int /* bool */, finish_enum_type,
> +	     gcc_type)		       /* Argument ENUM_TYPE.  */
> +
> +/* Create a new function type.  RETURN_TYPE is the type returned by
> +   the function, and ARGUMENT_TYPES is a vector, of length NARGS, of
> +   the argument types.  IS_VARARGS is true if the function is
> +   varargs.  */
> +
> +GCC_METHOD3 (gcc_type, build_function_type,
> +	     gcc_type,			   /* Argument RETURN_TYPE.  */
> +	     const struct gcc_type_array *,/* Argument ARGUMENT_TYPES.  */
> +	     int /* bool */)		   /* Argument IS_VARARGS.  */
> +
> +/* Create a variant of a function type with an exception
> +   specification.  FUNCTION_TYPE is a function or method type.
> +   EXCEPT_TYPES is an array with the list of exception types.  Zero as
> +   the array length implies throw() AKA noexcept(true); NULL as the
> +   pointer to gcc_type_array implies noexcept(false), which is almost
> +   equivalent (but distinguishable by the compiler) to an unspecified
> +   exception list.  */
> +
> +GCC_METHOD2 (gcc_type, build_exception_spec_variant,
> +	     gcc_type,			   /* Argument FUNCTION_TYPE.  */
> +	     const struct gcc_type_array *)/* Argument EXCEPT_TYPES.  */
> +
> +/* Create a new non-static member function type.  FUNC_TYPE is the
> +   method prototype, without the implicit THIS pointer, added as a
> +   pointer to the QUALS-qualified CLASS_TYPE.  If CLASS_TYPE is NULL,
> +   this creates a cv-qualified (member) function type not associated
> +   with any specific class, as needed to support "typedef void f(int)
> +   const;", which can later be used to declare member functions and
> +   pointers to member functions.  */
> +
> +GCC_METHOD4 (gcc_type, build_method_type,
> +	     gcc_type,			   /* Argument CLASS_TYPE.  */
> +	     gcc_type, 			   /* Argument FUNC_TYPE.  */
> +	     enum gcc_cp_qualifiers,	   /* Argument QUALS.  */
> +	     enum gcc_cp_ref_qualifiers)   /* Argument RQUALS.  */
> +
> +/* Return a declaration for the (INDEX - 1)th argument of
> +   FUNCTION_DECL, i.e., for the first argument, use zero as the index.
> +   If FUNCTION_DECL is a non-static member function, use -1 to get the
> +   implicit THIS parameter.  */
> +
> +GCC_METHOD2 (gcc_decl, get_function_parameter_decl,
> +	     gcc_decl,			     /* Argument FUNCTION_DECL.  */
> +	     int)				     /* Argument INDEX.  */
> +
> +/* Return a lambda expr that constructs an instance of CLOSURE_TYPE.
> +   Only lambda exprs without any captures can be correctly created
> +   through these mechanisms; that's all we need to support lambdas
> +   expressions in default parameters, the only kind that may have to
> +   be introduced through this interface.  */
> +
> +GCC_METHOD1 (gcc_expr, build_lambda_expr,
> +	     gcc_type)			      /* Argument CLOSURE_TYPE.  */
> +
> +/* Return an integer type with the given properties.  If BUILTIN_NAME
> +   is non-NULL, it must name a builtin integral type with the given
> +   signedness and size, and that is the type that will be returned.  */
> +
> +GCC_METHOD3 (gcc_type, get_int_type,
> +	     int /* bool */,		   /* Argument IS_UNSIGNED.  */
> +	     unsigned long,                /* Argument SIZE_IN_BYTES.  */
> +	     const char *)		   /* Argument BUILTIN_NAME.  */
> +
> +/* Return the 'char' type, a distinct type from both 'signed char' and
> +   'unsigned char' returned by int_type.  */
> +
> +GCC_METHOD0 (gcc_type, get_char_type)
> +
> +/* Return a floating point type with the given properties.  If BUILTIN_NAME
> +   is non-NULL, it must name a builtin integral type with the given
> +   signedness and size, and that is the type that will be returned.  */
> +
> +GCC_METHOD2 (gcc_type, get_float_type,
> +	     unsigned long,                /* Argument SIZE_IN_BYTES.  */
> +	     const char *)		   /* Argument BUILTIN_NAME.  */
> +
> +/* Return the 'void' type.  */
> +
> +GCC_METHOD0 (gcc_type, get_void_type)
> +
> +/* Return the 'bool' type.  */
> +
> +GCC_METHOD0 (gcc_type, get_bool_type)
> +
> +/* Return the std::nullptr_t type.  */
> +
> +GCC_METHOD0 (gcc_type, get_nullptr_type)
> +
> +/* Return the nullptr constant.  */
> +
> +GCC_METHOD0 (gcc_expr, get_nullptr_constant)
> +
> +/* Create a new array type.  If NUM_ELEMENTS is -1, then the array
> +   is assumed to have an unknown length.  */
> +
> +GCC_METHOD2 (gcc_type, build_array_type,
> +	     gcc_type,			  /* Argument ELEMENT_TYPE.  */
> +	     int)			  /* Argument NUM_ELEMENTS.  */
> +
> +/* Create a new array type.  NUM_ELEMENTS is a template-dependent
> +   expression.  */
> +
> +GCC_METHOD2 (gcc_type, build_dependent_array_type,
> +	     gcc_type,			  /* Argument ELEMENT_TYPE.  */
> +	     gcc_expr)			  /* Argument NUM_ELEMENTS.  */
> +
> +/* Create a new variably-sized array type.  UPPER_BOUND_NAME is the
> +   name of a local variable that holds the upper bound of the array;
> +   it is one less than the array size.  */
> +
> +GCC_METHOD2 (gcc_type, build_vla_array_type,
> +	     gcc_type,			  /* Argument ELEMENT_TYPE.  */
> +	     const char *)		  /* Argument UPPER_BOUND_NAME.  */
> +
> +/* Return a qualified variant of a given base type.  QUALIFIERS says
> +   which qualifiers to use; it is composed of or'd together
> +   constants from 'enum gcc_cp_qualifiers'.  */
> +
> +GCC_METHOD2 (gcc_type, build_qualified_type,
> +	     gcc_type,			      /* Argument UNQUALIFIED_TYPE.  */
> +	     enum gcc_cp_qualifiers)	      /* Argument QUALIFIERS.  */
> +
> +/* Build a complex type given its element type.  */
> +
> +GCC_METHOD1 (gcc_type, build_complex_type,
> +	     gcc_type)			  /* Argument ELEMENT_TYPE.  */
> +
> +/* Build a vector type given its element type and number of
> +   elements.  */
> +
> +GCC_METHOD2 (gcc_type, build_vector_type,
> +	     gcc_type,			  /* Argument ELEMENT_TYPE.  */
> +	     int)			  /* Argument NUM_ELEMENTS.  */
> +
> +/* Build a constant.  NAME is the constant's name and VALUE is its
> +   value.  FILENAME and LINE_NUMBER refer to the type's source
> +   location.  If this is not known, FILENAME can be NULL and
> +   LINE_NUMBER can be 0.  */
> +
> +GCC_METHOD5 (int /* bool */, build_constant,
> +	     gcc_type,		  /* Argument TYPE.  */
> +	     const char *,	  /* Argument NAME.  */
> +	     unsigned long,	  /* Argument VALUE.  */
> +	     const char *,	  /* Argument FILENAME.  */
> +	     unsigned int)	  /* Argument LINE_NUMBER.  */
> +
> +/* Emit an error and return an error type object.  */
> +
> +GCC_METHOD1 (gcc_type, error,
> +	     const char *)		 /* Argument MESSAGE.  */
> +
> +/* Declare a static_assert with the given CONDITION and ERRORMSG at
> +   FILENAME:LINE_NUMBER.  */
> +
> +GCC_METHOD4 (int /* bool */, add_static_assert,
> +	     gcc_expr,     /* Argument CONDITION.  */
> +	     const char *, /* Argument ERRORMSG.  */
> +	     const char *, /* Argument FILENAME.  */
> +	     unsigned int) /* Argument LINE_NUMBER.  */
> +
> +#if 0
> +
> +/* FIXME: We don't want to expose the internal implementation detail
> +   that default parms are stored in function types, and it's not clear
> +   how this or other approaches would interact with the type sharing
> +   of e.g. ctor clones, so we're leaving this out, since default args
> +   are not even present in debug information anyway.  Besides, the set
> +   of default args for a function may grow within its scope, and vary
> +   independently in other scopes.  */
> +
> +/* Create a modified version of a function type that has default
> +   values for some of its arguments.  The returned type should ONLY be
> +   used to define functions or methods, never to declare parameters,
> +   variables, types or the like.
> +
> +   DEFAULTS must have at most as many N_ELEMENTS as there are
> +   arguments without default values in FUNCTION_TYPE.  Say, if
> +   FUNCTION_TYPE has an argument list such as (T1, T2, T3, T4 = V0)
> +   and DEFAULTS has 2 elements (V1, V2), the returned type will have
> +   the following argument list: (T1, T2 = V1, T3 = V2, T4 = V0).
> +
> +   Any NULL expressions in DEFAULTS will be marked as deferred, and
> +   they should be filled in with set_deferred_function_default_args.  */
> +
> +GCC_METHOD2 (gcc_type, add_function_default_args,
> +	     gcc_type,			     /* Argument FUNCTION_TYPE.  */
> +	     const struct gcc_cp_function_args *) /* Argument DEFAULTS.  */
> +
> +/* Fill in the first deferred default args in FUNCTION_DECL with the
> +   expressions given in DEFAULTS.  This can be used when the
> +   declaration of a parameter is needed to create a default
> +   expression, such as taking the size of an earlier parameter, or
> +   building a lambda expression in the parameter's context.  */
> +
> +GCC_METHOD2 (int /* bool */, set_deferred_function_default_args,
> +	     gcc_decl,			     /* Argument FUNCTION_DECL.  */
> +	     const struct gcc_cp_function_args *) /* Argument DEFAULTS.  */
> +
> +#endif
> +
> +
> +/* When you add entry points, add them at the end, so that the new API
> +   version remains compatible with the old version.
> +
> +   The following conventions have been observed as to naming entry points:
> +
> +   - build_* creates (and maybe records) something and returns it;
> +   - add_* creates and records something, but doesn't return it;
> +   - get_* obtains something without creating it;
> +   - start_* marks the beginning of a compound (type, list, ...);
> +   - finish_* completes the compound when needed.
> +
> +  Entry points that return an int (bool) and don't have a return value
> +  specification return nonzero (true) on success and zero (false) on
> +  failure.  This is in line with libcc1's conventions of returning a
> +  zero-initialized value in case of e.g. a transport error.  */
> diff --git a/include/gcc-cp-interface.h b/include/gcc-cp-interface.h
> new file mode 100644
> index 0000000..6ef9e22
> --- /dev/null
> +++ b/include/gcc-cp-interface.h
> @@ -0,0 +1,496 @@
> +/* Interface between GCC C++ FE and GDB
> +
> +   Copyright (C) 2014-2017 Free Software Foundation, Inc.
> +
> +   This file is part of GCC.
> +
> +   This program is free software; you can redistribute it and/or modify
> +   it under the terms of the GNU General Public License as published by
> +   the Free Software Foundation; either version 3 of the License, or
> +   (at your option) any later version.
> +
> +   This program is distributed in the hope that it will be useful,
> +   but WITHOUT ANY WARRANTY; without even the implied warranty of
> +   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
> +   GNU General Public License for more details.
> +
> +   You should have received a copy of the GNU General Public License
> +   along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
> +
> +#ifndef GCC_CP_INTERFACE_H
> +#define GCC_CP_INTERFACE_H
> +
> +#include "gcc-interface.h"
> +
> +/* This header defines the interface to the GCC API.  It must be both
> +   valid C and valid C++, because it is included by both programs.  */
> +
> +#ifdef __cplusplus
> +extern "C" {
> +#endif
> +
> +/* Forward declaration.  */
> +
> +struct gcc_cp_context;
> +
> +/*
> + * Definitions and declarations for the C++ front end.
> + */
> +
> +/* Defined versions of the C++ front-end API.  */
> +
> +enum gcc_cp_api_version
> +{
> +  GCC_CP_FE_VERSION_0 = 0
> +};
> +
> +/* Qualifiers.  */
> +
> +enum gcc_cp_qualifiers
> +{
> +  GCC_CP_QUALIFIER_CONST = 1,
> +  GCC_CP_QUALIFIER_VOLATILE = 2,
> +  GCC_CP_QUALIFIER_RESTRICT = 4
> +};
> +
> +/* Ref qualifiers.  */
> +
> +enum gcc_cp_ref_qualifiers {
> +  GCC_CP_REF_QUAL_NONE = 0,
> +  GCC_CP_REF_QUAL_LVALUE = 1,
> +  GCC_CP_REF_QUAL_RVALUE = 2
> +};
> +
> +/* Opaque typedef for unbound class templates.  They are used for
> +   template arguments, and defaults for template template
> +   parameters.  */
> +
> +typedef unsigned long long gcc_utempl;
> +
> +/* Opaque typedef for expressions.  They are used for template
> +   arguments, defaults for non-type template parameters, and defaults
> +   for function arguments.  */
> +
> +typedef unsigned long long gcc_expr;
> +
> +typedef enum
> +  { GCC_CP_TPARG_VALUE, GCC_CP_TPARG_CLASS,
> +    GCC_CP_TPARG_TEMPL, GCC_CP_TPARG_PACK }
> +gcc_cp_template_arg_kind;
> +
> +typedef union
> +{ gcc_expr value; gcc_type type; gcc_utempl templ; gcc_type pack; }
> +gcc_cp_template_arg;
> +
> +/* An array of template arguments.  */
> +
> +struct gcc_cp_template_args
> +{
> +  /* Number of elements.  */
> +
> +  int n_elements;
> +
> +  /* kind[i] indicates what kind of template argument type[i] is.  */
> +
> +  char /* gcc_cp_template_arg_kind */ *kinds;
> +
> +  /* The template arguments.  */
> +
> +  gcc_cp_template_arg *elements;
> +};
> +
> +/* An array of (default) function arguments.  */
> +
> +struct gcc_cp_function_args
> +{
> +  /* Number of elements.  */
> +
> +  int n_elements;
> +
> +  /* The (default) values for each argument.  */
> +
> +  gcc_expr *elements;
> +};
> +
> +/* This enumerates the kinds of decls that GDB can create.  */
> +
> +enum gcc_cp_symbol_kind
> +{
> +  /* A function.  */
> +
> +  GCC_CP_SYMBOL_FUNCTION,
> +
> +  /* A variable.  */
> +
> +  GCC_CP_SYMBOL_VARIABLE,
> +
> +  /* A typedef, or an alias declaration (including template ones).  */
> +
> +  GCC_CP_SYMBOL_TYPEDEF,
> +
> +  /* A label.  */
> +
> +  GCC_CP_SYMBOL_LABEL,
> +
> +  /* A class, forward declared in build_decl (to be later defined in
> +     start_class_definition), or, in a template parameter list scope,
> +     a declaration of a template class, closing the parameter
> +     list.  */
> +
> +  GCC_CP_SYMBOL_CLASS,
> +
> +  /* A union, forward declared in build_decl (to be later defined in
> +     start_class_definition).  */
> +
> +  GCC_CP_SYMBOL_UNION,
> +
> +  /* An enumeration type being introduced with start_new_enum_type.  */
> +
> +  GCC_CP_SYMBOL_ENUM,
> +
> +  /* A nonstatic data member being introduced with new_field.  */
> +
> +  GCC_CP_SYMBOL_FIELD,
> +
> +  /* A base class in a gcc_vbase_array.  */
> +
> +  GCC_CP_SYMBOL_BASECLASS,
> +
> +  /* A using declaration in new_using_decl.  */
> +
> +  GCC_CP_SYMBOL_USING,
> +
> +  /* A (lambda) closure class type.  In many regards this is just like
> +     a regular class, but it's not supposed to have base classes, some
> +     of the member functions that are usually implicitly-defined are
> +     deleted, and it should have an operator() member function that
> +     holds the lambda body.  We can't instantiate objects of lambda
> +     types from the snippet, but we can interact with them in such
> +     ways as passing them to functions that take their types, and
> +     calling their body.  */
> +
> +  GCC_CP_SYMBOL_LAMBDA_CLOSURE,
> +
> +  /* Marker to check that we haven't exceeded GCC_CP_SYMBOL_MASK.  */
> +  GCC_CP_SYMBOL_END,
> +
> +  GCC_CP_SYMBOL_MASK = 15,
> +
> +  /* When defining a class member, at least one of the
> +     GCC_CP_ACCESS_MASK bits must be set; when defining a namespace-
> +     or union-scoped symbol, none of them must be set.  */
> +
> +  GCC_CP_ACCESS_PRIVATE,
> +  GCC_CP_ACCESS_PUBLIC = GCC_CP_ACCESS_PRIVATE << 1,
> +  GCC_CP_ACCESS_MASK = (GCC_CP_ACCESS_PUBLIC
> +			       | GCC_CP_ACCESS_PRIVATE),
> +  GCC_CP_ACCESS_PROTECTED = GCC_CP_ACCESS_MASK,
> +  GCC_CP_ACCESS_NONE = 0,
> +
> +  GCC_CP_FLAG_BASE = GCC_CP_ACCESS_PRIVATE << 2,
> +
> +  /* Flags to be used along with GCC_CP_SYMBOL_FUNCTION:  */
> +
> +  /* This flag should be set for constructors, destructors and
> +     operators.  */
> +  GCC_CP_FLAG_SPECIAL_FUNCTION = GCC_CP_FLAG_BASE,
> +
> +  /* We intentionally cannot express inline, constexpr, or virtual
> +     override for functions.  We can't inline or constexpr-replace
> +     without a source-level body.  The override keyword is only
> +     meaningful within the definition of the containing class.  */
> +
> +  /* This indicates a "virtual" member function, explicitly or
> +     implicitly (due to a virtual function with the same name and
> +     prototype in a base class) declared as such.  */
> +  GCC_CP_FLAG_VIRTUAL_FUNCTION = GCC_CP_FLAG_BASE << 1,
> +
> +  /* The following two flags should only be set when the flag above is
> +     set.  */
> +
> +  /* This indicates a pure virtual member function, i.e., one that is
> +     declared with "= 0", even if a body is provided in the
> +     definition.  */
> +  GCC_CP_FLAG_PURE_VIRTUAL_FUNCTION = GCC_CP_FLAG_BASE << 2,
> +
> +  /* This indicates a "final" virtual member function.  */
> +  GCC_CP_FLAG_FINAL_VIRTUAL_FUNCTION = GCC_CP_FLAG_BASE << 3,
> +
> +  /* This indicates a special member function should have its default
> +     implementation.  This either means the function declaration
> +     contains the "= default" tokens, or that the member function was
> +     implicitly generated by the compiler, although the latter use is
> +     discouraged: just let the compiler implicitly introduce it.
> +
> +     A member function defaulted after its first declaration has
> +     slightly different ABI implications from one implicitly generated
> +     or explicitly defaulted at the declaration (and definition)
> +     point.  To avoid silent (possibly harmless) violation of the one
> +     definition rule, it is recommended that this flag not be used for
> +     such functions, and that the address of the definition be
> +     supplied instead.  */
> +  GCC_CP_FLAG_DEFAULTED_FUNCTION = GCC_CP_FLAG_BASE << 4,
> +
> +  /* This indicates a deleted member function, i.e., one that has been
> +     defined as "= delete" at its declaration point, or one that has
> +     been implicitly defined as deleted (with or without an explicit
> +     "= default" definition).
> +
> +     This should not be used for implicitly-declared member functions
> +     that resolve to deleted definitions, as it may affect the
> +     implicit declaration of other member functions.  */
> +  GCC_CP_FLAG_DELETED_FUNCTION = GCC_CP_FLAG_BASE << 5,
> +
> +  /* This indicates a constructor or type-conversion operator declared
> +     as "explicit".  */
> +
> +  GCC_CP_FLAG_EXPLICIT_FUNCTION = GCC_CP_FLAG_BASE << 6,
> +
> +  GCC_CP_FLAG_END_FUNCTION,
> +  GCC_CP_FLAG_MASK_FUNCTION = (((GCC_CP_FLAG_END_FUNCTION - 1) << 1)
> +			       - GCC_CP_FLAG_BASE),
> +
> +  /* Flags to be used along with GCC_CP_SYMBOL_VARIABLE:  */
> +
> +  /* This indicates a variable declared as "constexpr".  */
> +
> +  GCC_CP_FLAG_CONSTEXPR_VARIABLE = GCC_CP_FLAG_BASE,
> +
> +  /* This indicates a variable declared as "thread_local".  ??? What
> +     should the ADDRESS be?  */
> +
> +  GCC_CP_FLAG_THREAD_LOCAL_VARIABLE = GCC_CP_FLAG_BASE << 1,
> +
> +  GCC_CP_FLAG_END_VARIABLE,
> +  GCC_CP_FLAG_MASK_VARIABLE = (((GCC_CP_FLAG_END_VARIABLE - 1) << 1)
> +			       - GCC_CP_FLAG_BASE),
> +
> +  /* Flags to be used when defining nonstatic data members of classes
> +     with new_field.  */
> +
> +  /* Use this when no flags are present.  */
> +  GCC_CP_FLAG_FIELD_NOFLAG = 0,
> +
> +  /* This indicates the field is declared as mutable.  */
> +  GCC_CP_FLAG_FIELD_MUTABLE = GCC_CP_FLAG_BASE,
> +
> +  GCC_CP_FLAG_END_FIELD,
> +  GCC_CP_FLAG_MASK_FIELD = (((GCC_CP_FLAG_END_FIELD - 1) << 1)
> +			    - GCC_CP_FLAG_BASE),
> +
> +  /* Flags to be used when defining an enum with
> +     start_new_enum_type.  */
> +
> +  /* This indicates an enum type without any flags.  */
> +  GCC_CP_FLAG_ENUM_NOFLAG = 0,
> +
> +  /* This indicates a scoped enum type.  */
> +  GCC_CP_FLAG_ENUM_SCOPED = GCC_CP_FLAG_BASE,
> +
> +  GCC_CP_FLAG_END_ENUM,
> +  GCC_CP_FLAG_MASK_ENUM = (((GCC_CP_FLAG_END_ENUM - 1) << 1)
> +			       - GCC_CP_FLAG_BASE),
> +
> +
> +  /* Flags to be used when introducing a class or a class template
> +     with build_decl.  */
> +
> +  /* This indicates an enum type without any flags.  */
> +  GCC_CP_FLAG_CLASS_NOFLAG = 0,
> +
> +  /* This indicates the class is actually a struct.  This has no
> +     effect whatsoever on access control in this interface, since all
> +     class members must have explicit access control bits set, but it
> +     may affect error messages.  */
> +  GCC_CP_FLAG_CLASS_IS_STRUCT = GCC_CP_FLAG_BASE,
> +
> +  GCC_CP_FLAG_END_CLASS,
> +  GCC_CP_FLAG_MASK_CLASS = (((GCC_CP_FLAG_END_CLASS - 1) << 1)
> +			       - GCC_CP_FLAG_BASE),
> +
> +
> +  /* Flags to be used when introducing a virtual base class in a
> +     gcc_vbase_array.  */
> +
> +  /* This indicates an enum type without any flags.  */
> +  GCC_CP_FLAG_BASECLASS_NOFLAG = 0,
> +
> +  /* This indicates the class is actually a struct.  This has no
> +     effect whatsoever on access control in this interface, since all
> +     class members must have explicit access control bits set, but it
> +     may affect error messages.  */
> +  GCC_CP_FLAG_BASECLASS_VIRTUAL = GCC_CP_FLAG_BASE,
> +
> +  GCC_CP_FLAG_END_BASECLASS,
> +  GCC_CP_FLAG_MASK_BASECLASS = (((GCC_CP_FLAG_END_BASECLASS - 1) << 1)
> +				- GCC_CP_FLAG_BASE),
> +
> +
> +  GCC_CP_FLAG_MASK = (GCC_CP_FLAG_MASK_FUNCTION
> +		      | GCC_CP_FLAG_MASK_VARIABLE
> +		      | GCC_CP_FLAG_MASK_FIELD
> +		      | GCC_CP_FLAG_MASK_ENUM
> +		      | GCC_CP_FLAG_MASK_CLASS
> +		      | GCC_CP_FLAG_MASK_BASECLASS
> +		      )
> +};
> +
> +
> +/* An array of types used for creating lists of base classes.  */
> +
> +struct gcc_vbase_array
> +{
> +  /* Number of elements.  */
> +
> +  int n_elements;
> +
> +  /* The base classes.  */
> +
> +  gcc_type *elements;
> +
> +  /* Flags for each base class.  Used to indicate access control and
> +     virtualness.  */
> +
> +  enum gcc_cp_symbol_kind *flags;
> +};
> +
> +
> +/* This enumerates the types of symbols that GCC might request from
> +   GDB.  */
> +
> +enum gcc_cp_oracle_request
> +{
> +  /* An identifier in namespace scope -- type, variable, function,
> +     namespace, template.  All namespace-scoped symbols with the
> +     requested name, in any namespace (including the global
> +     namespace), should be defined in response to this request.  */
> +
> +  GCC_CP_ORACLE_IDENTIFIER
> +};
> +
> +/* The type of the function called by GCC to ask GDB for a symbol's
> +   definition.  DATUM is an arbitrary value supplied when the oracle
> +   function is registered.  CONTEXT is the GCC context in which the
> +   request is being made.  REQUEST specifies what sort of symbol is
> +   being requested, and IDENTIFIER is the name of the symbol.  */
> +
> +typedef void gcc_cp_oracle_function (void *datum,
> +				     struct gcc_cp_context *context,
> +				     enum gcc_cp_oracle_request request,
> +				     const char *identifier);
> +
> +/* The type of the function called by GCC to ask GDB for a symbol's
> +   address.  This should return 0 if the address is not known.  */
> +
> +typedef gcc_address gcc_cp_symbol_address_function (void *datum,
> +						    struct gcc_cp_context *ctxt,
> +						    const char *identifier);
> +
> +/* The type of the function called by GCC to ask GDB to enter or leave
> +   the user expression scope.  */
> +
> +typedef void gcc_cp_enter_leave_user_expr_scope_function (void *datum,
> +							  struct gcc_cp_context
> +							  *context);
> +
> +/* The vtable used by the C front end.  */
> +
> +struct gcc_cp_fe_vtable
> +{
> +  /* The version of the C interface.  The value is one of the
> +     gcc_cp_api_version constants.  */
> +
> +  unsigned int cp_version;
> +
> +  /* Set the callbacks for this context.
> +
> +     The binding oracle is called whenever the C++ parser needs to
> +     look up a symbol.  This gives the caller a chance to lazily
> +     instantiate symbols using other parts of the gcc_cp_fe_interface
> +     API.  The symbol is looked up without a scope, and the oracle
> +     must supply a definition for ALL namespace-scoped definitions
> +     bound to the symbol.
> +
> +     The address oracle is called whenever the C++ parser needs to
> +     look up a symbol.  This may be called for symbols not provided by
> +     the symbol oracle, such as built-in functions where GCC provides
> +     the declaration; other internal symbols, such as those related
> +     with thunks, rtti, and virtual tables are likely to be queried
> +     through this interface too.  The identifier is a mangled symbol
> +     name.
> +
> +     DATUM is an arbitrary piece of data that is passed back verbatim
> +     to the callbacks in requests.  */
> +
> +  void (*set_callbacks) (struct gcc_cp_context *self,
> +			 gcc_cp_oracle_function *binding_oracle,
> +			 gcc_cp_symbol_address_function *address_oracle,
> +			 gcc_cp_enter_leave_user_expr_scope_function *enter_scope,
> +			 gcc_cp_enter_leave_user_expr_scope_function *leave_scope,
> +			 void *datum);
> +
> +#define GCC_METHOD0(R, N) \
> +  R (*N) (struct gcc_cp_context *);
> +#define GCC_METHOD1(R, N, A) \
> +  R (*N) (struct gcc_cp_context *, A);
> +#define GCC_METHOD2(R, N, A, B) \
> +  R (*N) (struct gcc_cp_context *, A, B);
> +#define GCC_METHOD3(R, N, A, B, C) \
> +  R (*N) (struct gcc_cp_context *, A, B, C);
> +#define GCC_METHOD4(R, N, A, B, C, D) \
> +  R (*N) (struct gcc_cp_context *, A, B, C, D);
> +#define GCC_METHOD5(R, N, A, B, C, D, E) \
> +  R (*N) (struct gcc_cp_context *, A, B, C, D, E);
> +#define GCC_METHOD7(R, N, A, B, C, D, E, F, G) \
> +  R (*N) (struct gcc_cp_context *, A, B, C, D, E, F, G);
> +
> +#include "gcc-cp-fe.def"
> +
> +#undef GCC_METHOD0
> +#undef GCC_METHOD1
> +#undef GCC_METHOD2
> +#undef GCC_METHOD3
> +#undef GCC_METHOD4
> +#undef GCC_METHOD5
> +#undef GCC_METHOD7
> +
> +};
> +
> +/* The C front end object.  */
> +
> +struct gcc_cp_context
> +{
> +  /* Base class.  */
> +
> +  struct gcc_base_context base;
> +
> +  /* Our vtable.  This is a separate field because this is simpler
> +     than implementing a vtable inheritance scheme in C.  */
> +
> +  const struct gcc_cp_fe_vtable *cp_ops;
> +};
> +
> +/* The name of the .so that the compiler builds.  We dlopen this
> +   later.  */
> +
> +#define GCC_CP_FE_LIBCC libcc1.so
> +
> +/* The compiler exports a single initialization function.  This macro
> +   holds its name as a symbol.  */
> +
> +#define GCC_CP_FE_CONTEXT gcc_cp_fe_context
> +
> +/* The type of the initialization function.  The caller passes in the
> +   desired base version and desired C-specific version.  If the
> +   request can be satisfied, a compatible gcc_context object will be
> +   returned.  Otherwise, the function returns NULL.  */
> +
> +typedef struct gcc_cp_context *gcc_cp_fe_context_function
> +    (enum gcc_base_api_version,
> +     enum gcc_cp_api_version);
> +
> +#ifdef __cplusplus
> +}
> +#endif
> +
> +#endif /* GCC_CP_INTERFACE_H */
> diff --git a/include/gcc-interface.h b/include/gcc-interface.h
> index e3ffd18..1dc3498 100644
> --- a/include/gcc-interface.h
> +++ b/include/gcc-interface.h
> @@ -169,6 +169,20 @@ struct gcc_base_context
>    const struct gcc_base_vtable *ops;
>  };
>  
> +/* An array of types used for creating function types in multiple
> +   languages.  */
> +
> +struct gcc_type_array
> +{
> +  /* Number of elements.  */
> +
> +  int n_elements;
> +
> +  /* The elements.  */
> +
> +  gcc_type *elements;
> +};
> +
>  /* The name of the dummy wrapper function generated by gdb.  */
>  
>  #define GCC_FE_WRAPPER_FUNCTION "_gdb_expr"
> diff --git a/include/libiberty.h b/include/libiberty.h
> index 0b6ef45..a0cbbcf 100644
> --- a/include/libiberty.h
> +++ b/include/libiberty.h
> @@ -3,7 +3,7 @@
>     Copyright (C) 1997-2017 Free Software Foundation, Inc.
>     
>     Note - certain prototypes declared in this header file are for
> -   functions whose implementation copyright does not belong to the
> +   functions whoes implementation copyright does not belong to the
>     FSF.  Those prototypes are present in this file for reference
>     purposes only and their presence in this file should not construed
>     as an indication of ownership by the FSF of the implementation of
> @@ -724,7 +724,7 @@ extern void *C_alloca (size_t) ATTRIBUTE_MALLOC;
>  # define ASTRDUP(X) \
>    (__extension__ ({ const char *const libiberty_optr = (X); \
>     const unsigned long libiberty_len = strlen (libiberty_optr) + 1; \
> -   char *const libiberty_nptr = (char *const) alloca (libiberty_len); \
> +   char *const libiberty_nptr = (char *) alloca (libiberty_len); \
>     (char *) memcpy (libiberty_nptr, libiberty_optr, libiberty_len); }))
>  #else
>  # define alloca(x) C_alloca(x)
> diff --git a/include/longlong.h b/include/longlong.h
> index 0ec11c5..c24568a 100644
> --- a/include/longlong.h
> +++ b/include/longlong.h
> @@ -197,17 +197,17 @@ extern UDItype __udiv_qrnnd (UDItype *, UDItype, UDItype, UDItype);
>  	   : "=r" ((USItype) (sh)),					\
>  	     "=&r" ((USItype) (sl))					\
>  	   : "%r" ((USItype) (ah)),					\
> -	     "rIJ" ((USItype) (bh)),					\
> +	     "rICal" ((USItype) (bh)),					\
>  	     "%r" ((USItype) (al)),					\
> -	     "rIJ" ((USItype) (bl)))
> +	     "rICal" ((USItype) (bl)))
>  #define sub_ddmmss(sh, sl, ah, al, bh, bl) \
>    __asm__ ("sub.f	%1, %4, %5\n\tsbc	%0, %2, %3"		\
>  	   : "=r" ((USItype) (sh)),					\
>  	     "=&r" ((USItype) (sl))					\
>  	   : "r" ((USItype) (ah)),					\
> -	     "rIJ" ((USItype) (bh)),					\
> +	     "rICal" ((USItype) (bh)),					\
>  	     "r" ((USItype) (al)),					\
> -	     "rIJ" ((USItype) (bl)))
> +	     "rICal" ((USItype) (bl)))
>  
>  #define __umulsidi3(u,v) ((UDItype)(USItype)u*(USItype)v)
>  #ifdef __ARC_NORM__
> @@ -221,8 +221,8 @@ extern UDItype __udiv_qrnnd (UDItype *, UDItype, UDItype, UDItype);
>      }									\
>    while (0)
>  #define COUNT_LEADING_ZEROS_0 32
> -#endif
> -#endif
> +#endif /* __ARC_NORM__ */
> +#endif /* __arc__ */
>  
>  #if defined (__arm__) && (defined (__thumb2__) || !defined (__thumb__)) \
>   && W_TYPE_SIZE == 32
> @@ -858,42 +858,6 @@ extern UDItype __umulsidi3 (USItype, USItype);
>  #endif
>  #endif /* __mips__ */
>  
> -#if defined (__ns32000__) && W_TYPE_SIZE == 32
> -#define umul_ppmm(w1, w0, u, v) \
> -  ({union {UDItype __ll;						\
> -	   struct {USItype __l, __h;} __i;				\
> -	  } __xx;							\
> -  __asm__ ("meid %2,%0"							\
> -	   : "=g" (__xx.__ll)						\
> -	   : "%0" ((USItype) (u)),					\
> -	     "g" ((USItype) (v)));					\
> -  (w1) = __xx.__i.__h; (w0) = __xx.__i.__l;})
> -#define __umulsidi3(u, v) \
> -  ({UDItype __w;							\
> -    __asm__ ("meid %2,%0"						\
> -	     : "=g" (__w)						\
> -	     : "%0" ((USItype) (u)),					\
> -	       "g" ((USItype) (v)));					\
> -    __w; })
> -#define udiv_qrnnd(q, r, n1, n0, d) \
> -  ({union {UDItype __ll;						\
> -	   struct {USItype __l, __h;} __i;				\
> -	  } __xx;							\
> -  __xx.__i.__h = (n1); __xx.__i.__l = (n0);				\
> -  __asm__ ("deid %2,%0"							\
> -	   : "=g" (__xx.__ll)						\
> -	   : "0" (__xx.__ll),						\
> -	     "g" ((USItype) (d)));					\
> -  (r) = __xx.__i.__l; (q) = __xx.__i.__h; })
> -#define count_trailing_zeros(count,x) \
> -  do {									\
> -    __asm__ ("ffsd     %2,%0"						\
> -	    : "=r" ((USItype) (count))					\
> -	    : "0" ((USItype) 0),					\
> -	      "r" ((USItype) (x)));					\
> -  } while (0)
> -#endif /* __ns32000__ */
> -
>  /* FIXME: We should test _IBMR2 here when we add assembly support for the
>     system vendor compilers.
>     FIXME: What's needed for gcc PowerPC VxWorks?  __vxworks__ is not good
> @@ -1086,7 +1050,7 @@ extern UDItype __umulsidi3 (USItype, USItype);
>    } while (0)
>  #endif
>  
> -#if defined(__sh__) && (!defined (__SHMEDIA__) || !__SHMEDIA__) && W_TYPE_SIZE == 32
> +#if defined(__sh__) && W_TYPE_SIZE == 32
>  #ifndef __sh1__
>  #define umul_ppmm(w1, w0, u, v) \
>    __asm__ (								\
> @@ -1159,21 +1123,6 @@ extern UDItype __umulsidi3 (USItype, USItype);
>  
>  #endif /* __sh__ */
>  
> -#if defined (__SH5__) && defined (__SHMEDIA__) && __SHMEDIA__ && W_TYPE_SIZE == 32
> -#define __umulsidi3(u,v) ((UDItype)(USItype)u*(USItype)v)
> -#define count_leading_zeros(count, x) \
> -  do									\
> -    {									\
> -      UDItype x_ = (USItype)(x);					\
> -      SItype c_;							\
> -									\
> -      __asm__ ("nsb %1, %0" : "=r" (c_) : "r" (x_));			\
> -      (count) = c_ - 31;						\
> -    }									\
> -  while (0)
> -#define COUNT_LEADING_ZEROS_0 32
> -#endif
> -
>  #if defined (__sparc__) && !defined (__arch64__) && !defined (__sparcv9) \
>      && W_TYPE_SIZE == 32
>  #define add_ssaaaa(sh, sl, ah, al, bh, bl) \
> diff --git a/include/simple-object.h b/include/simple-object.h
> index 8a8439b..f1bf88b 100644
> --- a/include/simple-object.h
> +++ b/include/simple-object.h
> @@ -197,6 +197,14 @@ simple_object_write_to_file (simple_object_write *simple_object,
>  extern void
>  simple_object_release_write (simple_object_write *);
>  
> +/* Copy LTO debug sections from SRC_OBJECT to DEST.
> +   If an error occurs, return the errno value in ERR and an error string.  */
> +
> +extern const char *
> +simple_object_copy_lto_debug_sections (simple_object_read *src_object,
> +				       const char *dest,
> +				       int *err);
> +
>  #ifdef __cplusplus
>  }
>  #endif
> diff --git a/libiberty/cp-demangle.c b/libiberty/cp-demangle.c
> index 7b8d0b4..c330052 100644
> --- a/libiberty/cp-demangle.c
> +++ b/libiberty/cp-demangle.c
> @@ -425,7 +425,7 @@ is_ctor_dtor_or_conversion (struct demangle_component *);
>  
>  static struct demangle_component *d_encoding (struct d_info *, int);
>  
> -static struct demangle_component *d_name (struct d_info *);
> +static struct demangle_component *d_name (struct d_info *, int);
>  
>  static struct demangle_component *d_nested_name (struct d_info *);
>  
> @@ -484,7 +484,7 @@ static struct demangle_component *d_expression (struct d_info *);
>  
>  static struct demangle_component *d_expr_primary (struct d_info *);
>  
> -static struct demangle_component *d_local_name (struct d_info *);
> +static struct demangle_component *d_local_name (struct d_info *, int);
>  
>  static int d_discriminator (struct d_info *);
>  
> @@ -568,22 +568,6 @@ static int d_demangle_callback (const char *, int,
>                                  demangle_callbackref, void *);
>  static char *d_demangle (const char *, int, size_t *);
>  
> -/* True iff TYPE is a demangling component representing a
> -   function-type-qualifier.  */
> -
> -static int
> -is_fnqual_component_type (enum demangle_component_type type)
> -{
> -  return (type == DEMANGLE_COMPONENT_RESTRICT_THIS
> -	  || type == DEMANGLE_COMPONENT_VOLATILE_THIS
> -	  || type == DEMANGLE_COMPONENT_CONST_THIS
> -	  || type == DEMANGLE_COMPONENT_RVALUE_REFERENCE_THIS
> -	  || type == DEMANGLE_COMPONENT_TRANSACTION_SAFE
> -	  || type == DEMANGLE_COMPONENT_NOEXCEPT
> -	  || type == DEMANGLE_COMPONENT_THROW_SPEC
> -	  || type == DEMANGLE_COMPONENT_REFERENCE_THIS);
> -}
> -
>  #define FNQUAL_COMPONENT_CASE				\
>      case DEMANGLE_COMPONENT_RESTRICT_THIS:		\
>      case DEMANGLE_COMPONENT_VOLATILE_THIS:		\
> @@ -594,6 +578,23 @@ is_fnqual_component_type (enum demangle_component_type type)
>      case DEMANGLE_COMPONENT_NOEXCEPT:			\
>      case DEMANGLE_COMPONENT_THROW_SPEC
>  
> +/* True iff TYPE is a demangling component representing a
> +   function-type-qualifier.  */
> +
> +static int
> +is_fnqual_component_type (enum demangle_component_type type)
> +{
> +  switch (type)
> +    {
> +    FNQUAL_COMPONENT_CASE:
> +      return 1;
> +    default:
> +      break;
> +    }
> +  return 0;
> +}
> +
> +
>  #ifdef CP_DEMANGLE_DEBUG
>  
>  static void
> @@ -1305,9 +1306,9 @@ d_encoding (struct d_info *di, int top_level)
>      return d_special_name (di);
>    else
>      {
> -      struct demangle_component *dc;
> +      struct demangle_component *dc, *dcr;
>  
> -      dc = d_name (di);
> +      dc = d_name (di, top_level);
>  
>        if (dc != NULL && top_level && (di->options & DMGL_PARAMS) == 0)
>  	{
> @@ -1327,8 +1328,6 @@ d_encoding (struct d_info *di, int top_level)
>  	     which is local to a function.  */
>  	  if (dc->type == DEMANGLE_COMPONENT_LOCAL_NAME)
>  	    {
> -	      struct demangle_component *dcr;
> -
>  	      dcr = d_right (dc);
>  	      while (is_fnqual_component_type (dcr->type))
>  		dcr = d_left (dcr);
> @@ -1341,8 +1340,8 @@ d_encoding (struct d_info *di, int top_level)
>        peek = d_peek_char (di);
>        if (dc == NULL || peek == '\0' || peek == 'E')
>  	return dc;
> -      return d_make_comp (di, DEMANGLE_COMPONENT_TYPED_NAME, dc,
> -			  d_bare_function_type (di, has_return_type (dc)));
> +      dcr = d_bare_function_type (di, has_return_type (dc));
> +      return d_make_comp (di, DEMANGLE_COMPONENT_TYPED_NAME, dc, dcr);
>      }
>  }
>  
> @@ -1384,7 +1383,7 @@ d_abi_tags (struct d_info *di, struct demangle_component *dc)
>  */
>  
>  static struct demangle_component *
> -d_name (struct d_info *di)
> +d_name (struct d_info *di, int top_level)
>  {
>    char peek = d_peek_char (di);
>    struct demangle_component *dc;
> @@ -1395,7 +1394,7 @@ d_name (struct d_info *di)
>        return d_nested_name (di);
>  
>      case 'Z':
> -      return d_local_name (di);
> +      return d_local_name (di, top_level);
>  
>      case 'U':
>        return d_unqualified_name (di);
> @@ -2080,11 +2079,11 @@ d_special_name (struct d_info *di)
>  
>  	case 'H':
>  	  return d_make_comp (di, DEMANGLE_COMPONENT_TLS_INIT,
> -			      d_name (di), NULL);
> +			      d_name (di, 0), NULL);
>  
>  	case 'W':
>  	  return d_make_comp (di, DEMANGLE_COMPONENT_TLS_WRAPPER,
> -			      d_name (di), NULL);
> +			      d_name (di, 0), NULL);
>  
>  	default:
>  	  return NULL;
> @@ -2095,11 +2094,12 @@ d_special_name (struct d_info *di)
>        switch (d_next_char (di))
>  	{
>  	case 'V':
> -	  return d_make_comp (di, DEMANGLE_COMPONENT_GUARD, d_name (di), NULL);
> +	  return d_make_comp (di, DEMANGLE_COMPONENT_GUARD,
> +			      d_name (di, 0), NULL);
>  
>  	case 'R':
>  	  {
> -	    struct demangle_component *name = d_name (di);
> +	    struct demangle_component *name = d_name (di, 0);
>  	    return d_make_comp (di, DEMANGLE_COMPONENT_REFTEMP, name,
>  				d_number_component (di));
>  	  }
> @@ -2935,7 +2935,7 @@ d_bare_function_type (struct d_info *di, int has_return_type)
>  static struct demangle_component *
>  d_class_enum_type (struct d_info *di)
>  {
> -  return d_name (di);
> +  return d_name (di, 0);
>  }
>  
>  /* <array-type> ::= A <(positive dimension) number> _ <(element) type>
> @@ -3568,9 +3568,10 @@ d_expr_primary (struct d_info *di)
>  */
>  
>  static struct demangle_component *
> -d_local_name (struct d_info *di)
> +d_local_name (struct d_info *di, int top_level)
>  {
>    struct demangle_component *function;
> +  struct demangle_component *name;
>  
>    if (! d_check_char (di, 'Z'))
>      return NULL;
> @@ -3585,13 +3586,10 @@ d_local_name (struct d_info *di)
>        d_advance (di, 1);
>        if (! d_discriminator (di))
>  	return NULL;
> -      return d_make_comp (di, DEMANGLE_COMPONENT_LOCAL_NAME, function,
> -			  d_make_name (di, "string literal",
> -				       sizeof "string literal" - 1));
> +      name = d_make_name (di, "string literal", sizeof "string literal" - 1);
>      }
>    else
>      {
> -      struct demangle_component *name;
>        int num = -1;
>  
>        if (d_peek_char (di) == 'd')
> @@ -3603,22 +3601,36 @@ d_local_name (struct d_info *di)
>  	    return NULL;
>  	}
>  
> -      name = d_name (di);
> -      if (name)
> -	switch (name->type)
> -	  {
> -	    /* Lambdas and unnamed types have internal discriminators.  */
> -	  case DEMANGLE_COMPONENT_LAMBDA:
> -	  case DEMANGLE_COMPONENT_UNNAMED_TYPE:
> -	    break;
> -	  default:
> -	    if (! d_discriminator (di))
> -	      return NULL;
> -	  }
> +      name = d_name (di, 0);
> +
> +      if (name
> +	  /* Lambdas and unnamed types have internal discriminators
> +	     and are not functions.  */
> +	  && name->type != DEMANGLE_COMPONENT_LAMBDA
> +	  && name->type != DEMANGLE_COMPONENT_UNNAMED_TYPE)
> +	{
> +	  if (!top_level
> +	      && d_peek_char (di) != 0 /* Not end of string.  */
> +	      && d_peek_char (di) != 'E' /* Not end of nested encoding.  */
> +	      && d_peek_char (di) != '_') /* Not discriminator.  */
> +	    {
> +	      struct demangle_component *args;
> +
> +	      args = d_bare_function_type (di, has_return_type (name));
> +	      name = d_make_comp (di, DEMANGLE_COMPONENT_TYPED_NAME,
> +				  name, args);
> +	    }
> +
> +	  /* Read and ignore an optional discriminator.  */
> +	  if (! d_discriminator (di))
> +	    return NULL;
> +	}
> +
>        if (num >= 0)
>  	name = d_make_default_arg (di, num, name);
> -      return d_make_comp (di, DEMANGLE_COMPONENT_LOCAL_NAME, function, name);
>      }
> +
> +  return d_make_comp (di, DEMANGLE_COMPONENT_LOCAL_NAME, function, name);
>  }
>  
>  /* <discriminator> ::= _ <number>    # when number < 10
> diff --git a/libiberty/dwarfnames.c b/libiberty/dwarfnames.c
> index e58d03c..dacd78d 100644
> --- a/libiberty/dwarfnames.c
> +++ b/libiberty/dwarfnames.c
> @@ -75,6 +75,7 @@ Boston, MA 02110-1301, USA.  */
>  #define DW_ATE(name, value) case name: return # name ;
>  #define DW_ATE_DUP(name, value)
>  #define DW_CFA(name, value) case name: return # name ;
> +#define DW_CFA_DUP(name, value)
>  #define DW_IDX(name, value) case name: return # name ;
>  #define DW_IDX_DUP(name, value)
>  
> @@ -105,5 +106,6 @@ Boston, MA 02110-1301, USA.  */
>  #undef DW_ATE
>  #undef DW_ATE_DUP
>  #undef DW_CFA
> +#undef DW_CFA_DUP
>  #undef DW_IDX
>  #undef DW_IDX_DUP
> diff --git a/libiberty/simple-object-elf.c b/libiberty/simple-object-elf.c
> index 6774eb2..7eb3df8 100644
> --- a/libiberty/simple-object-elf.c
> +++ b/libiberty/simple-object-elf.c
> @@ -1158,70 +1158,84 @@ simple_object_elf_copy_lto_debug_sections (simple_object_read *sobj,
>  
>    /* Mark sections as preserved that are required by to be preserved
>       sections.  */
> -  for (i = 1; i < shnum; ++i)
> +  int changed;
> +  do
>      {
> -      unsigned char *shdr;
> -      unsigned int sh_type, sh_info, sh_link;
> -      off_t offset;
> -      off_t length;
> -
> -      shdr = shdrs + (i - 1) * shdr_size;
> -      sh_type = ELF_FETCH_FIELD (type_functions, ei_class, Shdr,
> -				 shdr, sh_type, Elf_Word);
> -      sh_info = ELF_FETCH_FIELD (type_functions, ei_class, Shdr,
> -				 shdr, sh_info, Elf_Word);
> -      sh_link = ELF_FETCH_FIELD (type_functions, ei_class, Shdr,
> -				 shdr, sh_link, Elf_Word);
> -      if (sh_type == SHT_GROUP)
> +      changed = 0;
> +      for (i = 1; i < shnum; ++i)
>  	{
> -	  /* Mark groups containing copied sections.  */
> -	  unsigned entsize = ELF_FETCH_FIELD (type_functions, ei_class, Shdr,
> -					      shdr, sh_entsize, Elf_Addr);
> -	  unsigned char *ent, *buf;
> -	  int keep = 0;
> -	  offset = ELF_FETCH_FIELD (type_functions, ei_class, Shdr,
> -				    shdr, sh_offset, Elf_Addr);
> -	  length = ELF_FETCH_FIELD (type_functions, ei_class, Shdr,
> -				    shdr, sh_size, Elf_Addr);
> -	  buf = XNEWVEC (unsigned char, length);
> -	  if (!simple_object_internal_read (sobj->descriptor,
> -					    sobj->offset + offset, buf,
> -					    (size_t) length, &errmsg, err))
> +	  unsigned char *shdr;
> +	  unsigned int sh_type, sh_info, sh_link;
> +	  off_t offset;
> +	  off_t length;
> +
> +	  shdr = shdrs + (i - 1) * shdr_size;
> +	  sh_type = ELF_FETCH_FIELD (type_functions, ei_class, Shdr,
> +				     shdr, sh_type, Elf_Word);
> +	  sh_info = ELF_FETCH_FIELD (type_functions, ei_class, Shdr,
> +				     shdr, sh_info, Elf_Word);
> +	  sh_link = ELF_FETCH_FIELD (type_functions, ei_class, Shdr,
> +				     shdr, sh_link, Elf_Word);
> +	  if (sh_type == SHT_GROUP)
>  	    {
> -	      XDELETEVEC (buf);
> -	      XDELETEVEC (names);
> -	      XDELETEVEC (shdrs);
> -	      return errmsg;
> -	    }
> -	  for (ent = buf + entsize; ent < buf + length; ent += entsize)
> -	    {
> -	      unsigned sec = type_functions->fetch_Elf_Word (ent);
> -	      if (pfnret[sec - 1] == 0)
> -		keep = 1;
> +	      /* Mark groups containing copied sections.  */
> +	      unsigned entsize = ELF_FETCH_FIELD (type_functions, ei_class,
> +						  Shdr, shdr, sh_entsize,
> +						  Elf_Addr);
> +	      unsigned char *ent, *buf;
> +	      int keep = 0;
> +	      offset = ELF_FETCH_FIELD (type_functions, ei_class, Shdr,
> +					shdr, sh_offset, Elf_Addr);
> +	      length = ELF_FETCH_FIELD (type_functions, ei_class, Shdr,
> +					shdr, sh_size, Elf_Addr);
> +	      buf = XNEWVEC (unsigned char, length);
> +	      if (!simple_object_internal_read (sobj->descriptor,
> +						sobj->offset + offset, buf,
> +						(size_t) length, &errmsg, err))
> +		{
> +		  XDELETEVEC (buf);
> +		  XDELETEVEC (names);
> +		  XDELETEVEC (shdrs);
> +		  return errmsg;
> +		}
> +	      for (ent = buf + entsize; ent < buf + length; ent += entsize)
> +		{
> +		  unsigned sec = type_functions->fetch_Elf_Word (ent);
> +		  if (pfnret[sec - 1] == 0)
> +		    keep = 1;
> +		}
> +	      if (keep)
> +		{
> +		  changed |= (pfnret[sh_link - 1] == -1
> +			      || pfnret[i - 1] == -1);
> +		  pfnret[sh_link - 1] = 0;
> +		  pfnret[i - 1] = 0;
> +		}
>  	    }
> -	  if (keep)
> +	  if (sh_type == SHT_RELA
> +	      || sh_type == SHT_REL)
>  	    {
> -	      pfnret[sh_link - 1] = 0;
> -	      pfnret[i - 1] = 0;
> +	      /* Mark relocation sections and symtab of copied sections.  */
> +	      if (pfnret[sh_info - 1] == 0)
> +		{
> +		  changed |= (pfnret[sh_link - 1] == -1
> +			      || pfnret[i - 1] == -1);
> +		  pfnret[sh_link - 1] = 0;
> +		  pfnret[i - 1] = 0;
> +		}
>  	    }
> -	}
> -      if (sh_type == SHT_RELA
> -	  || sh_type == SHT_REL)
> -	{
> -	  /* Mark relocation sections and symtab of copied sections.  */
> -	  if (pfnret[sh_info - 1] == 0)
> +	  if (sh_type == SHT_SYMTAB)
>  	    {
> -	      pfnret[sh_link - 1] = 0;
> -	      pfnret[i - 1] = 0;
> +	      /* Mark strings sections of copied symtabs.  */
> +	      if (pfnret[i - 1] == 0)
> +		{
> +		  changed |= pfnret[sh_link - 1] == -1;
> +		  pfnret[sh_link - 1] = 0;
> +		}
>  	    }
>  	}
> -      if (sh_type == SHT_SYMTAB)
> -	{
> -	  /* Mark strings sections of copied symtabs.  */
> -	  if (pfnret[i - 1] == 0)
> -	    pfnret[sh_link - 1] = 0;
> -	}
>      }
> +  while (changed);
>  
>    /* Then perform the actual copying.  */
>    for (i = 1; i < shnum; ++i)
> diff --git a/libiberty/testsuite/demangle-expected b/libiberty/testsuite/demangle-expected
> index f2a12b9..c1a9a73 100644
> --- a/libiberty/testsuite/demangle-expected
> +++ b/libiberty/testsuite/demangle-expected
> @@ -4720,18 +4720,33 @@ _ZdvMMMMMMMMMMMMMrrrrA_DTdvfp_fp_Eededilfdfdfdfd
>  
>  _Z1MA_aMMMMA_MMA_MMMMMMMMSt1MS_o11T0000000000t2M0oooozoooo
>  _Z1MA_aMMMMA_MMA_MMMMMMMMSt1MS_o11T0000000000t2M0oooozoooo
> -
>  #
>  # demangler/80513 Test for overflow in d_number
> +
>  _Z4294967297x
>  _Z4294967297x
> -
>  #
>  # demangler/80513 Test for bogus characters after __thunk_
> +
>  __thunk_16a_$_1x
>  __thunk_16a_$_1x
> -
>  #
>  # demangler/80513 Test for overflow in consume_count
> +
>  __thunk_4294967297__$_1x
>  __thunk_4294967297__$_1x
> +#
> +# demangler/82195 members of lambdas
> +--no-params
> +_ZZZ3FoovENKUlT_E_clIiEEfS_EN5Local2fnEv
> +Foo()::float {lambda(auto:1)#1}::operator()<int>(int) const::Local::fn()
> +Foo()::float {lambda(auto:1)#1}::operator()<int>(int) const::Local::fn
> +--no-params
> +_Z7CaptureIZZ3FoovENKUlT_E_clIiEEvS0_EUlvE_EvOS0_
> +void Capture<Foo()::void {lambda(auto:1)#1}::operator()<int>(int) const::{lambda()#1}>(Foo()::void {lambda(auto:1)#1}::operator()<int>(int) const::{lambda()#1}&&)
> +Capture<Foo()::void {lambda(auto:1)#1}::operator()<int>(int) const::{lambda()#1}>
> +--no-params
> +_Z4FrobIZZ3FoovENKUlT_E_clIiEEvS0_EUlvE_Evv
> +void Frob<Foo()::void {lambda(auto:1)#1}::operator()<int>(int) const::{lambda()#1}>()
> +Frob<Foo()::void {lambda(auto:1)#1}::operator()<int>(int) const::{lambda()#1}>
> +#
> 



Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]