GCC-3.4.6源代码学习笔记(139-续2)

在类节点的 TYPE_FIELDS 中,一个 FIELD_DECL 被用来代表一个非静态的数据成员,一个 VAR_DECL 被用来代表一个静态数据成员,而一个 TYPE_DECL 用来代表一个类型。用于一个枚举类型的 CONST_DECL 也会出现在 TYPE_FIELDS 链表中,如果该枚举类型声明在该类里。

4691 4707 行的代码处理非静态成员以外的实体。注意静态成员的类型在类定义中可以是未完成的,因为它不占用类对象的空间。这也显示了 C++ 语言的哲学思想——尽可能灵活。

 

layout_class_type (continue)

 

4683     Layout the non-static data members.  */

4684     for (field = non_static_data_members; field; field = TREE_CHAIN (field))

4685     {

4686       tree type;

4687       tree padding;

4688  

4689        /* We still pass things that aren't non-static data members to

4690         the back-end, in case it wants to do something with them.  */

4691       if (TREE_CODE (field) != FIELD_DECL)

4692       {

4693         place_field (rli, field);

4694          /* If the static data member has incomplete type, keep track

4695           of it so that it can be completed later. (The handling

4696           of pending statics in finish_record_layout is

4697           insufficient; consider:

4698  

4699            struct S1;

4700            struct S2 { static S1 s1; };

4701              

4702           At this point, finish_record_layout will be called, but

4703           S1 is still incomplete.)  */

4704         if (TREE_CODE (field) == VAR_DECL)

4705           maybe_register_incomplete_var (field);

4706         continue ;

4707       }

4708  

4709       type = TREE_TYPE (field);

4710        

4711       padding = NULL_TREE;

4712  

4713       /* If this field is a bit-field whose width is greater than its

4714         type, then there are some special rules for allocating

4715         it.  */

4716       if (DECL_C_BIT_FIELD (field)

4717          && INT_CST_LT (TYPE_SIZE (type), DECL_SIZE (field)))

4718       {

4719         integer_type_kind itk;

4720         tree integer_type;

4721         bool was_unnamed_p = false;

4722         /* We must allocate the bits as if suitably aligned for the

4723           longest integer type that fits in this many bits. type

4724           of the field. Then, we are supposed to use the left over

4725           bits as additional padding.  */

4726         for (itk = itk_char; itk != itk_none; ++itk)

4727           if (INT_CST_LT (DECL_SIZE (field),

4728                          TYPE_SIZE (integer_types[itk])))

4729             break ;

4730  

4731         /* ITK now indicates a type that is too large for the

4732           field. We have to back up by one to find the largest

4733           type that fits.  */

4734         integer_type = integer_types[itk - 1];

4735  

4736         /* Figure out how much additional padding is required. GCC

4737           3.2 always created a padding field, even if it had zero

4738           width.  */

4739         if (!abi_version_at_least (2)

4740            || INT_CST_LT (TYPE_SIZE (integer_type), DECL_SIZE (field)))

4741         {

4742           if (abi_version_at_least (2) && TREE_CODE (t) == UNION_TYPE)

4743             /* In a union, the padding field must have the full width

4744               of the bit-field; all fields start at offset zero.  */

4745             padding = DECL_SIZE (field);

4746           else

4747           {

4748             if (warn_abi && TREE_CODE (t) == UNION_TYPE)

4749               warning ("size assigned to `%T' may not be "

4750                       "ABI-compliant and may change in a future "

4751                       "version of GCC",

4752                       t);

4753             padding = size_binop (MINUS_EXPR, DECL_SIZE (field),

4754                               TYPE_SIZE (integer_type));

4755           }

4756         }

4757   #ifdef PCC_BITFIELD_TYPE_MATTERS

4758         /* An unnamed bitfield does not normally affect the

4759           alignment of the containing class on a target where

4760           PCC_BITFIELD_TYPE_MATTERS. But, the C++ ABI does not

4761           make any exceptions for unnamed bitfields when the

4762           bitfields are longer than their types. Therefore, we

4763           temporarily give the field a name.  */

4764         if (PCC_BITFIELD_TYPE_MATTERS && !DECL_NAME (field))

4765         {

4766           was_unnamed_p = true;

4767           DECL_NAME (field) = make_anon_name ();

4768          }

4769   #endif

4770         DECL_SIZE (field) = TYPE_SIZE (integer_type);

4771         DECL_ALIGN (field) = TYPE_ALIGN (integer_type);

4772         DECL_USER_ALIGN (field) = TYPE_USER_ALIGN (integer_type);

4773         layout_nonempty_base_or_field (rli, field, NULL_TREE,

4774                                    empty_base_offsets);

4775         if (was_unnamed_p)

4776           DECL_NAME (field) = NULL_TREE;

4777          /* Now that layout has been performed, set the size of the

4778           field to the size of its declared type; the rest of the

4779           field is effectively invisible.  */

4780         DECL_SIZE (field) = TYPE_SIZE (type);

4781         /* We must also reset the DECL_MODE of the field.  */

4782         if (abi_version_at_least (2))

4783           DECL_MODE (field) = TYPE_MODE (type);

4784         else if (warn_abi

4785               && DECL_MODE (field) != TYPE_MODE (type))

4786           /* Versions of G++ before G++ 3.4 did not reset the

4787             DECL_MODE.  */

4788           warning ("the offset of `%D' may not be ABI-compliant and may "

4789                   "change in a future version of GCC", field);

4790       }

4791       else

4792         layout_nonempty_base_or_field (rli, field, NULL_TREE,

4793                                    empty_base_offsets);

4794  

4795        /* Remember the location of any empty classes in FIELD.  */

4796       if (abi_version_at_least (2))

4797         record_subobject_offsets (TREE_TYPE (field),

4798                               byte_position(field),

4799                               empty_base_offsets,

4800                               /*vbases_p=*/ 1);

 

看到如前一节那样,数据成员由 layout_nonempty_base_or_field 来处理。对于像:“ char i: 16; ”这样的语句,它声明了比自己类型要宽的尺寸,编译器需要对其进行适当的提升。不过,编译器选择仅次于比要求尺寸大的类型的类型,而让余下的比特随后以填充比特的形式加上,以使得占用的空间尽可能小。因为在 place_field 中,现在这个位域默认地将被对齐到这个新类型的对齐边界。

 

layout_class_type (continue)

 

4802     /* If a bit-field does not immediately follow another bit-field,

4803       and yet it starts in the middle of a byte, we have failed to

4804       comply with the ABI.  */

4805      if (warn_abi

4806         && DECL_C_BIT_FIELD (field)

4807         && !last_field_was_bitfield

4808         && !integer_zerop (size_binop (TRUNC_MOD_EXPR,

4809                          DECL_FIELD_BIT_OFFSET (field),

4810                          bitsize_unit_node)))

4811        cp_warning_at ("offset of `%D' is not ABI-compliant and may change in a future version of GCC",

4812                      field);

4813

4814       /* G++ used to use DECL_FIELD_OFFSET as if it were the byte

4815        offset of the field.  */

4816      if (warn_abi

4817         && !tree_int_cst_equal (DECL_FIELD_OFFSET (field),

4818                             byte_position (field))

4819         && contains_empty_class_p (TREE_TYPE (field)))

4820        cp_warning_at ("`%D' contains empty classes which may cause base "

4821                     "classes to be placed at different locations in a "

4822                     "future version of GCC",

4823                     field);

4824

4825      /* If we needed additional padding after this field, add it

4826        now.  */

4827      if (padding)

4828      {

4829        tree padding_field;

4830  

4831         padding_field = build_decl (FIELD_DECL,

4832                                NULL_TREE,

4833                                char_type_node);

4834         DECL_BIT_FIELD (padding_field) = 1;

4835         DECL_SIZE (padding_field) = padding;

4836         DECL_CONTEXT (padding_field) = t;

4837         DECL_ARTIFICIAL (padding_field) = 1;

4838         layout_nonempty_base_or_field (rli, padding_field,

4839                                    NULL_TREE,

4840                                     empty_base_offsets);

4841       }

4842  

4843       last_field_was_bitfield = DECL_C_BIT_FIELD (field);

4844     }

 

