@@ -800,11 +800,37 @@ llvm::Error ClangDocBitcodeReader::readBlock(unsigned ID, T I) {
800800  }
801801}
802802
803- //  TODO: Create a helper that can receive a function to reduce repetition for
804- //  most blocks.
803+ template  <typename  InfoType, typename  T, typename  Callback>
804+ llvm::Error ClangDocBitcodeReader::handleSubBlock (unsigned  ID, T Parent,
805+                                                   Callback Function) {
806+   InfoType Info;
807+   if  (auto  Err = readBlock (ID, &Info))
808+     return  Err;
809+   Function (Parent, std::move (Info));
810+   return  llvm::Error::success ();
811+ }
812+ 
813+ template  <typename  InfoType, typename  T, typename  Callback>
814+ llvm::Error ClangDocBitcodeReader::handleTypeSubBlock (unsigned  ID, T Parent,
815+                                                       Callback Function) {
816+   InfoType Info;
817+   if  (auto  Err = readBlock (ID, &Info))
818+     return  Err;
819+   if  (auto  Err = Function (Parent, std::move (Info)))
820+     return  Err;
821+   return  llvm::Error::success ();
822+ }
823+ 
805824template  <typename  T>
806825llvm::Error ClangDocBitcodeReader::readSubBlock (unsigned  ID, T I) {
807826  llvm::TimeTraceScope (" Reducing infos"  , " readSubBlock"  );
827+ 
828+   static  auto  CreateAddFunc = [](auto  AddFunc) {
829+     return  [AddFunc](auto  Parent, auto  Child) {
830+       return  AddFunc (Parent, std::move (Child));
831+     };
832+   };
833+ 
808834  switch  (ID) {
809835  //  Blocks can only have certain types of sub blocks.
810836  case  BI_COMMENT_BLOCK_ID: {
@@ -816,28 +842,16 @@ llvm::Error ClangDocBitcodeReader::readSubBlock(unsigned ID, T I) {
816842    return  llvm::Error::success ();
817843  }
818844  case  BI_TYPE_BLOCK_ID: {
819-     TypeInfo TI;
820-     if  (auto  Err = readBlock (ID, &TI))
821-       return  Err;
822-     if  (auto  Err = addTypeInfo (I, std::move (TI)))
823-       return  Err;
824-     return  llvm::Error::success ();
845+     return  handleTypeSubBlock<TypeInfo>(
846+         ID, I, CreateAddFunc (addTypeInfo<T, TypeInfo>));
825847  }
826848  case  BI_FIELD_TYPE_BLOCK_ID: {
827-     FieldTypeInfo TI;
828-     if  (auto  Err = readBlock (ID, &TI))
829-       return  Err;
830-     if  (auto  Err = addTypeInfo (I, std::move (TI)))
831-       return  Err;
832-     return  llvm::Error::success ();
849+     return  handleTypeSubBlock<FieldTypeInfo>(
850+         ID, I, CreateAddFunc (addTypeInfo<T, FieldTypeInfo>));
833851  }
834852  case  BI_MEMBER_TYPE_BLOCK_ID: {
835-     MemberTypeInfo TI;
836-     if  (auto  Err = readBlock (ID, &TI))
837-       return  Err;
838-     if  (auto  Err = addTypeInfo (I, std::move (TI)))
839-       return  Err;
840-     return  llvm::Error::success ();
853+     return  handleTypeSubBlock<MemberTypeInfo>(
854+         ID, I, CreateAddFunc (addTypeInfo<T, MemberTypeInfo>));
841855  }
842856  case  BI_REFERENCE_BLOCK_ID: {
843857    Reference R;
@@ -848,81 +862,46 @@ llvm::Error ClangDocBitcodeReader::readSubBlock(unsigned ID, T I) {
848862    return  llvm::Error::success ();
849863  }
850864  case  BI_FUNCTION_BLOCK_ID: {
851-     FunctionInfo F;
852-     if  (auto  Err = readBlock (ID, &F))
853-       return  Err;
854-     addChild (I, std::move (F));
855-     return  llvm::Error::success ();
865+     return  handleSubBlock<FunctionInfo>(
866+         ID, I, CreateAddFunc (addChild<T, FunctionInfo>));
856867  }
857868  case  BI_BASE_RECORD_BLOCK_ID: {
858-     BaseRecordInfo BR;
859-     if  (auto  Err = readBlock (ID, &BR))
860-       return  Err;
861-     addChild (I, std::move (BR));
862-     return  llvm::Error::success ();
869+     return  handleSubBlock<BaseRecordInfo>(
870+         ID, I, CreateAddFunc (addChild<T, BaseRecordInfo>));
863871  }
864872  case  BI_ENUM_BLOCK_ID: {
865-     EnumInfo E;
866-     if  (auto  Err = readBlock (ID, &E))
867-       return  Err;
868-     addChild (I, std::move (E));
869-     return  llvm::Error::success ();
873+     return  handleSubBlock<EnumInfo>(ID, I,
874+                                     CreateAddFunc (addChild<T, EnumInfo>));
870875  }
871876  case  BI_ENUM_VALUE_BLOCK_ID: {
872-     EnumValueInfo EV;
873-     if  (auto  Err = readBlock (ID, &EV))
874-       return  Err;
875-     addChild (I, std::move (EV));
876-     return  llvm::Error::success ();
877+     return  handleSubBlock<EnumValueInfo>(
878+         ID, I, CreateAddFunc (addChild<T, EnumValueInfo>));
877879  }
878880  case  BI_TEMPLATE_BLOCK_ID: {
879-     TemplateInfo TI;
880-     if  (auto  Err = readBlock (ID, &TI))
881-       return  Err;
882-     addTemplate (I, std::move (TI));
883-     return  llvm::Error::success ();
881+     return  handleSubBlock<TemplateInfo>(ID, I, CreateAddFunc (addTemplate<T>));
884882  }
885883  case  BI_TEMPLATE_SPECIALIZATION_BLOCK_ID: {
886-     TemplateSpecializationInfo TSI;
887-     if  (auto  Err = readBlock (ID, &TSI))
888-       return  Err;
889-     addTemplateSpecialization (I, std::move (TSI));
890-     return  llvm::Error::success ();
884+     return  handleSubBlock<TemplateSpecializationInfo>(
885+         ID, I, CreateAddFunc (addTemplateSpecialization<T>));
891886  }
892887  case  BI_TEMPLATE_PARAM_BLOCK_ID: {
893-     TemplateParamInfo TPI;
894-     if  (auto  Err = readBlock (ID, &TPI))
895-       return  Err;
896-     addTemplateParam (I, std::move (TPI));
897-     return  llvm::Error::success ();
888+     return  handleSubBlock<TemplateParamInfo>(
889+         ID, I, CreateAddFunc (addTemplateParam<T>));
898890  }
899891  case  BI_TYPEDEF_BLOCK_ID: {
900-     TypedefInfo TI;
901-     if  (auto  Err = readBlock (ID, &TI))
902-       return  Err;
903-     addChild (I, std::move (TI));
904-     return  llvm::Error::success ();
892+     return  handleSubBlock<TypedefInfo>(ID, I,
893+                                        CreateAddFunc (addChild<T, TypedefInfo>));
905894  }
906895  case  BI_CONSTRAINT_BLOCK_ID: {
907-     ConstraintInfo CI;
908-     if  (auto  Err = readBlock (ID, &CI))
909-       return  Err;
910-     addConstraint (I, std::move (CI));
911-     return  llvm::Error::success ();
896+     return  handleSubBlock<ConstraintInfo>(ID, I,
897+                                           CreateAddFunc (addConstraint<T>));
912898  }
913899  case  BI_CONCEPT_BLOCK_ID: {
914-     ConceptInfo CI;
915-     if  (auto  Err = readBlock (ID, &CI))
916-       return  Err;
917-     addChild (I, std::move (CI));
918-     return  llvm::Error::success ();
900+     return  handleSubBlock<ConceptInfo>(ID, I,
901+                                        CreateAddFunc (addChild<T, ConceptInfo>));
919902  }
920903  case  BI_VAR_BLOCK_ID: {
921-     VarInfo VI;
922-     if  (auto  Err = readBlock (ID, &VI))
923-       return  Err;
924-     addChild (I, std::move (VI));
925-     return  llvm::Error::success ();
904+     return  handleSubBlock<VarInfo>(ID, I, CreateAddFunc (addChild<T, VarInfo>));
926905  }
927906  default :
928907    return  llvm::createStringError (llvm::inconvertibleErrorCode (),
0 commit comments