@@ -892,11 +892,17 @@ def collect_in_array(self, rspec, rmod):
892892        for  rtag , _ , _  in  registers [1 :]:
893893            self .ptag .find ("registers" ).remove (rtag )
894894        rtag  =  registers [0 ][0 ]
895+         nametag  =  rtag .find ("name" )
895896        if  "name"  in  rmod :
896897            name  =  rmod ["name" ]
897898        else :
898899            name  =  rspec [:li ] +  "%s"  +  rspec [len (rspec ) -  ri  :]
899-         rtag .find ("name" ).text  =  name 
900+         if  dimIndex [0 ] ==  "0" :
901+             desc  =  rtag .find ("description" )
902+             desc .text  =  desc .text .replace (
903+                 nametag .text [li  : len (nametag .text ) -  ri ], "%s" 
904+             )
905+         nametag .text  =  name 
900906        self .process_register (name , rmod )
901907        ET .SubElement (rtag , "dim" ).text  =  str (dim )
902908        ET .SubElement (rtag , "dimIncrement" ).text  =  hex (dimIncrement )
@@ -1021,6 +1027,10 @@ def process_register(self, rspec, register, update_fields=True):
10211027                    if  not  fspec .startswith ("_" ):
10221028                        field  =  register [fspec ]
10231029                        r .process_field (pname , fspec , field )
1030+             # Handle field arrays 
1031+             for  fspec  in  register .get ("_array" , {}):
1032+                 fmod  =  register ["_array" ][fspec ]
1033+                 r .collect_fields_in_array (fspec , fmod )
10241034        if  rcount  ==  0 :
10251035            raise  MissingRegisterError ("Could not find {}:{}" .format (pname , rspec ))
10261036
@@ -1134,6 +1144,56 @@ def merge_fields(self, fspec):
11341144        ET .SubElement (fnew , "bitOffset" ).text  =  str (bitoffset )
11351145        ET .SubElement (fnew , "bitWidth" ).text  =  str (bitwidth )
11361146
1147+     def  collect_fields_in_array (self , fspec , fmod ):
1148+         """Collect same fields in peripheral into register array.""" 
1149+         fields  =  []
1150+         li , ri  =  spec_ind (fspec )
1151+         for  ftag  in  list (self .iter_fields (fspec )):
1152+             fname  =  ftag .findtext ("name" )
1153+             fields .append (
1154+                 [ftag , fname [li  : len (fname ) -  ri ], int (ftag .findtext ("bitOffset" ), 0 )]
1155+             )
1156+         dim  =  len (fields )
1157+         if  dim  ==  0 :
1158+             raise  SvdPatchError (
1159+                 "{}: fields {} not found" .format (self .rtag .findtext ("name" ), fspec )
1160+             )
1161+         fields  =  sorted (fields , key = lambda  f : f [2 ])
1162+ 
1163+         if  fmod .get ("_start_from_zero" , "" ):
1164+             dimIndex  =  "," .join ([str (i ) for  i  in  range (dim )])
1165+         else :
1166+             if  dim  ==  1 :
1167+                 dimIndex  =  "{0}-{0}" .format (fields [0 ][1 ])
1168+             else :
1169+                 dimIndex  =  "," .join (f [1 ] for  f  in  fields )
1170+         offsets  =  [f [2 ] for  f  in  fields ]
1171+         dimIncrement  =  0 
1172+         if  dim  >  1 :
1173+             dimIncrement  =  offsets [1 ] -  offsets [0 ]
1174+ 
1175+         if  not  check_offsets (offsets , dimIncrement ):
1176+             raise  SvdPatchError (
1177+                 "{}: fields cannot be collected into {} array" .format (
1178+                     self .rtag .findtext ("name" ), fspec 
1179+                 )
1180+             )
1181+         for  ftag , _ , _  in  fields [1 :]:
1182+             self .rtag .find ("fields" ).remove (ftag )
1183+         ftag  =  fields [0 ][0 ]
1184+         nametag  =  ftag .find ("name" )
1185+         if  "name"  in  fmod :
1186+             name  =  fmod ["name" ]
1187+         else :
1188+             name  =  fspec [:li ] +  "%s"  +  fspec [len (fspec ) -  ri  :]
1189+         desc  =  ftag .find ("description" )
1190+         desc .text  =  desc .text .replace (nametag .text [li  : len (nametag .text ) -  ri ], "%s" )
1191+         nametag .text  =  name 
1192+         # self.process_field(name, fmod) 
1193+         ET .SubElement (ftag , "dim" ).text  =  str (dim )
1194+         ET .SubElement (ftag , "dimIndex" ).text  =  dimIndex 
1195+         ET .SubElement (ftag , "dimIncrement" ).text  =  hex (dimIncrement )
1196+ 
11371197    def  split_fields (self , fspec ):
11381198        """split all fspec in rtag.""" 
11391199        fields  =  list (self .iter_fields (fspec ))
@@ -1179,56 +1239,60 @@ def process_field_enum(self, pname, fspec, field, usage="read-write"):
11791239
11801240        derived , enum , enum_name , enum_usage  =  None , None , None , None 
11811241        for  ftag  in  self .iter_fields (fspec ):
1182-             name  =  ftag .find ("name" ).text 
1183- 
1184-             if  enum  is  None :
1185-                 enum  =  make_enumerated_values (name , field , usage = usage )
1186-                 enum_name  =  enum .find ("name" ).text 
1187-                 enum_usage  =  enum .find ("usage" ).text 
1188- 
1189-             for  ev  in  ftag .iter ("enumeratedValues" ):
1190-                 if  len (ev ) >  0 :
1191-                     ev_usage_tag  =  ev .find ("usage" )
1192-                     ev_usage  =  (
1193-                         ev_usage_tag .text  if  ev_usage_tag  is  not None  else  "read-write" 
1194-                     )
1195-                 else :
1196-                     # This is a derived enumeratedValues => Try to find the 
1197-                     # original definition to extract its <usage> 
1198-                     derived_name  =  ev .attrib ["derivedFrom" ]
1199-                     derived_enums  =  self .rtag .findall (
1200-                         "./fields/field/enumeratedValues/[name='{}']" .format (
1201-                             derived_name 
1202-                         )
1203-                     )
1242+             if  "_derivedFrom"  in  field :
1243+                 derived  =  field ["_derivedFrom" ]
1244+             else :
1245+                 name  =  ftag .find ("name" ).text 
12041246
1205-                     if  derived_enums  ==  []:
1206-                         raise  SvdPatchError (
1207-                             "{}: field {} derives enumeratedValues {} which could not be found" .format (
1208-                                 pname , name , derived_name 
1209-                             )
1247+             if  derived  is  None :
1248+                 if  enum  is  None :
1249+                     enum  =  make_enumerated_values (name , field , usage = usage )
1250+                     enum_name  =  enum .find ("name" ).text 
1251+                     enum_usage  =  enum .find ("usage" ).text 
1252+ 
1253+                 for  ev  in  ftag .iter ("enumeratedValues" ):
1254+                     if  len (ev ) >  0 :
1255+                         ev_usage_tag  =  ev .find ("usage" )
1256+                         ev_usage  =  (
1257+                             ev_usage_tag .text 
1258+                             if  ev_usage_tag  is  not None 
1259+                             else  "read-write" 
12101260                        )
1211-                     elif  len (derived_enums ) !=  1 :
1212-                         raise  SvdPatchError (
1213-                             "{}: field {} derives enumeratedValues {} which was found multiple times" .format (
1214-                                 pname , name , derived_name 
1261+                     else :
1262+                         # This is a derived enumeratedValues => Try to find the 
1263+                         # original definition to extract its <usage> 
1264+                         derived_name  =  ev .attrib ["derivedFrom" ]
1265+                         derived_enums  =  self .rtag .findall (
1266+                             "./fields/field/enumeratedValues/[name='{}']" .format (
1267+                                 derived_name 
12151268                            )
12161269                        )
12171270
1218-                     ev_usage  =  derived_enums [0 ].find ("usage" ).text 
1219- 
1220-                 if  ev_usage  ==  enum_usage  or  ev_usage  ==  "read-write" :
1221-                     if  replace_if_exists :
1222-                         ftag .remove (ev )
1223-                     else :
1224-                         print (pname , fspec , field )
1225-                         raise  SvdPatchError (
1226-                             "{}: field {} already has enumeratedValues for {}" .format (
1227-                                 pname , name , ev_usage 
1271+                         if  derived_enums  ==  []:
1272+                             raise  SvdPatchError (
1273+                                 "{}: field {} derives enumeratedValues {} which could not be found" .format (
1274+                                     pname , name , derived_name 
1275+                                 )
1276+                             )
1277+                         elif  len (derived_enums ) !=  1 :
1278+                             raise  SvdPatchError (
1279+                                 "{}: field {} derives enumeratedValues {} which was found multiple times" .format (
1280+                                     pname , name , derived_name 
1281+                                 )
12281282                            )
1229-                         )
12301283
1231-             if  derived  is  None :
1284+                         ev_usage  =  derived_enums [0 ].find ("usage" ).text 
1285+ 
1286+                     if  ev_usage  ==  enum_usage  or  ev_usage  ==  "read-write" :
1287+                         if  replace_if_exists :
1288+                             ftag .remove (ev )
1289+                         else :
1290+                             print (pname , fspec , field )
1291+                             raise  SvdPatchError (
1292+                                 "{}: field {} already has enumeratedValues for {}" .format (
1293+                                     pname , name , ev_usage 
1294+                                 )
1295+                             )
12321296                ftag .append (enum )
12331297                derived  =  enum_name 
12341298            else :
0 commit comments