上面的 padding 即是余下的比特,它被单独创建成一个 char 类型的位域,因此它将被对齐在字节边界,因而能接上正在处理位域的前半部分。

 

layout_class_type (continue)

 

4846     if (abi_version_at_least (2) && !integer_zerop (rli->bitpos))

4847     {

4848       /* Make sure that we are on a byte boundary so that the size of

4849         the class without virtual bases will always be a round number

4850         of bytes.  */

4851       rli->bitpos = round_up (rli->bitpos, BITS_PER_UNIT);

4852       normalize_rli (rli);

4853     }

4854  

4855     /* G++ 3.2 does not allow virtual bases to be overlaid with tail

4856       padding.  */

4857     if (!abi_version_at_least (2))

4858       include_empty_classes (rli);

4859  

4860     /* Delete all zero-width bit-fields from the list of fields. Now

4861       that the type is laid out they are no longer important.  */

4862     remove_zero_width_bit_fields (t);

 

在这一点上,所有的域,除了虚拟的非主要基类,都已经被布置了,首先我们把类目前的大小往上取整到字节边界,并移除空的位域(仅是位域,不包括空的基类)。

 

4070   static void

4071   remove_zero_width_bit_fields (tree t)                                                               in class.c

4072   {

4073     tree *fieldsp;

4074  

4075     fieldsp = &TYPE_FIELDS (t);

4076     while (*fieldsp)

4077     {

4078       if (TREE_CODE (*fieldsp) == FIELD_DECL

4079          && DECL_C_BIT_FIELD (*fieldsp)

4080          && DECL_INITIAL (*fieldsp))

4081         *fieldsp = TREE_CHAIN (*fieldsp);

4082       else

4083         fieldsp = &TREE_CHAIN (*fieldsp);

4084     }

4085   }

 

