@@ -117,6 +117,12 @@ TEnum *EnsureValidEnum(std::string_view enumName)
117117 return e;
118118}
119119
120+ void EnsureValidAlignment (std::size_t align)
121+ {
122+ if (align == 0 || align > ROOT ::RFieldBase::kMaxAlignment || !ROOT::Internal::IsPowerOfTwo (align))
123+ throw ROOT::RException (R__FAIL (std::string (" invalid alignment: " ) + std::to_string (align)));
124+ }
125+
120126// / Create a comma-separated list of type names from the given fields. Uses either the real type names or the
121127// / type aliases (if there are any, otherwise the actual type name). Used to construct template argument lists
122128// / for templated types such as std::pair<...>, std::tuple<...>, std::variant<...>.
@@ -187,8 +193,7 @@ std::string BuildMapTypeName(ROOT::RMapField::EMapType mapType, const ROOT::RFie
187193ROOT ::RClassField::RClassField(std::string_view fieldName, const RClassField &source)
188194 : ROOT ::RFieldBase(fieldName, source.GetTypeName(), ROOT ::ENTupleStructure::kRecord , false /* isSimple */ ),
189195 fClass (source.fClass ),
190- fSubfieldsInfo(source.fSubfieldsInfo ),
191- fMaxAlignment(source.fMaxAlignment )
196+ fSubfieldsInfo(source.fSubfieldsInfo )
192197{
193198 for (const auto &f : source.GetConstSubfields ()) {
194199 RFieldBase::Attach (f->Clone (f->GetFieldName ()));
@@ -281,7 +286,6 @@ ROOT::RClassField::~RClassField()
281286
282287void ROOT::RClassField::Attach (std::unique_ptr<RFieldBase> child, RSubfieldInfo info)
283288{
284- fMaxAlignment = std::max (fMaxAlignment , child->GetAlignment ());
285289 fSubfieldsInfo .push_back (info);
286290 RFieldBase::Attach (std::move (child));
287291}
@@ -623,11 +627,18 @@ std::vector<ROOT::RFieldBase::RValue> ROOT::RClassField::SplitValue(const RValue
623627 return result;
624628}
625629
626- size_t ROOT::RClassField::GetValueSize () const
630+ std:: size_t ROOT::RClassField::GetValueSize () const
627631{
628632 return fClass ->GetClassSize ();
629633}
630634
635+ std::size_t ROOT::RClassField::GetAlignment () const
636+ {
637+ const auto align = fClass ->GetClassAlignment ();
638+ EnsureValidAlignment (align);
639+ return align;
640+ }
641+
631642std::uint32_t ROOT::RClassField::GetTypeVersion () const
632643{
633644 return fClass ->GetClassVersion ();
@@ -658,8 +669,7 @@ ROOT::Experimental::RSoAField::RSoAField(std::string_view fieldName, const RSoAF
658669 : ROOT ::RFieldBase(fieldName, source.GetTypeName(), ROOT ::ENTupleStructure::kCollection , false /* isSimple */ ),
659670 fSoAClass (source.fSoAClass ),
660671 fSoAMemberOffsets(source.fSoAMemberOffsets ),
661- fRecordMemberIndexes(source.fRecordMemberIndexes ),
662- fMaxAlignment(source.fMaxAlignment )
672+ fRecordMemberIndexes(source.fRecordMemberIndexes )
663673{
664674 fTraits = source.GetTraits ();
665675 Attach (source.fSubfields [0 ]->Clone (source.fSubfields [0 ]->GetFieldName ()));
@@ -750,8 +760,6 @@ ROOT::Experimental::RSoAField::RSoAField(std::string_view fieldName, TClass *clS
750760 leftType + " vs. " + rightType + " )" ));
751761 }
752762
753- fMaxAlignment = std::max (fMaxAlignment , vecField->GetAlignment ());
754-
755763 fSoAMemberOffsets .emplace_back (dataMember->GetOffset ());
756764 fRecordMemberIndexes .emplace_back (itr->second );
757765 }
@@ -856,11 +864,18 @@ std::vector<ROOT::RFieldBase::RValue> ROOT::Experimental::RSoAField::SplitValue(
856864 return std::vector<RValue>();
857865}
858866
859- size_t ROOT::Experimental::RSoAField::GetValueSize () const
867+ std:: size_t ROOT::Experimental::RSoAField::GetValueSize () const
860868{
861869 return fSoAClass ->GetClassSize ();
862870}
863871
872+ std::size_t ROOT::Experimental::RSoAField::GetAlignment () const
873+ {
874+ const auto align = fSoAClass ->GetClassAlignment ();
875+ EnsureValidAlignment (align);
876+ return align;
877+ }
878+
864879const std::type_info *ROOT ::Experimental::RSoAField::GetPolymorphicTypeInfo() const
865880{
866881 // TODO(jblomer): factor out
@@ -1181,6 +1196,18 @@ std::vector<ROOT::RFieldBase::RValue> ROOT::RProxiedCollectionField::SplitValue(
11811196 return result;
11821197}
11831198
1199+ std::size_t ROOT::RProxiedCollectionField::GetValueSize () const
1200+ {
1201+ return fProxy ->Sizeof ();
1202+ }
1203+
1204+ std::size_t ROOT::RProxiedCollectionField::GetAlignment () const
1205+ {
1206+ const auto align = fProxy ->GetCollectionClass ()->GetClassAlignment ();
1207+ EnsureValidAlignment (align);
1208+ return align;
1209+ }
1210+
11841211void ROOT::RProxiedCollectionField::AcceptVisitor (ROOT ::Detail::RFieldVisitor &visitor) const
11851212{
11861213 visitor.VisitProxiedCollectionField (*this );
@@ -1388,7 +1415,9 @@ ROOT::RExtraTypeInfoDescriptor ROOT::RStreamerField::GetExtraTypeInfo() const
13881415
13891416std::size_t ROOT::RStreamerField::GetAlignment () const
13901417{
1391- return std::min (alignof (std::max_align_t ), GetValueSize ()); // TODO(jblomer): fix me
1418+ const auto align = fClass ->GetClassAlignment ();
1419+ EnsureValidAlignment (align);
1420+ return align;
13921421}
13931422
13941423std::size_t ROOT::RStreamerField::GetValueSize () const
0 commit comments