[v3] Machine_Mode: Extend machine_mode from 8 to 16 bits

Message ID 20230513131325.1667305-1-pan2.li@intel.com
State Accepted
Headers
Series [v3] Machine_Mode: Extend machine_mode from 8 to 16 bits |

Checks

Context Check Description
snail/gcc-patch-check success Github commit url

Commit Message

Li, Pan2 via Gcc-patches May 13, 2023, 1:13 p.m. UTC
  From: Pan Li <pan2.li@intel.com>

We are running out of the machine_mode(8 bits) in RISC-V backend. Thus
we would like to extend the machine_mode bit size from 8 to 16 bits.
However, it is sensitive to extend the memory size in common structure
like tree or rtx. This patch would like to extend the machine_mode bits
to 16 bits by shrinking, like:

* Swap the bit size of code and machine code in rtx_def.
* Adjust the machine_mode location and spare in tree.

The memory impact of this patch for correlated structure looks like below:

+-------------------+----------+---------+------+
| struct/bytes      | upstream | patched | diff |
+-------------------+----------+---------+------+
| rtx_obj_reference |        8 |      12 |   +4 |
| ext_modified      |        2 |       4 |   +2 |
| ira_allocno       |      192 |     184 |   -8 |
| qty_table_elem    |       40 |      40 |    0 |
| reg_stat_type     |       64 |      64 |    0 |
| rtx_def           |       40 |      40 |    0 |
| table_elt         |       80 |      80 |    0 |
| tree_decl_common  |      112 |     112 |    0 |
| tree_type_common  |      128 |     128 |    0 |
+-------------------+----------+---------+------+

The tree and rtx related struct has no memory changes after this patch,
and the machine_mode changes to 16 bits already.

Signed-off-by: Pan Li <pan2.li@intel.com>
Co-authored-by: Ju-Zhe Zhong <juzhe.zhong@rivai.ai>
Co-authored-by: Kito Cheng <kito.cheng@sifive.com>
Co-Authored-By: Richard Biener <rguenther@suse.de>
Co-Authored-By: Richard Sandiford <richard.sandiford@arm.com>

gcc/ChangeLog:

	* combine.cc (struct reg_stat_type): Extend machine_mode to 16 bits.
	* cse.cc (struct qty_table_elem): Extend machine_mode to 16 bits
	(struct table_elt): Extend machine_mode to 16 bits.
	(struct set): Ditto.
	* genmodes.cc (emit_mode_wider): Extend type from char to short.
	(emit_mode_complex): Ditto.
	(emit_mode_inner): Ditto.
	(emit_class_narrowest_mode): Ditto.
	* genopinit.cc (main): Extend the machine_mode limit.
	* ira-int.h (struct ira_allocno): Extend machine_mode to 16 bits and
	re-ordered the struct fields for padding.
	* machmode.h (MACHINE_MODE_BITSIZE): New macro.
	(GET_MODE_2XWIDER_MODE): Extend type from char to short.
	(get_mode_alignment): Extend type from char to short.
	* ree.cc (struct ext_modified): Extend machine_mode to 16 bits and
	removed the ATTRIBUTE_PACKED.
	* rtl-ssa/accesses.h: Extend machine_mode to 16 bits.
	* rtl.h (RTX_CODE_BITSIZE): New macro.
	(struct rtx_def): Swap both the bit size and location between the
	rtx_code and the machine_mode.
	(subreg_shape::unique_id): Extend the machine_mode limit.
	* rtlanal.h: Extend machine_mode to 16 bits.
	* tree-core.h (struct tree_type_common): Extend machine_mode to 16
	bits and re-ordered the struct fields for padding.
	(struct tree_decl_common): Extend machine_mode to 16 bits.
---
 gcc/combine.cc         |  4 +--
 gcc/cse.cc             | 16 ++++--------
 gcc/genmodes.cc        | 16 ++++++------
 gcc/genopinit.cc       |  3 ++-
 gcc/ira-int.h          | 56 +++++++++++++++++++++---------------------
 gcc/machmode.h         | 27 +++++++++++++++-----
 gcc/ree.cc             |  4 +--
 gcc/rtl-ssa/accesses.h |  2 +-
 gcc/rtl.h              | 12 +++++----
 gcc/rtlanal.h          |  2 +-
 gcc/tree-core.h        |  9 ++++---
 11 files changed, 82 insertions(+), 69 deletions(-)
  

Comments

Li, Pan2 via Gcc-patches May 16, 2023, 1:12 a.m. UTC | #1
Kindly ping for this PATCH v3.

Pan

-----Original Message-----
From: Li, Pan2 <pan2.li@intel.com> 
Sent: Saturday, May 13, 2023 9:13 PM
To: gcc-patches@gcc.gnu.org
Cc: juzhe.zhong@rivai.ai; kito.cheng@sifive.com; Li, Pan2 <pan2.li@intel.com>; Wang, Yanzhang <yanzhang.wang@intel.com>; jeffreyalaw@gmail.com; rguenther@suse.de; richard.sandiford@arm.com
Subject: [PATCH v3] Machine_Mode: Extend machine_mode from 8 to 16 bits

From: Pan Li <pan2.li@intel.com>

We are running out of the machine_mode(8 bits) in RISC-V backend. Thus we would like to extend the machine_mode bit size from 8 to 16 bits.
However, it is sensitive to extend the memory size in common structure like tree or rtx. This patch would like to extend the machine_mode bits to 16 bits by shrinking, like:

* Swap the bit size of code and machine code in rtx_def.
* Adjust the machine_mode location and spare in tree.

The memory impact of this patch for correlated structure looks like below:

+-------------------+----------+---------+------+
| struct/bytes      | upstream | patched | diff |
+-------------------+----------+---------+------+
| rtx_obj_reference |        8 |      12 |   +4 |
| ext_modified      |        2 |       4 |   +2 |
| ira_allocno       |      192 |     184 |   -8 |
| qty_table_elem    |       40 |      40 |    0 |
| reg_stat_type     |       64 |      64 |    0 |
| rtx_def           |       40 |      40 |    0 |
| table_elt         |       80 |      80 |    0 |
| tree_decl_common  |      112 |     112 |    0 |
| tree_type_common  |      128 |     128 |    0 |
+-------------------+----------+---------+------+

The tree and rtx related struct has no memory changes after this patch, and the machine_mode changes to 16 bits already.

Signed-off-by: Pan Li <pan2.li@intel.com>
Co-authored-by: Ju-Zhe Zhong <juzhe.zhong@rivai.ai>
Co-authored-by: Kito Cheng <kito.cheng@sifive.com>
Co-Authored-By: Richard Biener <rguenther@suse.de>
Co-Authored-By: Richard Sandiford <richard.sandiford@arm.com>

gcc/ChangeLog:

	* combine.cc (struct reg_stat_type): Extend machine_mode to 16 bits.
	* cse.cc (struct qty_table_elem): Extend machine_mode to 16 bits
	(struct table_elt): Extend machine_mode to 16 bits.
	(struct set): Ditto.
	* genmodes.cc (emit_mode_wider): Extend type from char to short.
	(emit_mode_complex): Ditto.
	(emit_mode_inner): Ditto.
	(emit_class_narrowest_mode): Ditto.
	* genopinit.cc (main): Extend the machine_mode limit.
	* ira-int.h (struct ira_allocno): Extend machine_mode to 16 bits and
	re-ordered the struct fields for padding.
	* machmode.h (MACHINE_MODE_BITSIZE): New macro.
	(GET_MODE_2XWIDER_MODE): Extend type from char to short.
	(get_mode_alignment): Extend type from char to short.
	* ree.cc (struct ext_modified): Extend machine_mode to 16 bits and
	removed the ATTRIBUTE_PACKED.
	* rtl-ssa/accesses.h: Extend machine_mode to 16 bits.
	* rtl.h (RTX_CODE_BITSIZE): New macro.
	(struct rtx_def): Swap both the bit size and location between the
	rtx_code and the machine_mode.
	(subreg_shape::unique_id): Extend the machine_mode limit.
	* rtlanal.h: Extend machine_mode to 16 bits.
	* tree-core.h (struct tree_type_common): Extend machine_mode to 16
	bits and re-ordered the struct fields for padding.
	(struct tree_decl_common): Extend machine_mode to 16 bits.