现在将要构建 CLASSTYPE_AS_BASE 节点,它不包括虚拟基类。并且在类中还将构建相应的 FIELD_DECL 。当该类被用作基类时,这个 CLASSTYPE_AS_BASE 就代表这个类(这也是为什么排除虚拟基类,因为它们为整个派生树所共享)。

注意这里使用 make_node 来构建节点,而不是 make_aggr_type ,因此断言 CLASS_TYPE_P 将失败,当这个基本部分用作基类并作为 FIELD_DECL 插入派生类时,在 check_field_decl 中的 abstract_virtuals_error 将被跳过。这样做的原因是经过斟酌的,考虑一个纯虚类,它可以作为基类,但不允许作为类的一个域。这两个形式都会产生 FIELD_DECL ,不过关联了不同的类型节点;对于后者使用的是普通的 RECORD_TYPE 节点,执行在 check_field_decl abstract_virtuals_error

 

layout_class_type (continue)

 

4864     /* Create the version of T used for virtual bases. We do not use

4865       make_aggr_type for this version; this is an artificial type. For

4866       a POD type, we just reuse T.  */

4867     if (CLASSTYPE_NON_POD_P (t) || CLASSTYPE_EMPTY_P (t))

4868     {

4869       base_t = make_node (TREE_CODE (t));

4870        

4871       /* Set the size and alignment for the new type. In G++ 3.2, all

4872         empty classes were considered to have size zero when used as

4873         base classes.  */

4874       if (!abi_version_at_least (2) && CLASSTYPE_EMPTY_P (t))

4875       {

4876         TYPE_SIZE (base_t) = bitsize_zero_node;

4877         TYPE_SIZE_UNIT (base_t) = size_zero_node;

4878         if (warn_abi && !integer_zerop (rli_size_unit_so_far (rli)))

4879           warning ("layout of classes derived from empty class `%T' "

4880                   "may change in a future version of GCC",

4881                   t);

4882       }

4883       else

4884       {

4885         tree eoc;

4886  

4887         /* If the ABI version is not at least two, and the last

4888           field was a bit-field, RLI may not be on a byte

4889           boundary. In particular, rli_size_unit_so_far might

4890           indicate the last complete byte, while rli_size_so_far

4891           indicates the total number of bits used. Therefore,

4892           rli_size_so_far, rather than rli_size_unit_so_far, is

4893           used to compute TYPE_SIZE_UNIT.  */

4894         eoc = end_of_class (t, /*include_virtuals_p=*/ 0);

4895         TYPE_SIZE_UNIT (base_t)

4896            = size_binop (MAX_EXPR,

4897                   convert (sizetype,

4898                          size_binop (CEIL_DIV_EXPR,

4899                                    rli_size_so_far (rli),

4900                                    bitsize_int (BITS_PER_UNIT))),

4901                     eoc);

4902         TYPE_SIZE (base_t)

4903            = size_binop (MAX_EXPR,

4904                       rli_size_so_far (rli),

4905                       size_binop (MULT_EXPR,

4906                                 convert (bitsizetype, eoc),

4907                                 bitsize_int (BITS_PER_UNIT)));

4908       }

4909       TYPE_ALIGN (base_t) = rli->record_align;

4910       TYPE_USER_ALIGN (base_t) = TYPE_USER_ALIGN (t);

4911  

4912       /* Copy the fields from T.  */

4913       next_field = &TYPE_FIELDS (base_t);

4914       for (field = TYPE_FIELDS (t); field; field = TREE_CHAIN (field))

4915         if (TREE_CODE (field) == FIELD_DECL)

4916         {

4917           *next_field = build_decl (FIELD_DECL,

4918                                DECL_NAME (field),

4919                                TREE_TYPE (field));

4920           DECL_CONTEXT (*next_field) = base_t;

4921           DECL_FIELD_OFFSET (*next_field) = DECL_FIELD_OFFSET (field);

4922           DECL_FIELD_BIT_OFFSET (*next_field)

4923              = DECL_FIELD_BIT_OFFSET (field);

4924           DECL_SIZE (*next_field) = DECL_SIZE (field);

4925           DECL_MODE (*next_field) = DECL_MODE (field);

4926           next_field = &TREE_CHAIN (*next_field);

4927         }

4928  

4929          /* Record the base version of the type.  */

4930         CLASSTYPE_AS_BASE (t) = base_t;

4931         TYPE_CONTEXT (base_t) = t;

4932       }

4933       else

4934         CLASSTYPE_AS_BASE (t) = t;

 

函数 end_of_class 返回在 t 中具有 最大偏移量的基类末尾字节的偏移量 。如果参数 include_virtuals_p 0 ,那么仅包含非虚拟基类。看到对于空的类, end_of_class 返回 size_zero_node

 

4503   static tree

4504   end_of_class (tree t, int in clude_virtuals_p)                                                in class.c

4505   {

4506     tree result = size_zero_node;

4507     tree binfo;

4508     tree offset;

4509     int i;

4510  

4511     for (i = 0; i < CLASSTYPE_N_BASECLASSES (t); ++i)

4512     {

4513       binfo = BINFO_BASETYPE (TYPE_BINFO (t), i);

4514  

4515       if (!include_virtuals_p

4516          && TREE_VIA_VIRTUAL (binfo)

4517          && BINFO_PRIMARY_BASE_OF (binfo) != TYPE_BINFO (t))

4518         continue ;

4519  

4520       offset = end_of_base (binfo);

4521       if (INT_CST_LT_UNSIGNED (result, offset))

4522         result = offset;

4523     }

4524  

4525     /* G++ 3.2 did not check indirect virtual bases.  */

4526     if (abi_version_at_least (2) && include_virtuals_p)

4527       for (binfo = CLASSTYPE_VBASECLASSES (t);

4528           binfo;

4529           binfo = TREE_CHAIN (binfo))

4530       {

4531         offset = end_of_base (TREE_VALUE (binfo));

4532         if (INT_CST_LT_UNSIGNED (result, offset))

4533           result = offset;

4534       }

4535  

4536     return result;

4537   }

 

而函数 end_of_base 返回基类 binfo 末尾字节的偏移量。

 

4483   static tree

4484   end_of_base (tree binfo)                                                                           in class.c

4485   {

4486     tree size;

4487  

4488     if (is_empty_class (BINFO_TYPE (binfo)))

4489       /* An empty class has zero CLASSTYPE_SIZE_UNIT, but we need to

4490         allocate some space for it. It cannot have virtual bases, so

4491         TYPE_SIZE_UNIT is fine.  */

4492       size = TYPE_SIZE_UNIT (BINFO_TYPE (binfo));

4493     else

4494       size = CLASSTYPE_SIZE_UNIT (BINFO_TYPE (binfo));

4495  

4496     return size_binop (PLUS_EXPR, BINFO_OFFSET (binfo), size);

4497   }

 

上面的 TYPE_SIZE_UNIT 返回以字节计算的类型的尺寸。即便空的类也将占据 1 个字节,这可随后在 layout_class_type 中看到。而 CLASSTYPE_SIZE_UNIT 请求 binfo CLASSTYPE_AS_BASE 对应的 TYPE_SIZE_UNIT ,它不包含虚拟基类。

 

layout_class_type (continue)

 

4936     /* Every empty class contains an empty class.  */

4937     if (CLASSTYPE_EMPTY_P (t))

4938       CLASSTYPE_CONTAINS_EMPTY_CLASS_P (t) = 1;

4939  

4940     /* Set the TYPE_DECL for this type to contain the right

4941       value for DECL_OFFSET, so that we can use it as part

4942       of a COMPONENT_REF for multiple inheritance.  */