---
 gcc/combine.cc         |  4 +--
 gcc/cse.cc             | 16 ++++--------
 gcc/genmodes.cc        | 16 ++++++------
 gcc/genopinit.cc       |  3 ++-
 gcc/ira-int.h          | 56 +++++++++++++++++++++---------------------
 gcc/machmode.h         | 27 +++++++++++++++-----
 gcc/ree.cc             |  4 +--
 gcc/rtl-ssa/accesses.h |  2 +-
 gcc/rtl.h              | 12 +++++----
 gcc/rtlanal.h          |  2 +-
 gcc/tree-core.h        |  9 ++++---
 11 files changed, 82 insertions(+), 69 deletions(-)

diff --git a/gcc/combine.cc b/gcc/combine.cc index 5aa0ec5c45a..a23caeed96f 100644
--- a/gcc/combine.cc
+++ b/gcc/combine.cc
@@ -200,7 +200,7 @@ struct reg_stat_type {
 
   unsigned HOST_WIDE_INT	last_set_nonzero_bits;
   char				last_set_sign_bit_copies;
-  ENUM_BITFIELD(machine_mode)	last_set_mode : 8;
+  ENUM_BITFIELD(machine_mode)	last_set_mode : MACHINE_MODE_BITSIZE;
 
   /* Set nonzero if references to register n in expressions should not be
      used.  last_set_invalid is set nonzero when this register is being @@ -235,7 +235,7 @@ struct reg_stat_type {
      truncation if we know that value already contains a truncated
      value.  */
 
-  ENUM_BITFIELD(machine_mode)	truncated_to_mode : 8;
+  ENUM_BITFIELD(machine_mode)	truncated_to_mode : MACHINE_MODE_BITSIZE;
 };
 
 
diff --git a/gcc/cse.cc b/gcc/cse.cc
index b10c9b0c94d..86403b95938 100644
--- a/gcc/cse.cc
+++ b/gcc/cse.cc
@@ -248,10 +248,8 @@ struct qty_table_elem
   rtx comparison_const;
   int comparison_qty;
   unsigned int first_reg, last_reg;
-  /* The sizes of these fields should match the sizes of the
-     code and mode fields of struct rtx_def (see rtl.h).  */
-  ENUM_BITFIELD(rtx_code) comparison_code : 16;
-  ENUM_BITFIELD(machine_mode) mode : 8;
+  ENUM_BITFIELD(machine_mode) mode : MACHINE_MODE_BITSIZE;
+  ENUM_BITFIELD(rtx_code) comparison_code : RTX_CODE_BITSIZE;
 };
 
 /* The table of all qtys, indexed by qty number.  */ @@ -404,9 +402,7 @@ struct table_elt
   struct table_elt *related_value;
   int cost;
   int regcost;
-  /* The size of this field should match the size
-     of the mode field of struct rtx_def (see rtl.h).  */
-  ENUM_BITFIELD(machine_mode) mode : 8;
+  ENUM_BITFIELD(machine_mode) mode : MACHINE_MODE_BITSIZE;
   char in_memory;
   char is_const;
   char flag;
@@ -4152,10 +4148,8 @@ struct set
   /* Nonzero if the SET_SRC contains something
      whose value cannot be predicted and understood.  */
   char src_volatile;
-  /* Original machine mode, in case it becomes a CONST_INT.
-     The size of this field should match the size of the mode
-     field of struct rtx_def (see rtl.h).  */
-  ENUM_BITFIELD(machine_mode) mode : 8;
+  /* Original machine mode, in case it becomes a CONST_INT.  */
+  ENUM_BITFIELD(machine_mode) mode : MACHINE_MODE_BITSIZE;
   /* Hash value of constant equivalent for SET_SRC.  */
   unsigned src_const_hash;
   /* A constant equivalent for SET_SRC, if any.  */ diff --git a/gcc/genmodes.cc b/gcc/genmodes.cc index 715787b8f48..55ac2adb559 100644
--- a/gcc/genmodes.cc
+++ b/gcc/genmodes.cc
@@ -1141,10 +1141,10 @@ inline __attribute__((__always_inline__))\n\
 #else\n\
 extern __inline__ __attribute__((__always_inline__, __gnu_inline__))\n\  #endif\n\ -unsigned char\n\