4943     layout_decl (TYPE_MAIN_DECL (t), 0);

4944  

4945     /* Now fix up any virtual base class types that we left lying

4946       around. We must get these done before we try to lay out the

4947       virtual function table. As a side-effect, this will remove the

4948       base subobject fields.  */

4949     layout_virtual_bases (rli, empty_base_offsets);

4950  

4951     /* Make sure that empty classes are reflected in RLI at this

4952       point.  */

4953     include_empty_classes (rli);

4954  

4955     /* Make sure not to create any structures with zero size.  */

4956     if (integer_zerop (rli_size_unit_so_far (rli)) && CLASSTYPE_EMPTY_P (t))

4957       place_field (rli,

4958                 build_decl (FIELD_DECL, NULL_TREE, char_type_node));

4959  

4960     /* Let the back-end lay out the type.  */

4961     finish_record_layout (rli, /*free_p=*/ true);

4962  

4963     /* Warn about bases that can't be talked about due to ambiguity.  */

4964     warn_about_ambiguous_bases (t);

4965  

4966     /* Clean up.  */

4967     splay_tree_delete (empty_base_offsets);

4968   }

 

记住我们总是布置直接或间接基类的 CLASSTYPE_AS_BASE ,它们不包含虚拟基类。现在是时候布置直接或间接的虚拟基类,除非它被用作主要基类。

 

4408   static void

4409   layout_virtual_bases (record_layout_info rli, splay_tree offsets)                   in class.c

4410   {

4411     tree vbase;

4412     tree t = rli->t;

4413     bool first_vbase = true;

4414     tree *next_field;

4415  

4416     if (CLASSTYPE_N_BASECLASSES (t) == 0)

4417       return ;

4418  

4419     if (!abi_version_at_least(2))

4420     {

4421        /* In G++ 3.2, we incorrectly rounded the size before laying out

4422         the virtual bases.  */

4423       finish_record_layout (rli, /*free_p=*/ false);

4424   #ifdef STRUCTURE_SIZE_BOUNDARY

4425       /* Packed structures don't need to have minimum size.  */

4426       if (! TYPE_PACKED (t))

4427         TYPE_ALIGN (t) = MAX (TYPE_ALIGN (t), (unsigned) STRUCTURE_SIZE_BOUNDARY);

4428   #endif

4429       rli->offset = TYPE_SIZE_UNIT (t);

4430       rli->bitpos = bitsize_zero_node;

4431       rli->record_align = TYPE_ALIGN (t);

4432     }

4433  

4434     /* Find the last field. The artificial fields created for virtual

4435       bases will go after the last extant field to date.  */

4436     next_field = &TYPE_FIELDS (t);

4437     while (*next_field)

4438       next_field = &TREE_CHAIN (*next_field);

4439  

4440     /* Go through the virtual bases, allocating space for each virtual

4441       base that is not already a primary base class. These are

4442       allocated in inheritance graph order.  */

4443     for (vbase = TYPE_BINFO (t); vbase; vbase = TREE_CHAIN (vbase))

4444     {

4445       if (!TREE_VIA_VIRTUAL (vbase))

4446         continue ;

4447  

4448       if (!BINFO_PRIMARY_P (vbase))

4449       {

4450         tree basetype = TREE_TYPE (vbase);

4451  

4452          /* This virtual base is not a primary base of any class in the

4453           hierarchy, so we have to add space for it.  */

4454         next_field = build_base_field (rli, vbase,

4455                                  offsets, next_field);

4456  

4457          /* If the first virtual base might have been placed at a

4458           lower address, had we started from CLASSTYPE_SIZE, rather

4459           than TYPE_SIZE, issue a warning. There can be both false

4460            positives and false negatives from this warning in rare

4461           cases; to deal with all the possibilities would probably

4462           require performing both layout algorithms and comparing

4463           the results which is not particularly tractable.  */

4464         if (warn_abi

4465            && first_vbase

4466            && (tree_int_cst_lt

4467                  (size_binop (CEIL_DIV_EXPR,

4468                            round_up (CLASSTYPE_SIZE (t),

4469                                      CLASSTYPE_ALIGN (basetype)),

4470                            bitsize_unit_node),

4471                   BINFO_OFFSET (vbase))))

4472           warning ("offset of virtual base `%T' is not ABI-compliant and may change in a future version of GCC",

4473                   basetype);

4474  

4475         first_vbase = false;

4476       }

4477     }

4478   }

 