+unsigned short\n\
 mode_inner_inline (machine_mode mode)\n\  {\n\
-  extern const unsigned char mode_inner[NUM_MACHINE_MODES];\n\
+  extern const unsigned short mode_inner[NUM_MACHINE_MODES];\n\
   gcc_assert (mode >= 0 && mode < NUM_MACHINE_MODES);\n\
   switch (mode)\n\
     {");
@@ -1529,7 +1529,7 @@ emit_mode_wider (void)
   int c;
   struct mode_data *m;
 
-  print_decl ("unsigned char", "mode_next", "NUM_MACHINE_MODES");
+  print_decl ("unsigned short", "mode_next", "NUM_MACHINE_MODES");
 
   for_all_modes (c, m)
     tagged_printf ("E_%smode",
@@ -1537,7 +1537,7 @@ emit_mode_wider (void)
 		   m->name);
 
   print_closer ();
-  print_decl ("unsigned char", "mode_wider", "NUM_MACHINE_MODES");
+  print_decl ("unsigned short", "mode_wider", "NUM_MACHINE_MODES");
 
   for_all_modes (c, m)
     {
@@ -1568,7 +1568,7 @@ emit_mode_wider (void)
     }
 
   print_closer ();
-  print_decl ("unsigned char", "mode_2xwider", "NUM_MACHINE_MODES");
+  print_decl ("unsigned short", "mode_2xwider", "NUM_MACHINE_MODES");
 
   for_all_modes (c, m)
     {
@@ -1625,7 +1625,7 @@ emit_mode_complex (void)
   int c;
   struct mode_data *m;
 
-  print_decl ("unsigned char", "mode_complex", "NUM_MACHINE_MODES");
+  print_decl ("unsigned short", "mode_complex", "NUM_MACHINE_MODES");
 
   for_all_modes (c, m)
     tagged_printf ("E_%smode",
@@ -1665,7 +1665,7 @@ emit_mode_inner (void)
   int c;
   struct mode_data *m;
 
-  print_decl ("unsigned char", "mode_inner", "NUM_MACHINE_MODES");
+  print_decl ("unsigned short", "mode_inner", "NUM_MACHINE_MODES");
 
   for_all_modes (c, m)
     tagged_printf ("E_%smode",
@@ -1738,7 +1738,7 @@ emit_class_narrowest_mode (void)  {
   int c;
 
-  print_decl ("unsigned char", "class_narrowest_mode", "MAX_MODE_CLASS");
+  print_decl ("unsigned short", "class_narrowest_mode", 
+ "MAX_MODE_CLASS");
 
   for (c = 0; c < MAX_MODE_CLASS; c++)
     {
diff --git a/gcc/genopinit.cc b/gcc/genopinit.cc index 83cb7504fa1..0c1b6859ca0 100644
--- a/gcc/genopinit.cc
+++ b/gcc/genopinit.cc
@@ -182,7 +182,8 @@ main (int argc, const char **argv)
 
   progname = "genopinit";
 
-  if (NUM_OPTABS > 0xffff || MAX_MACHINE_MODE >= 0xff)
+  if (NUM_OPTABS > 0xffff
+    || MAX_MACHINE_MODE >= ((1 << MACHINE_MODE_BITSIZE) - 1))
     fatal ("genopinit range assumptions invalid");
 
   if (!init_rtx_reader_args_cb (argc, argv, handle_arg)) diff --git a/gcc/ira-int.h b/gcc/ira-int.h index e2de47213b4..e7460cfd906 100644
--- a/gcc/ira-int.h
+++ b/gcc/ira-int.h
@@ -281,13 +281,20 @@ struct ira_allocno
   int regno;
   /* Mode of the allocno which is the mode of the corresponding
      pseudo-register.  */
-  ENUM_BITFIELD (machine_mode) mode : 8;
+  ENUM_BITFIELD (machine_mode) mode : MACHINE_MODE_BITSIZE;
   /* Widest mode of the allocno which in at least one case could be
      for paradoxical subregs where wmode > mode.  */
-  ENUM_BITFIELD (machine_mode) wmode : 8;
+  ENUM_BITFIELD (machine_mode) wmode : MACHINE_MODE_BITSIZE;
   /* Register class which should be used for allocation for given
      allocno.  NO_REGS means that we should use memory.  */
   ENUM_BITFIELD (reg_class) aclass : 16;
+  /* Hard register assigned to given allocno.  Negative value means
+     that memory was allocated to the allocno.  During the reload,
+     spilled allocno has value equal to the corresponding stack slot
+     number (0, ...) - 2.  Value -1 is used for allocnos spilled by the
+     reload (at this point pseudo-register has only one allocno) which
+     did not get stack slot yet.  */
+  signed int hard_regno : 16;
   /* A bitmask of the ABIs used by calls that occur while the allocno
      is live.  */
   unsigned int crossed_calls_abis : NUM_ABI_IDS; @@ -321,22 +328,6 @@ struct ira_allocno
 
      This is only ever true for non-cap allocnos.  */
   unsigned int might_conflict_with_parent_p : 1;
-  /* Hard register assigned to given allocno.  Negative value means
-     that memory was allocated to the allocno.  During the reload,
-     spilled allocno has value equal to the corresponding stack slot
-     number (0, ...) - 2.  Value -1 is used for allocnos spilled by the
-     reload (at this point pseudo-register has only one allocno) which
-     did not get stack slot yet.  */
-  signed int hard_regno : 16;
-  /* Allocnos with the same regno are linked by the following member.
-     Allocnos corresponding to inner loops are first in the list (it
-     corresponds to depth-first traverse of the loops).  */
-  ira_allocno_t next_regno_allocno;
-  /* There may be different allocnos with the same regno in different
-     regions.  Allocnos are bound to the corresponding loop tree node.
-     Pseudo-register may have only one regular allocno with given loop
-     tree node but more than one cap (see comments above).  */
-  ira_loop_tree_node_t loop_tree_node;
   /* Accumulated usage references of the allocno.  Here and below,
      word 'accumulated' means info for given region and all nested
      subregions.  In this case, 'accumulated' means sum of references @@ -362,6 +353,25 @@ struct ira_allocno
      register class living at the point than number of hard-registers
      of the class available for the allocation.  */
   int excess_pressure_points_num;
+  /* The number of objects tracked in the following array.  */  int 
+ num_objects;
+  /* Accumulated frequency of calls which given allocno
+     intersects.  */
+  int call_freq;
+  /* Accumulated number of the intersected calls.  */  int 
+ calls_crossed_num;
+  /* The number of calls across which it is live, but which should not
+     affect register preferences.  */
+  int cheap_calls_crossed_num;
+  /* Allocnos with the same regno are linked by the following member.
+     Allocnos corresponding to inner loops are first in the list (it
+     corresponds to depth-first traverse of the loops).  */  
+ ira_allocno_t next_regno_allocno;
+  /* There may be different allocnos with the same regno in different
+     regions.  Allocnos are bound to the corresponding loop tree node.
+     Pseudo-register may have only one regular allocno with given loop
+     tree node but more than one cap (see comments above).  */  
+ ira_loop_tree_node_t loop_tree_node;
   /* Allocno hard reg preferences.  */
   ira_pref_t allocno_prefs;
   /* Copies to other non-conflicting allocnos.  The copies can @@ -374,21 +384,11 @@ struct ira_allocno
   /* It is a link to allocno (cap) on lower loop level represented by
      given cap.  Null if given allocno is not a cap.  */
   ira_allocno_t cap_member;
-  /* The number of objects tracked in the following array.  */
-  int num_objects;
   /* An array of structures describing conflict information and live
      ranges for each object associated with the allocno.  There may be
      more than one such object in cases where the allocno represents a
      multi-word register.  */
   ira_object_t objects[2];
-  /* Accumulated frequency of calls which given allocno
-     intersects.  */
-  int call_freq;
-  /* Accumulated number of the intersected calls.  */
-  int calls_crossed_num;
-  /* The number of calls across which it is live, but which should not
-     affect register preferences.  */
-  int cheap_calls_crossed_num;
   /* Registers clobbered by intersected calls.  */
    HARD_REG_SET crossed_calls_clobbered_regs;
   /* Array of usage costs (accumulated and the one updated during diff --git a/gcc/machmode.h b/gcc/machmode.h index f1865c1ef42..a22df60dc20 100644
--- a/gcc/machmode.h
+++ b/gcc/machmode.h
@@ -24,13 +24,13 @@ typedef opt_mode<machine_mode> opt_machine_mode;
 
 extern CONST_MODE_SIZE poly_uint16_pod mode_size[NUM_MACHINE_MODES];  extern CONST_MODE_PRECISION poly_uint16_pod mode_precision[NUM_MACHINE_MODES];
-extern const unsigned char mode_inner[NUM_MACHINE_MODES];
+extern const unsigned short mode_inner[NUM_MACHINE_MODES];
 extern CONST_MODE_NUNITS poly_uint16_pod mode_nunits[NUM_MACHINE_MODES];  extern CONST_MODE_UNIT_SIZE unsigned char mode_unit_size[NUM_MACHINE_MODES];
 extern const unsigned short mode_unit_precision[NUM_MACHINE_MODES];
-extern const unsigned char mode_next[NUM_MACHINE_MODES]; -extern const unsigned char mode_wider[NUM_MACHINE_MODES]; -extern const unsigned char mode_2xwider[NUM_MACHINE_MODES];
+extern const unsigned short mode_next[NUM_MACHINE_MODES]; extern const 
+unsigned short mode_wider[NUM_MACHINE_MODES]; extern const unsigned 
+short mode_2xwider[NUM_MACHINE_MODES];
 
 template<typename T>
 struct mode_traits
@@ -242,6 +242,21 @@ extern const unsigned char mode_class[NUM_MACHINE_MODES];
    || CLASS == MODE_ACCUM                      \
    || CLASS == MODE_UACCUM)
 
+/* The MACHINE_MODE_BITSIZE should be exactly aligned with the type of the
+   machine_mode array in the machmode.h and genmodes.cc.  For example as below.
+   +------------------------+-------+
+   | MACHINE_MODE_BITSIZE   |    16 |
+   +------------------------+-------+
+   | mode_inter[]           | short |
+   | mode_next[]            | short |
+   | mode_wider[]           | short |
+   | mode_2xwider[]         | short |
+   | mode_complex[]         | short |
+   | class_narrowest_mode[] | short |
+   +------------------------+-------+
+   */
+#define MACHINE_MODE_BITSIZE 16
+
 /* An optional T (i.e. a T or nothing), where T is some form of mode class.  */  template<typename T>  class opt_mode @@ -797,7 +812,7 @@ GET_MODE_2XWIDER_MODE (const T &m)  }
 
 /* Get the complex mode from the component mode.  */ -extern const unsigned char mode_complex[NUM_MACHINE_MODES];
+extern const unsigned short mode_complex[NUM_MACHINE_MODES];
 #define GET_MODE_COMPLEX_MODE(MODE) ((machine_mode) mode_complex[MODE])
 
 /* Represents a machine mode that must have a fixed size.  The main @@ -946,7 +961,7 @@ extern unsigned get_mode_alignment (machine_mode);
 
 /* For each class, get the narrowest mode in that class.  */
 
-extern const unsigned char class_narrowest_mode[MAX_MODE_CLASS];
+extern const unsigned short class_narrowest_mode[MAX_MODE_CLASS];
 #define GET_CLASS_NARROWEST_MODE(CLASS) \
   ((machine_mode) class_narrowest_mode[CLASS])
 
diff --git a/gcc/ree.cc b/gcc/ree.cc
index 413aec7c8eb..fc04249fa84 100644
--- a/gcc/ree.cc
+++ b/gcc/ree.cc
@@ -564,10 +564,10 @@ enum ext_modified_kind
   EXT_MODIFIED_SEXT
 };
 
-struct ATTRIBUTE_PACKED ext_modified
+struct ext_modified
 {
   /* Mode from which ree has zero or sign extended the destination.  */
-  ENUM_BITFIELD(machine_mode) mode : 8;
+  ENUM_BITFIELD(machine_mode) mode : MACHINE_MODE_BITSIZE;
 
   /* Kind of modification of the insn.  */
   ENUM_BITFIELD(ext_modified_kind) kind : 2; diff --git a/gcc/rtl-ssa/accesses.h b/gcc/rtl-ssa/accesses.h index c5180b9308a..38b4d6160c2 100644
--- a/gcc/rtl-ssa/accesses.h
+++ b/gcc/rtl-ssa/accesses.h
@@ -254,7 +254,7 @@ private:
   unsigned int m_spare : 2;
 
   // The value returned by the accessor above.
-  machine_mode m_mode : 8;
+  machine_mode m_mode : MACHINE_MODE_BITSIZE;
 };
 
 // A contiguous array of access_info pointers.  Used to represent a diff --git a/gcc/rtl.h b/gcc/rtl.h index f634cab730b..364782b6060 100644
--- a/gcc/rtl.h
+++ b/gcc/rtl.h
@@ -63,6 +63,8 @@ enum rtx_code  {
 # define NON_GENERATOR_NUM_RTX_CODE ((int) MATCH_OPERAND)  #endif
 
+#define RTX_CODE_BITSIZE 8
+
 /* Register Transfer Language EXPRESSIONS CODE CLASSES */
 
 enum rtx_class  {
@@ -309,11 +311,11 @@ struct GTY((variable_size)) const_poly_int_def {  struct GTY((desc("0"), tag("0"),
 	    chain_next ("RTX_NEXT (&%h)"),
 	    chain_prev ("RTX_PREV (&%h)"))) rtx_def {
-  /* The kind of expression this is.  */
-  ENUM_BITFIELD(rtx_code) code: 16;
-
   /* The kind of value the expression has.  */
-  ENUM_BITFIELD(machine_mode) mode : 8;
+  ENUM_BITFIELD(machine_mode) mode : MACHINE_MODE_BITSIZE;
+
+  /* The kind of expression this is.  */
+  ENUM_BITFIELD(rtx_code) code: RTX_CODE_BITSIZE;
 
   /* 1 in a MEM if we should keep the alias set for this mem unchanged
      when we access a component.
@@ -2164,7 +2166,7 @@ subreg_shape::operator != (const subreg_shape &other) const  inline unsigned HOST_WIDE_INT  subreg_shape::unique_id () const  {
-  { STATIC_ASSERT (MAX_MACHINE_MODE <= 256); }
+  { STATIC_ASSERT (MAX_MACHINE_MODE <= (1 << MACHINE_MODE_BITSIZE)); }
   { STATIC_ASSERT (NUM_POLY_INT_COEFFS <= 3); }
   { STATIC_ASSERT (sizeof (offset.coeffs[0]) <= 2); }
   int res = (int) inner_mode + ((int) outer_mode << 8); diff --git a/gcc/rtlanal.h b/gcc/rtlanal.h index 5fbed816e20..9013e75c04b 100644
--- a/gcc/rtlanal.h
+++ b/gcc/rtlanal.h
@@ -100,7 +100,7 @@ public:
 
   /* The mode of the reference.  If IS_MULTIREG, this is the mode of
      REGNO - MULTIREG_OFFSET.  */
-  machine_mode mode : 8;
+  machine_mode mode : MACHINE_MODE_BITSIZE;
 
   /* If IS_MULTIREG, the offset of REGNO from the start of the register.  */
   unsigned int multireg_offset : 8;
diff --git a/gcc/tree-core.h b/gcc/tree-core.h index a1aea136e75..9d44c04bf03 100644
--- a/gcc/tree-core.h
+++ b/gcc/tree-core.h
@@ -1680,8 +1680,9 @@ struct GTY(()) tree_type_common {
   tree attributes;
   unsigned int uid;
 
+  ENUM_BITFIELD(machine_mode) mode : MACHINE_MODE_BITSIZE;
+
   unsigned int precision : 16;
-  ENUM_BITFIELD(machine_mode) mode : 8;
   unsigned lang_flag_0 : 1;
   unsigned lang_flag_1 : 1;
   unsigned lang_flag_2 : 1;
@@ -1712,7 +1713,7 @@ struct GTY(()) tree_type_common {
   unsigned empty_flag : 1;
   unsigned indivisible_p : 1;
   unsigned no_named_args_stdarg_p : 1;
-  unsigned spare : 9;
+  unsigned spare : 1;
 
   alias_set_type alias_set;
   tree pointer_to;
@@ -1770,7 +1771,7 @@ struct GTY(()) tree_decl_common {
   struct tree_decl_minimal common;
   tree size;
 
-  ENUM_BITFIELD(machine_mode) mode : 8;
+  ENUM_BITFIELD(machine_mode) mode : MACHINE_MODE_BITSIZE;
 
   unsigned nonlocal_flag : 1;
   unsigned virtual_flag : 1;
@@ -1828,7 +1829,7 @@ struct GTY(()) tree_decl_common {
   /* In FIELD_DECL, this is DECL_NOT_FLEXARRAY.  */
   unsigned int decl_not_flexarray : 1;
 
-  /* 13 bits unused.  */
+  /* 5 bits unused.  */
 
   /* UID for points-to sets, stable over copying from inlining.  */
   unsigned int pt_uid;
--
2.34.1
  
Richard Sandiford May 16, 2023, 7:29 a.m. UTC | #2
"Li, Pan2" <pan2.li@intel.com> writes:
> Kindly ping for this PATCH v3.

The patch was sent on Saturday, so this is effectively pinging after
one working day in most of Europe and America.  That's too soon and
comes across as aggressive.

I realise you and others are working intensively on this.  But in a
sense that's part of the reason why reviews might seem slow.  The volume
of RVV patches recently has been pretty high, so it's been difficult to
keep up.  There are have also been many other non-RVV patches that have
been "unlocked" by stage 1 opening, so there's a high volume from that
as well.

Also, please bear in mind that most people active in the GCC community
have their own work to do and can only a dedicate a certain amount of
the day to reviews.  And reviewing patches can be time-consuming in
itsself.

So sometimes a patch will get a review within the day.  Sometimes it
will take a bit longer.  The fact that a patch doesn't get a response
within one working day doesn't mean that it's been forgotten.

Thanks,
Richard
  
Li, Pan2 via Gcc-patches May 16, 2023, 7:55 a.m. UTC | #3
I see, thanks Richard for reminding. I am sorry I failed to locate anywhere(doc or something else) mentioned such convention about ping, will follow the below convention in future.

Pan

-----Original Message-----
From: Richard Sandiford <richard.sandiford@arm.com> 
Sent: Tuesday, May 16, 2023 3:30 PM
To: Li, Pan2 <pan2.li@intel.com>
Cc: gcc-patches@gcc.gnu.org; juzhe.zhong@rivai.ai; kito.cheng@sifive.com; Wang, Yanzhang <yanzhang.wang@intel.com>; jeffreyalaw@gmail.com; rguenther@suse.de
Subject: Re: [PATCH v3] Machine_Mode: Extend machine_mode from 8 to 16 bits

"Li, Pan2" <pan2.li@intel.com> writes:
> Kindly ping for this PATCH v3.

The patch was sent on Saturday, so this is effectively pinging after one working day in most of Europe and America.  That's too soon and comes across as aggressive.

I realise you and others are working intensively on this.  But in a sense that's part of the reason why reviews might seem slow.  The volume of RVV patches recently has been pretty high, so it's been difficult to keep up.  There are have also been many other non-RVV patches that have been "unlocked" by stage 1 opening, so there's a high volume from that as well.

Also, please bear in mind that most people active in the GCC community have their own work to do and can only a dedicate a certain amount of the day to reviews.  And reviewing patches can be time-consuming in itsself.

So sometimes a patch will get a review within the day.  Sometimes it will take a bit longer.  The fact that a patch doesn't get a response within one working day doesn't mean that it's been forgotten.

Thanks,
Richard
  
Xi Ruoyao May 16, 2023, 8:03 a.m. UTC | #4
On Tue, 2023-05-16 at 07:55 +0000, Li, Pan2 via Gcc-patches wrote:
> I see, thanks Richard for reminding. I am sorry I failed to locate
> anywhere(doc or something else) mentioned such convention about ping,

https://gcc.gnu.org/contribute.html suggests two week.

> will follow the below convention in future.
> 
> Pan
> 
> -----Original Message-----
> From: Richard Sandiford <richard.sandiford@arm.com> 
> Sent: Tuesday, May 16, 2023 3:30 PM
> To: Li, Pan2 <pan2.li@intel.com>
> Cc: gcc-patches@gcc.gnu.org; juzhe.zhong@rivai.ai;
> kito.cheng@sifive.com; Wang, Yanzhang <yanzhang.wang@intel.com>;
> jeffreyalaw@gmail.com; rguenther@suse.de
> Subject: Re: [PATCH v3] Machine_Mode: Extend machine_mode from 8 to 16
> bits
> 
> "Li, Pan2" <pan2.li@intel.com> writes:
> > Kindly ping for this PATCH v3.
> 
> The patch was sent on Saturday, so this is effectively pinging after
> one working day in most of Europe and America.  That's too soon and
> comes across as aggressive.
> 
> I realise you and others are working intensively on this.  But in a
> sense that's part of the reason why reviews might seem slow.  The
> volume of RVV patches recently has been pretty high, so it's been
> difficult to keep up.  There are have also been many other non-RVV
> patches that have been "unlocked" by stage 1 opening, so there's a
> high volume from that as well.
> 
> Also, please bear in mind that most people active in the GCC community
> have their own work to do and can only a dedicate a certain amount of
> the day to reviews.  And reviewing patches can be time-consuming in
> itsself.
> 
> So sometimes a patch will get a review within the day.  Sometimes it
> will take a bit longer.  The fact that a patch doesn't get a response
> within one working day doesn't mean that it's been forgotten.
> 
> Thanks,
> Richard
  
Li, Pan2 via Gcc-patches May 16, 2023, 8:05 a.m. UTC | #5
Got it. Thank you!

Pan

-----Original Message-----
From: Xi Ruoyao <xry111@xry111.site> 
Sent: Tuesday, May 16, 2023 4:04 PM
To: Li, Pan2 <pan2.li@intel.com>; Richard Sandiford <richard.sandiford@arm.com>
Cc: gcc-patches@gcc.gnu.org; juzhe.zhong@rivai.ai; kito.cheng@sifive.com; Wang, Yanzhang <yanzhang.wang@intel.com>; jeffreyalaw@gmail.com; rguenther@suse.de
Subject: Re: [PATCH v3] Machine_Mode: Extend machine_mode from 8 to 16 bits

On Tue, 2023-05-16 at 07:55 +0000, Li, Pan2 via Gcc-patches wrote:
> I see, thanks Richard for reminding. I am sorry I failed to locate 
> anywhere(doc or something else) mentioned such convention about ping,

https://gcc.gnu.org/contribute.html suggests two week.

> will follow the below convention in future.
> 
> Pan
> 
> -----Original Message-----
> From: Richard Sandiford <richard.sandiford@arm.com>
> Sent: Tuesday, May 16, 2023 3:30 PM
> To: Li, Pan2 <pan2.li@intel.com>
> Cc: gcc-patches@gcc.gnu.org; juzhe.zhong@rivai.ai; 
> kito.cheng@sifive.com; Wang, Yanzhang <yanzhang.wang@intel.com>; 
> jeffreyalaw@gmail.com; rguenther@suse.de
> Subject: Re: [PATCH v3] Machine_Mode: Extend machine_mode from 8 to 16 
> bits
> 
> "Li, Pan2" <pan2.li@intel.com> writes:
> > Kindly ping for this PATCH v3.
> 
> The patch was sent on Saturday, so this is effectively pinging after 
> one working day in most of Europe and America.  That's too soon and 
> comes across as aggressive.
> 
> I realise you and others are working intensively on this.  But in a 
> sense that's part of the reason why reviews might seem slow.  The 
> volume of RVV patches recently has been pretty high, so it's been 
> difficult to keep up.  There are have also been many other non-RVV 
> patches that have been "unlocked" by stage 1 opening, so there's a 
> high volume from that as well.
> 
> Also, please bear in mind that most people active in the GCC community 
> have their own work to do and can only a dedicate a certain amount of 
> the day to reviews.  And reviewing patches can be time-consuming in 
> itsself.
> 
> So sometimes a patch will get a review within the day.  Sometimes it 
> will take a bit longer.  The fact that a patch doesn't get a response 
> within one working day doesn't mean that it's been forgotten.
> 
> Thanks,
> Richard

--
Xi Ruoyao <xry111@xry111.site>
School of Aerospace Science and Technology, Xidian University
  
Richard Sandiford May 16, 2023, 9:09 a.m. UTC | #6
pan2.li@intel.com writes:
> diff --git a/gcc/rtl-ssa/accesses.h b/gcc/rtl-ssa/accesses.h
> index c5180b9308a..38b4d6160c2 100644
> --- a/gcc/rtl-ssa/accesses.h
> +++ b/gcc/rtl-ssa/accesses.h
> @@ -254,7 +254,7 @@ private:
>    unsigned int m_spare : 2;
>  
>    // The value returned by the accessor above.
> -  machine_mode m_mode : 8;
> +  machine_mode m_mode : MACHINE_MODE_BITSIZE;
>  };
>  
>  // A contiguous array of access_info pointers.  Used to represent a

This structure (access_info) isn't mentioned in the table in the patch
description.  The structure is currently 1 LP64 word and is very
size-sensitive.  I think we should:

- Put the mode after m_regno
- Reduce m_kind to 2 bits
- Remove m_spare

I *think* that will keep the current size, but please check.

LGTM otherwise.

Thanks,
Richard
  
Li, Pan2 via Gcc-patches May 16, 2023, 12:17 p.m. UTC | #7
Thanks Richard Sandiford for review.

Yes, currently the class access_info will be extended from 8 bytes to 12 bytes, which is missed in the table. With the adjustment as you suggested it will be 8 bytes but unfortunately the change of m_kind may trigger some ICE in some test case(s).

I will take a look into it and keep you posted.

Pan

-----Original Message-----
From: Richard Sandiford <richard.sandiford@arm.com> 
Sent: Tuesday, May 16, 2023 5:09 PM
To: Li, Pan2 <pan2.li@intel.com>
Cc: gcc-patches@gcc.gnu.org; juzhe.zhong@rivai.ai; kito.cheng@sifive.com; Wang, Yanzhang <yanzhang.wang@intel.com>; jeffreyalaw@gmail.com; rguenther@suse.de
Subject: Re: [PATCH v3] Machine_Mode: Extend machine_mode from 8 to 16 bits

pan2.li@intel.com writes:
> diff --git a/gcc/rtl-ssa/accesses.h b/gcc/rtl-ssa/accesses.h index 
> c5180b9308a..38b4d6160c2 100644
> --- a/gcc/rtl-ssa/accesses.h
> +++ b/gcc/rtl-ssa/accesses.h
> @@ -254,7 +254,7 @@ private:
>    unsigned int m_spare : 2;
>  
>    // The value returned by the accessor above.
> -  machine_mode m_mode : 8;
> +  machine_mode m_mode : MACHINE_MODE_BITSIZE;
>  };
>  
>  // A contiguous array of access_info pointers.  Used to represent a

This structure (access_info) isn't mentioned in the table in the patch description.  The structure is currently 1 LP64 word and is very size-sensitive.  I think we should:

- Put the mode after m_regno
- Reduce m_kind to 2 bits
- Remove m_spare

I *think* that will keep the current size, but please check.

LGTM otherwise.

Thanks,
Richard
  
Li, Pan2 via Gcc-patches May 16, 2023, 3:39 p.m. UTC | #8
Update the PATCH v4 (I am sorry, missed the v4 in subject) as below with x86 bootstrap test passed.

https://gcc.gnu.org/pipermail/gcc-patches/2023-May/618742.html

Pan

-----Original Message-----
From: Gcc-patches <gcc-patches-bounces+pan2.li=intel.com@gcc.gnu.org> On Behalf Of Li, Pan2 via Gcc-patches
Sent: Tuesday, May 16, 2023 8:17 PM
To: Richard Sandiford <richard.sandiford@arm.com>
Cc: gcc-patches@gcc.gnu.org; juzhe.zhong@rivai.ai; kito.cheng@sifive.com; Wang, Yanzhang <yanzhang.wang@intel.com>; jeffreyalaw@gmail.com; rguenther@suse.de
Subject: RE: [PATCH v3] Machine_Mode: Extend machine_mode from 8 to 16 bits

Thanks Richard Sandiford for review.

Yes, currently the class access_info will be extended from 8 bytes to 12 bytes, which is missed in the table. With the adjustment as you suggested it will be 8 bytes but unfortunately the change of m_kind may trigger some ICE in some test case(s).

I will take a look into it and keep you posted.

Pan

-----Original Message-----
From: Richard Sandiford <richard.sandiford@arm.com> 
Sent: Tuesday, May 16, 2023 5:09 PM
To: Li, Pan2 <pan2.li@intel.com>
Cc: gcc-patches@gcc.gnu.org; juzhe.zhong@rivai.ai; kito.cheng@sifive.com; Wang, Yanzhang <yanzhang.wang@intel.com>; jeffreyalaw@gmail.com; rguenther@suse.de
Subject: Re: [PATCH v3] Machine_Mode: Extend machine_mode from 8 to 16 bits

pan2.li@intel.com writes:
> diff --git a/gcc/rtl-ssa/accesses.h b/gcc/rtl-ssa/accesses.h index 
> c5180b9308a..38b4d6160c2 100644
> --- a/gcc/rtl-ssa/accesses.h
> +++ b/gcc/rtl-ssa/accesses.h
> @@ -254,7 +254,7 @@ private:
>    unsigned int m_spare : 2;
>  
>    // The value returned by the accessor above.
> -  machine_mode m_mode : 8;
> +  machine_mode m_mode : MACHINE_MODE_BITSIZE;
>  };
>  
>  // A contiguous array of access_info pointers.  Used to represent a

This structure (access_info) isn't mentioned in the table in the patch description.  The structure is currently 1 LP64 word and is very size-sensitive.  I think we should:

- Put the mode after m_regno
- Reduce m_kind to 2 bits
- Remove m_spare

I *think* that will keep the current size, but please check.

LGTM otherwise.

Thanks,
Richard
  

Patch

diff --git a/gcc/combine.cc b/gcc/combine.cc
index 5aa0ec5c45a..a23caeed96f 100644
--- a/gcc/combine.cc
+++ b/gcc/combine.cc
@@ -200,7 +200,7 @@  struct reg_stat_type {
 
   unsigned HOST_WIDE_INT	last_set_nonzero_bits;
   char				last_set_sign_bit_copies;
-  ENUM_BITFIELD(machine_mode)	last_set_mode : 8;
+  ENUM_BITFIELD(machine_mode)	last_set_mode : MACHINE_MODE_BITSIZE;
 
   /* Set nonzero if references to register n in expressions should not be
      used.  last_set_invalid is set nonzero when this register is being
@@ -235,7 +235,7 @@  struct reg_stat_type {
      truncation if we know that value already contains a truncated
      value.  */
 
-  ENUM_BITFIELD(machine_mode)	truncated_to_mode : 8;
+  ENUM_BITFIELD(machine_mode)	truncated_to_mode : MACHINE_MODE_BITSIZE;
 };
 
 
diff --git a/gcc/cse.cc b/gcc/cse.cc
index b10c9b0c94d..86403b95938 100644
--- a/gcc/cse.cc
+++ b/gcc/cse.cc
@@ -248,10 +248,8 @@  struct qty_table_elem
   rtx comparison_const;
   int comparison_qty;
   unsigned int first_reg, last_reg;
-  /* The sizes of these fields should match the sizes of the
-     code and mode fields of struct rtx_def (see rtl.h).  */
-  ENUM_BITFIELD(rtx_code) comparison_code : 16;
-  ENUM_BITFIELD(machine_mode) mode : 8;
+  ENUM_BITFIELD(machine_mode) mode : MACHINE_MODE_BITSIZE;
+  ENUM_BITFIELD(rtx_code) comparison_code : RTX_CODE_BITSIZE;
 };
 
 /* The table of all qtys, indexed by qty number.  */
@@ -404,9 +402,7 @@  struct table_elt
   struct table_elt *related_value;
   int cost;
   int regcost;
-  /* The size of this field should match the size
-     of the mode field of struct rtx_def (see rtl.h).  */
-  ENUM_BITFIELD(machine_mode) mode : 8;
+  ENUM_BITFIELD(machine_mode) mode : MACHINE_MODE_BITSIZE;
   char in_memory;
   char is_const;
   char flag;
@@ -4152,10 +4148,8 @@  struct set
   /* Nonzero if the SET_SRC contains something
      whose value cannot be predicted and understood.  */
   char src_volatile;
-  /* Original machine mode, in case it becomes a CONST_INT.
-     The size of this field should match the size of the mode
-     field of struct rtx_def (see rtl.h).  */
-  ENUM_BITFIELD(machine_mode) mode : 8;
+  /* Original machine mode, in case it becomes a CONST_INT.  */
+  ENUM_BITFIELD(machine_mode) mode : MACHINE_MODE_BITSIZE;
   /* Hash value of constant equivalent for SET_SRC.  */
   unsigned src_const_hash;
   /* A constant equivalent for SET_SRC, if any.  */
diff --git a/gcc/genmodes.cc b/gcc/genmodes.cc
index 715787b8f48..55ac2adb559 100644
--- a/gcc/genmodes.cc
+++ b/gcc/genmodes.cc
@@ -1141,10 +1141,10 @@  inline __attribute__((__always_inline__))\n\
 #else\n\
 extern __inline__ __attribute__((__always_inline__, __gnu_inline__))\n\
 #endif\n\
-unsigned char\n\
+unsigned short\n\
 mode_inner_inline (machine_mode mode)\n\
 {\n\
-  extern const unsigned char mode_inner[NUM_MACHINE_MODES];\n\
+  extern const unsigned short mode_inner[NUM_MACHINE_MODES];\n\
   gcc_assert (mode >= 0 && mode < NUM_MACHINE_MODES);\n\
   switch (mode)\n\
     {");
@@ -1529,7 +1529,7 @@  emit_mode_wider (void)
   int c;
   struct mode_data *m;
 
-  print_decl ("unsigned char", "mode_next", "NUM_MACHINE_MODES");
+  print_decl ("unsigned short", "mode_next", "NUM_MACHINE_MODES");
 
   for_all_modes (c, m)
     tagged_printf ("E_%smode",
@@ -1537,7 +1537,7 @@  emit_mode_wider (void)
 		   m->name);
 
   print_closer ();
-  print_decl ("unsigned char", "mode_wider", "NUM_MACHINE_MODES");
+  print_decl ("unsigned short", "mode_wider", "NUM_MACHINE_MODES");
 
   for_all_modes (c, m)
     {
@@ -1568,7 +1568,7 @@  emit_mode_wider (void)
     }
 
   print_closer ();
-  print_decl ("unsigned char", "mode_2xwider", "NUM_MACHINE_MODES");
+  print_decl ("unsigned short", "mode_2xwider", "NUM_MACHINE_MODES");
 
   for_all_modes (c, m)
     {
@@ -1625,7 +1625,7 @@  emit_mode_complex (void)
   int c;
   struct mode_data *m;
 
-  print_decl ("unsigned char", "mode_complex", "NUM_MACHINE_MODES");
+  print_decl ("unsigned short", "mode_complex", "NUM_MACHINE_MODES");
 
   for_all_modes (c, m)
     tagged_printf ("E_%smode",
@@ -1665,7 +1665,7 @@  emit_mode_inner (void)
   int c;
   struct mode_data *m;
 
-  print_decl ("unsigned char", "mode_inner", "NUM_MACHINE_MODES");
+  print_decl ("unsigned short", "mode_inner", "NUM_MACHINE_MODES");
 
   for_all_modes (c, m)
     tagged_printf ("E_%smode",
@@ -1738,7 +1738,7 @@  emit_class_narrowest_mode (void)
 {
   int c;
 
-  print_decl ("unsigned char", "class_narrowest_mode", "MAX_MODE_CLASS");
+  print_decl ("unsigned short", "class_narrowest_mode", "MAX_MODE_CLASS");
 
   for (c = 0; c < MAX_MODE_CLASS; c++)
     {
diff --git a/gcc/genopinit.cc b/gcc/genopinit.cc
index 83cb7504fa1..0c1b6859ca0 100644
--- a/gcc/genopinit.cc
+++ b/gcc/genopinit.cc
@@ -182,7 +182,8 @@  main (int argc, const char **argv)
 
   progname = "genopinit";
 
-  if (NUM_OPTABS > 0xffff || MAX_MACHINE_MODE >= 0xff)
+  if (NUM_OPTABS > 0xffff
+    || MAX_MACHINE_MODE >= ((1 << MACHINE_MODE_BITSIZE) - 1))
     fatal ("genopinit range assumptions invalid");
 
   if (!init_rtx_reader_args_cb (argc, argv, handle_arg))
diff --git a/gcc/ira-int.h b/gcc/ira-int.h
index e2de47213b4..e7460cfd906 100644
--- a/gcc/ira-int.h
+++ b/gcc/ira-int.h
@@ -281,13 +281,20 @@  struct ira_allocno
   int regno;
   /* Mode of the allocno which is the mode of the corresponding
      pseudo-register.  */
-  ENUM_BITFIELD (machine_mode) mode : 8;
+  ENUM_BITFIELD (machine_mode) mode : MACHINE_MODE_BITSIZE;
   /* Widest mode of the allocno which in at least one case could be
      for paradoxical subregs where wmode > mode.  */
-  ENUM_BITFIELD (machine_mode) wmode : 8;
+  ENUM_BITFIELD (machine_mode) wmode : MACHINE_MODE_BITSIZE;
   /* Register class which should be used for allocation for given
      allocno.  NO_REGS means that we should use memory.  */
   ENUM_BITFIELD (reg_class) aclass : 16;
+  /* Hard register assigned to given allocno.  Negative value means
+     that memory was allocated to the allocno.  During the reload,
+     spilled allocno has value equal to the corresponding stack slot
+     number (0, ...) - 2.  Value -1 is used for allocnos spilled by the
+     reload (at this point pseudo-register has only one allocno) which
+     did not get stack slot yet.  */
+  signed int hard_regno : 16;
   /* A bitmask of the ABIs used by calls that occur while the allocno
      is live.  */
   unsigned int crossed_calls_abis : NUM_ABI_IDS;
@@ -321,22 +328,6 @@  struct ira_allocno
 
      This is only ever true for non-cap allocnos.  */
   unsigned int might_conflict_with_parent_p : 1;
-  /* Hard register assigned to given allocno.  Negative value means
-     that memory was allocated to the allocno.  During the reload,
-     spilled allocno has value equal to the corresponding stack slot
-     number (0, ...) - 2.  Value -1 is used for allocnos spilled by the
-     reload (at this point pseudo-register has only one allocno) which
-     did not get stack slot yet.  */
-  signed int hard_regno : 16;
-  /* Allocnos with the same regno are linked by the following member.
-     Allocnos corresponding to inner loops are first in the list (it
-     corresponds to depth-first traverse of the loops).  */
-  ira_allocno_t next_regno_allocno;
-  /* There may be different allocnos with the same regno in different
-     regions.  Allocnos are bound to the corresponding loop tree node.
-     Pseudo-register may have only one regular allocno with given loop
-     tree node but more than one cap (see comments above).  */
-  ira_loop_tree_node_t loop_tree_node;
   /* Accumulated usage references of the allocno.  Here and below,
      word 'accumulated' means info for given region and all nested
      subregions.  In this case, 'accumulated' means sum of references
@@ -362,6 +353,25 @@  struct ira_allocno
      register class living at the point than number of hard-registers
      of the class available for the allocation.  */
   int excess_pressure_points_num;
+  /* The number of objects tracked in the following array.  */
+  int num_objects;
+  /* Accumulated frequency of calls which given allocno
+     intersects.  */
+  int call_freq;
+  /* Accumulated number of the intersected calls.  */
+  int calls_crossed_num;
+  /* The number of calls across which it is live, but which should not
+     affect register preferences.  */
+  int cheap_calls_crossed_num;
+  /* Allocnos with the same regno are linked by the following member.
+     Allocnos corresponding to inner loops are first in the list (it
+     corresponds to depth-first traverse of the loops).  */
+  ira_allocno_t next_regno_allocno;
+  /* There may be different allocnos with the same regno in different
+     regions.  Allocnos are bound to the corresponding loop tree node.
+     Pseudo-register may have only one regular allocno with given loop
+     tree node but more than one cap (see comments above).  */
+  ira_loop_tree_node_t loop_tree_node;
   /* Allocno hard reg preferences.  */
   ira_pref_t allocno_prefs;
   /* Copies to other non-conflicting allocnos.  The copies can
@@ -374,21 +384,11 @@  struct ira_allocno
   /* It is a link to allocno (cap) on lower loop level represented by
      given cap.  Null if given allocno is not a cap.  */
   ira_allocno_t cap_member;
-  /* The number of objects tracked in the following array.  */
-  int num_objects;
   /* An array of structures describing conflict information and live
      ranges for each object associated with the allocno.  There may be
      more than one such object in cases where the allocno represents a
      multi-word register.  */
   ira_object_t objects[2];
-  /* Accumulated frequency of calls which given allocno
-     intersects.  */
-  int call_freq;
-  /* Accumulated number of the intersected calls.  */
-  int calls_crossed_num;
-  /* The number of calls across which it is live, but which should not
-     affect register preferences.  */
-  int cheap_calls_crossed_num;
   /* Registers clobbered by intersected calls.  */
    HARD_REG_SET crossed_calls_clobbered_regs;
   /* Array of usage costs (accumulated and the one updated during
diff --git a/gcc/machmode.h b/gcc/machmode.h
index f1865c1ef42..a22df60dc20 100644
--- a/gcc/machmode.h
+++ b/gcc/machmode.h
@@ -24,13 +24,13 @@  typedef opt_mode<machine_mode> opt_machine_mode;
 
 extern CONST_MODE_SIZE poly_uint16_pod mode_size[NUM_MACHINE_MODES];
 extern CONST_MODE_PRECISION poly_uint16_pod mode_precision[NUM_MACHINE_MODES];
-extern const unsigned char mode_inner[NUM_MACHINE_MODES];
+extern const unsigned short mode_inner[NUM_MACHINE_MODES];
 extern CONST_MODE_NUNITS poly_uint16_pod mode_nunits[NUM_MACHINE_MODES];
 extern CONST_MODE_UNIT_SIZE unsigned char mode_unit_size[NUM_MACHINE_MODES];
 extern const unsigned short mode_unit_precision[NUM_MACHINE_MODES];
-extern const unsigned char mode_next[NUM_MACHINE_MODES];
-extern const unsigned char mode_wider[NUM_MACHINE_MODES];
-extern const unsigned char mode_2xwider[NUM_MACHINE_MODES];
+extern const unsigned short mode_next[NUM_MACHINE_MODES];
+extern const unsigned short mode_wider[NUM_MACHINE_MODES];
+extern const unsigned short mode_2xwider[NUM_MACHINE_MODES];
 
 template<typename T>
 struct mode_traits
@@ -242,6 +242,21 @@  extern const unsigned char mode_class[NUM_MACHINE_MODES];
    || CLASS == MODE_ACCUM                      \
    || CLASS == MODE_UACCUM)
 
+/* The MACHINE_MODE_BITSIZE should be exactly aligned with the type of the
+   machine_mode array in the machmode.h and genmodes.cc.  For example as below.
+   +------------------------+-------+
+   | MACHINE_MODE_BITSIZE   |    16 |
+   +------------------------+-------+
+   | mode_inter[]           | short |
+   | mode_next[]            | short |
+   | mode_wider[]           | short |
+   | mode_2xwider[]         | short |
+   | mode_complex[]         | short |
+   | class_narrowest_mode[] | short |
+   +------------------------+-------+
+   */
+#define MACHINE_MODE_BITSIZE 16
+
 /* An optional T (i.e. a T or nothing), where T is some form of mode class.  */
 template<typename T>
 class opt_mode
@@ -797,7 +812,7 @@  GET_MODE_2XWIDER_MODE (const T &m)
 }
 
 /* Get the complex mode from the component mode.  */
-extern const unsigned char mode_complex[NUM_MACHINE_MODES];
+extern const unsigned short mode_complex[NUM_MACHINE_MODES];
 #define GET_MODE_COMPLEX_MODE(MODE) ((machine_mode) mode_complex[MODE])
 
 /* Represents a machine mode that must have a fixed size.  The main
@@ -946,7 +961,7 @@  extern unsigned get_mode_alignment (machine_mode);
 
 /* For each class, get the narrowest mode in that class.  */
 
-extern const unsigned char class_narrowest_mode[MAX_MODE_CLASS];
+extern const unsigned short class_narrowest_mode[MAX_MODE_CLASS];
 #define GET_CLASS_NARROWEST_MODE(CLASS) \
   ((machine_mode) class_narrowest_mode[CLASS])
 
diff --git a/gcc/ree.cc b/gcc/ree.cc
index 413aec7c8eb..fc04249fa84 100644
--- a/gcc/ree.cc
+++ b/gcc/ree.cc
@@ -564,10 +564,10 @@  enum ext_modified_kind
   EXT_MODIFIED_SEXT
 };
 
-struct ATTRIBUTE_PACKED ext_modified
+struct ext_modified
 {
   /* Mode from which ree has zero or sign extended the destination.  */
-  ENUM_BITFIELD(machine_mode) mode : 8;
+  ENUM_BITFIELD(machine_mode) mode : MACHINE_MODE_BITSIZE;
 
   /* Kind of modification of the insn.  */
   ENUM_BITFIELD(ext_modified_kind) kind : 2;
diff --git a/gcc/rtl-ssa/accesses.h b/gcc/rtl-ssa/accesses.h
index c5180b9308a..38b4d6160c2 100644
--- a/gcc/rtl-ssa/accesses.h
+++ b/gcc/rtl-ssa/accesses.h
@@ -254,7 +254,7 @@  private:
   unsigned int m_spare : 2;
 
   // The value returned by the accessor above.
-  machine_mode m_mode : 8;
+  machine_mode m_mode : MACHINE_MODE_BITSIZE;
 };
 
 // A contiguous array of access_info pointers.  Used to represent a
diff --git a/gcc/rtl.h b/gcc/rtl.h
index f634cab730b..364782b6060 100644
--- a/gcc/rtl.h
+++ b/gcc/rtl.h
@@ -63,6 +63,8 @@  enum rtx_code  {
 # define NON_GENERATOR_NUM_RTX_CODE ((int) MATCH_OPERAND)
 #endif
 
+#define RTX_CODE_BITSIZE 8
+
 /* Register Transfer Language EXPRESSIONS CODE CLASSES */
 
 enum rtx_class  {
@@ -309,11 +311,11 @@  struct GTY((variable_size)) const_poly_int_def {
 struct GTY((desc("0"), tag("0"),
 	    chain_next ("RTX_NEXT (&%h)"),
 	    chain_prev ("RTX_PREV (&%h)"))) rtx_def {
-  /* The kind of expression this is.  */
-  ENUM_BITFIELD(rtx_code) code: 16;
-
   /* The kind of value the expression has.  */
-  ENUM_BITFIELD(machine_mode) mode : 8;
+  ENUM_BITFIELD(machine_mode) mode : MACHINE_MODE_BITSIZE;
+
+  /* The kind of expression this is.  */
+  ENUM_BITFIELD(rtx_code) code: RTX_CODE_BITSIZE;
 
   /* 1 in a MEM if we should keep the alias set for this mem unchanged
      when we access a component.
@@ -2164,7 +2166,7 @@  subreg_shape::operator != (const subreg_shape &other) const
 inline unsigned HOST_WIDE_INT
 subreg_shape::unique_id () const
 {
-  { STATIC_ASSERT (MAX_MACHINE_MODE <= 256); }
+  { STATIC_ASSERT (MAX_MACHINE_MODE <= (1 << MACHINE_MODE_BITSIZE)); }
   { STATIC_ASSERT (NUM_POLY_INT_COEFFS <= 3); }
   { STATIC_ASSERT (sizeof (offset.coeffs[0]) <= 2); }
   int res = (int) inner_mode + ((int) outer_mode << 8);
diff --git a/gcc/rtlanal.h b/gcc/rtlanal.h
index 5fbed816e20..9013e75c04b 100644
--- a/gcc/rtlanal.h
+++ b/gcc/rtlanal.h
@@ -100,7 +100,7 @@  public:
 
   /* The mode of the reference.  If IS_MULTIREG, this is the mode of
      REGNO - MULTIREG_OFFSET.  */
-  machine_mode mode : 8;
+  machine_mode mode : MACHINE_MODE_BITSIZE;
 
   /* If IS_MULTIREG, the offset of REGNO from the start of the register.  */
   unsigned int multireg_offset : 8;
diff --git a/gcc/tree-core.h b/gcc/tree-core.h
index a1aea136e75..9d44c04bf03 100644
--- a/gcc/tree-core.h
+++ b/gcc/tree-core.h
@@ -1680,8 +1680,9 @@  struct GTY(()) tree_type_common {
   tree attributes;
   unsigned int uid;
 
+  ENUM_BITFIELD(machine_mode) mode : MACHINE_MODE_BITSIZE;
+
   unsigned int precision : 16;
-  ENUM_BITFIELD(machine_mode) mode : 8;
   unsigned lang_flag_0 : 1;
   unsigned lang_flag_1 : 1;
   unsigned lang_flag_2 : 1;
@@ -1712,7 +1713,7 @@  struct GTY(()) tree_type_common {
   unsigned empty_flag : 1;
   unsigned indivisible_p : 1;
   unsigned no_named_args_stdarg_p : 1;
-  unsigned spare : 9;
+  unsigned spare : 1;
 
   alias_set_type alias_set;
   tree pointer_to;
@@ -1770,7 +1771,7 @@  struct GTY(()) tree_decl_common {
   struct tree_decl_minimal common;
   tree size;
 
-  ENUM_BITFIELD(machine_mode) mode : 8;
+  ENUM_BITFIELD(machine_mode) mode : MACHINE_MODE_BITSIZE;
 
   unsigned nonlocal_flag : 1;
   unsigned virtual_flag : 1;
@@ -1828,7 +1829,7 @@  struct GTY(()) tree_decl_common {
   /* In FIELD_DECL, this is DECL_NOT_FLEXARRAY.  */
   unsigned int decl_not_flexarray : 1;
 
-  /* 13 bits unused.  */
+  /* 5 bits unused.  */
 
   /* UID for points-to sets, stable over copying from inlining.  */
   unsigned int pt_uid;