因为我们准备布置直接或间接虚拟基类,我们需要遍历整个派生树来访问这些虚拟基类。同样的,这样的记录也需要 build_base_field 来构建 FIELD_DECL 。虚拟基类的布置与非虚拟基类的布置没有什么两样。注意到虚拟基类的 FIELD_DECL 同样不包含它自身的虚拟基类。

build_base_field 中,我们看到空的类的布局仅反映在类的 BINFO_OFFSET 上,并且通过 propagate_binfo_offsets 传播到受影响的基类。但是 rli ——追踪布局的数据,对此一无所知。现在需要做的事情,就是更新 rli 中的尺寸信息,使得布局足够大,能包含这些空类。

 

4591   static void

4592   include_empty_classes (record_layout_info rli)                                           in class.c

4593   {

4594     tree eoc;

4595     tree rli_size;

4596  

4597     /* It might be the case that we grew the class to allocate a

4598       zero-sized base class. That won't be reflected in RLI, yet,

4599       because we are willing to overlay multiple bases at the same

4600       offset. However, now we need to make sure that RLI is big enough

4601       to reflect the entire class.  */

4602     eoc = end_of_class (rli->t,

4603                       CLASSTYPE_AS_BASE (rli->t) != NULL_TREE);

4604     rli_size = rli_size_unit_so_far (rli);

4605     if (TREE_CODE (rli_size) == INTEGER_CST

4606         && INT_CST_LT_UNSIGNED (rli_size, eoc))

4607     {

4608       if (!abi_version_at_least (2))

4609         /* In version 1 of the ABI, the size of a class that ends with

4610            a bitfield was not rounded up to a whole multiple of a

4611            byte. Because rli_size_unit_so_far returns only the number

4612            of fully allocated bytes, any extra bits were not included

4613            i n the size.  */

4614         rli->bitpos = round_down (rli->bitpos, BITS_PER_UNIT);

4615       else

4616         /* The size should have been rounded to a whole byte.  */

4617         my_friendly_assert (tree_int_cst_equal (rli->bitpos,

4618                                         round_down (rli->bitpos,

4619                                                     BITS_PER_UNIT)),

4620                          20030903);

4621       rli->bitpos

4622         = size_binop (PLUS_EXPR,

4623                      rli->bitpos,

4624                      size_binop (MULT_EXPR,

4625                                convert (bitsizetype,

4626                                        size_binop (MINUS_EXPR,

4627                                                 eoc, rli_size)),

4628                               bitsize_int (BITS_PER_UNIT)));

4629       normalize_rli (rli);

4630     }

4631   }

 

接着,我们可以看到如果当前类是空的,需要插入一个匿名的 char 类型的域,使得它不是 0 大小的。然后 finish_record_layout rli 的帮助下填充类型节点的相关的域。

 

4549   static void

4550   warn_about_ambiguous_bases (tree t)                                                               in class.c

4551   {

4552     int i;

4553     tree vbases;

4554     tree basetype;

4555  

4556     /* Check direct bases.  */

4557     for (i = 0; i < CLASSTYPE_N_BASECLASSES (t); ++i)

4558     {

4559       basetype = TYPE_BINFO_BASETYPE (t, i);

4560  

4561       if (!lookup_base (t, basetype, ba_ignore | ba_quiet, NULL))

4562         warning ("direct base `%T' inaccessible in `%T' due to ambiguity",

4563                 basetype, t);

4564     }

4565  

4566     /* Check for ambiguous virtual bases.  */

4567     if (extra_warnings )

4568       for (vbases = CLASSTYPE_VBASECLASSES (t);

4569            vbases;

4570             vbases = TREE_CHAIN (vbases))

4571       {

4572         basetype = BINFO_TYPE (TREE_VALUE (vbases));

4573       

4574         if (!lookup_base (t, basetype, ba_ignore | ba_quiet, NULL))

4575            warning ("virtual base `%T' inaccessible in `%T' due to ambiguity",

4576                    basetype, t);

4577       }

4578   }

 

跟着, warn_about_ambiguous_bases 对有二义性的基类给出警告信息。例如:

struct S {};

struct T : public S {};

struct U : public S, public T {};

S U 中就是具有二义性的。

最后,因为布局已完成,可以删除伸展树了。

layout_class_type 退出,我们回到 finish_struct_1 并确定类的基本部分的机器模式,如果它不是类本身的话。

 

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值