Changeset 8:b9554b04aa0f in rrlib_rtti_conversion


Ignore:
Timestamp:
12.09.2017 10:07:21 (21 months ago)
Author:
Max Reichardt <mreichardt@…>
Branch:
17.03
Phase:
public
Message:

Adds conversion operations for tuples - and unifies 'for-each' and 'get-element' conversion operations for vectors and arrays

Files:
4 edited

Legend:

Unmodified
Added
Removed
  • defined_conversions.cpp

    r7 r8  
    342342      return tConversionOption(source_type, destination_type, &FirstConversionFunction, &GetDestinationReference); 
    343343    } 
     344    unsigned int index = parameter ? parameter->GetData<unsigned int>() : 0; 
     345    if (source_type.IsArray() && source_type.GetElementType() == destination_type && index < source_type.GetArraySize()) 
     346    { 
     347      return tConversionOption(source_type, destination_type, index * source_type.GetElementType().GetSize()); 
     348    } 
    344349    return tConversionOption(); 
    345350  } 
     
    373378{ 
    374379public: 
    375   tForEach() : tRegisteredConversionOperation(util::tManagedConstCharPointer("For Each", false), tSupportedTypeFilter::GENERIC_VECTOR_CAST, tSupportedTypeFilter::GENERIC_VECTOR_CAST) 
    376   {} 
    377  
    378   virtual tConversionOption GetConversionOption(const tType& source_type, const tType& destination_type, const tGenericObject* parameter) const override 
    379   { 
    380     if ((source_type.GetTypeTraits() & trait_flags::cIS_LIST_TYPE) && destination_type) 
     380  tForEach() : tRegisteredConversionOperation(util::tManagedConstCharPointer("For Each", false), tSupportedTypeFilter::FOR_EACH, tSupportedTypeFilter::FOR_EACH) 
     381  {} 
     382 
     383  virtual tConversionOption GetConversionOption(const tType& source_type, const tType& destination_type, const tGenericObject* parameter) const override 
     384  { 
     385    if ((source_type.IsListType() || source_type.IsArray()) && destination_type) 
    381386    { 
    382387      return tConversionOption(source_type, destination_type, false, &FirstConversionFunction, &FinalConversionFunction); 
     
    387392  static void FirstConversionFunction(const tTypedConstPointer& source_object, const tTypedPointer& destination_object, const tCurrentConversionOperation& operation) 
    388393  { 
    389     size_t size = source_object.GetVectorSize(); 
     394    const tType& source_type = source_object.GetType(); 
     395    const tType& destination_type = source_object.GetType(); 
     396    size_t size = source_type.IsArray() ? source_type.GetArraySize() : source_object.GetVectorSize(); 
     397    if (source_type.IsListType() && destination_type.IsListType()) 
     398    { 
     399      destination_object.ResizeVector(size); 
     400      if (size) 
     401      { 
     402        tTypedConstPointer source_first = source_object.GetVectorElement(0); 
     403        tTypedPointer destination_first = destination_object.GetVectorElement(0); 
     404        operation.Continue(source_first, destination_object); 
     405        if (size > 1) 
     406        { 
     407          tTypedConstPointer source_next = source_object.GetVectorElement(1); 
     408          tTypedPointer destination_next = destination_object.GetVectorElement(1); 
     409          operation.Continue(source_next, destination_next); 
     410          size_t offset_source = static_cast<const char*>(source_next.GetRawDataPointer()) - static_cast<const char*>(source_first.GetRawDataPointer()); 
     411          size_t offset_destination = static_cast<const char*>(destination_next.GetRawDataPointer()) - static_cast<const char*>(destination_first.GetRawDataPointer()); 
     412          for (size_t i = 2; i < size; i++) 
     413          { 
     414            source_next = tTypedConstPointer(static_cast<const char*>(source_next.GetRawDataPointer()) + offset_source, source_type); 
     415            destination_next = tTypedPointer(static_cast<char*>(destination_next.GetRawDataPointer()) + offset_destination, destination_type); 
     416            operation.Continue(source_next, destination_next); 
     417          } 
     418        } 
     419      } 
     420    } 
     421    else if (source_type.IsArray() && destination_type.IsArray()) 
     422    { 
     423      if (size != destination_type.GetArraySize()) 
     424      { 
     425        throw std::runtime_error("Arrays must have the same size"); 
     426      } 
     427 
     428      size_t source_element_offset = source_type.GetSize() / size; 
     429      size_t destination_element_offset = destination_type.GetSize() / size; 
     430      for (size_t i = 0; i < size; i++) 
     431      { 
     432        tTypedConstPointer source(static_cast<const char*>(source_object.GetRawDataPointer()) + i * source_element_offset, source_type); 
     433        tTypedPointer destination(static_cast<char*>(destination_object.GetRawDataPointer()) + i * destination_element_offset, destination_type); 
     434        operation.Continue(source, destination); 
     435      } 
     436    } 
     437    else if (source_type.IsArray() && destination_type.IsListType()) 
     438    { 
     439      size_t size = source_type.GetArraySize(); 
     440      destination_object.ResizeVector(size); 
     441      if (size) 
     442      { 
     443        size_t source_element_offset = source_type.GetSize() / size; 
     444        tTypedConstPointer source(static_cast<const char*>(source_object.GetRawDataPointer()), source_type); 
     445        tTypedPointer destination_first = destination_object.GetVectorElement(0); 
     446        operation.Continue(source, destination_object); 
     447        if (size > 1) 
     448        { 
     449          tTypedConstPointer source(static_cast<const char*>(source_object.GetRawDataPointer()) + source_element_offset, source_type); 
     450          tTypedPointer destination_next = destination_object.GetVectorElement(1); 
     451          operation.Continue(source, destination_next); 
     452          size_t offset_destination = static_cast<const char*>(destination_next.GetRawDataPointer()) - static_cast<const char*>(destination_first.GetRawDataPointer()); 
     453          for (size_t i = 2; i < size; i++) 
     454          { 
     455            tTypedConstPointer source(static_cast<const char*>(source_object.GetRawDataPointer()) + i * source_element_offset, source_type); 
     456            destination_next = tTypedPointer(static_cast<char*>(destination_next.GetRawDataPointer()) + offset_destination, destination_type); 
     457            operation.Continue(source, destination_next); 
     458          } 
     459        } 
     460      } 
     461    } 
     462    else 
     463    { 
     464      throw std::runtime_error("Unsupported types for 'For Each' Operation"); 
     465    } 
     466  } 
     467 
     468  static void FinalConversionFunction(const tTypedConstPointer& source_object, const tTypedPointer& destination_object, const tCurrentConversionOperation& operation) 
     469  { 
     470    throw std::logic_error("Not supported as single or second operation"); 
     471  } 
     472}; 
     473 
     474class tArrayToVector : public tRegisteredConversionOperation 
     475{ 
     476public: 
     477  tArrayToVector() : tRegisteredConversionOperation(util::tManagedConstCharPointer("ToVector", false), tSupportedTypeFilter::ARRAY_TO_VECTOR, tSupportedTypeFilter::ARRAY_TO_VECTOR) 
     478  {} 
     479 
     480  virtual tConversionOption GetConversionOption(const tType& source_type, const tType& destination_type, const tGenericObject* parameter) const override 
     481  { 
     482    if (source_type.IsArray() && destination_type.IsListType() && source_type.GetElementType() == destination_type.GetElementType()) 
     483    { 
     484      return tConversionOption(source_type, destination_type, false, &FirstConversionFunction, &FinalConversionFunction); 
     485    } 
     486    return tConversionOption(); 
     487  } 
     488 
     489  static void FirstConversionFunction(const tTypedConstPointer& source_object, const tTypedPointer& destination_object, const tCurrentConversionOperation& operation) 
     490  { 
     491    tType inter_type = operation.compiled_operation.IntermediateType(); 
     492    char intermediate_memory[inter_type.GetSize(true)]; 
     493    auto intermediate_object = inter_type.EmplaceGenericObject(intermediate_memory); 
     494    FinalConversionFunction(source_object, *intermediate_object, operation); 
     495    operation.Continue(*intermediate_object, destination_object); 
     496  } 
     497 
     498  static void FinalConversionFunction(const tTypedConstPointer& source_object, const tTypedPointer& destination_object, const tCurrentConversionOperation& operation) 
     499  { 
     500    const tType& source_type = source_object.GetType(); 
     501    size_t size = source_type.GetArraySize(); 
    390502    destination_object.ResizeVector(size); 
    391503    if (size) 
    392504    { 
    393       tTypedConstPointer source_first = source_object.GetVectorElement(0); 
     505      size_t source_element_offset = source_type.GetSize() / size; 
     506      tTypedConstPointer source(static_cast<const char*>(source_object.GetRawDataPointer()), source_type); 
    394507      tTypedPointer destination_first = destination_object.GetVectorElement(0); 
    395       operation.Continue(source_first, destination_object); 
     508      destination_first.DeepCopyFrom(source); 
    396509      if (size > 1) 
    397510      { 
    398         tTypedConstPointer source_next = source_object.GetVectorElement(1); 
     511        tTypedConstPointer source(static_cast<const char*>(source_object.GetRawDataPointer()) + source_element_offset, source_type); 
    399512        tTypedPointer destination_next = destination_object.GetVectorElement(1); 
    400         operation.Continue(source_next, destination_next); 
    401         size_t offset_source = static_cast<const char*>(source_next.GetRawDataPointer()) - static_cast<const char*>(source_first.GetRawDataPointer()); 
     513        destination_next.DeepCopyFrom(source); 
    402514        size_t offset_destination = static_cast<const char*>(destination_next.GetRawDataPointer()) - static_cast<const char*>(destination_first.GetRawDataPointer()); 
    403515        for (size_t i = 2; i < size; i++) 
    404516        { 
    405           source_next = tTypedConstPointer(static_cast<const char*>(source_next.GetRawDataPointer()) + offset_source, source_next.GetType()); 
     517          tTypedConstPointer source(static_cast<const char*>(source_object.GetRawDataPointer()) + i * source_element_offset, source_type); 
    406518          destination_next = tTypedPointer(static_cast<char*>(destination_next.GetRawDataPointer()) + offset_destination, destination_next.GetType()); 
    407           operation.Continue(source_next, destination_next); 
     519          destination_next.DeepCopyFrom(source); 
    408520        } 
    409521      } 
    410522    } 
    411523  } 
    412  
    413   static void FinalConversionFunction(const tTypedConstPointer& source_object, const tTypedPointer& destination_object, const tCurrentConversionOperation& operation) 
    414   { 
    415     throw std::logic_error("Not supported as single or second operation"); 
    416   } 
    417 }; 
    418  
    419 class tGetArrayElement : public tRegisteredConversionOperation 
    420 { 
    421 public: 
    422   tGetArrayElement() : tRegisteredConversionOperation(util::tManagedConstCharPointer("[]", false), tSupportedTypeFilter::GET_ARRAY_ELEMENT, tSupportedTypeFilter::GET_ARRAY_ELEMENT, nullptr, tParameterDefinition("Index", tDataType<unsigned int>(), true)) 
     524}; 
     525 
     526class tGetTupleElement : public tRegisteredConversionOperation 
     527{ 
     528public: 
     529  tGetTupleElement() : tRegisteredConversionOperation(util::tManagedConstCharPointer("get", false), tSupportedTypeFilter::GET_TUPLE_ELEMENT, tSupportedTypeFilter::GET_TUPLE_ELEMENT, nullptr, tParameterDefinition("Index", tDataType<unsigned int>(), true)) 
    423530  {} 
    424531 
     
    426533  { 
    427534    unsigned int index = parameter ? parameter->GetData<unsigned int>() : 0; 
    428     if (source_type.IsArray() && source_type.GetElementType() == destination_type && index < source_type.GetArraySize()) 
    429     { 
    430       return tConversionOption(source_type, destination_type, index * source_type.GetElementType().GetSize()); 
    431     } 
    432     return tConversionOption(); 
    433   } 
    434 }; 
    435  
    436 class tForEachArray : public tRegisteredConversionOperation 
    437 { 
    438 public: 
    439   tForEachArray() : tRegisteredConversionOperation(util::tManagedConstCharPointer("For Each", false), tSupportedTypeFilter::GENERIC_ARRAY_CAST, tSupportedTypeFilter::GENERIC_ARRAY_CAST) 
    440   {} 
    441  
    442   virtual tConversionOption GetConversionOption(const tType& source_type, const tType& destination_type, const tGenericObject* parameter) const override 
    443   { 
    444     if ((source_type.GetTypeTraits() & trait_flags::cIS_ARRAY) && destination_type) 
    445     { 
    446       return tConversionOption(source_type, destination_type, false, &FirstConversionFunction, &FinalConversionFunction); 
    447     } 
    448     return tConversionOption(); 
    449   } 
    450  
    451   static void FirstConversionFunction(const tTypedConstPointer& source_object, const tTypedPointer& destination_object, const tCurrentConversionOperation& operation) 
    452   { 
    453     tType source_type = source_object.GetType(); 
    454     tType destination_type = destination_object.GetType(); 
    455     size_t size = source_type.GetArraySize(); 
    456     if (size != destination_type.GetArraySize()) 
    457     { 
    458       throw std::runtime_error("Arrays must have the same size"); 
    459     } 
    460  
    461     size_t source_element_offset = source_type.GetSize() / size; 
    462     size_t destination_element_offset = destination_type.GetSize() / size; 
    463     for (size_t i = 0; i < size; i++) 
    464     { 
    465       tTypedConstPointer source(static_cast<const char*>(source_object.GetRawDataPointer()) + i * source_element_offset, source_type); 
    466       tTypedPointer destination(static_cast<char*>(destination_object.GetRawDataPointer()) + i * destination_element_offset, destination_type); 
    467       operation.Continue(source, destination); 
    468     } 
    469   } 
    470  
    471   static void FinalConversionFunction(const tTypedConstPointer& source_object, const tTypedPointer& destination_object, const tCurrentConversionOperation& operation) 
    472   { 
    473     throw std::logic_error("Not supported as single or second operation"); 
     535    auto tuple_types = source_type.GetTupleTypes(); 
     536    if (index < tuple_types.second && destination_type == tType(tuple_types.first[index].type_info)) 
     537    { 
     538      return tConversionOption(source_type, destination_type, tuple_types.first[index].offset); 
     539    } 
     540    return tConversionOption(); 
    474541  } 
    475542}; 
     
    551618const tBinarySerializationOperation cBINARY_SERIALIZATION; 
    552619const tBinaryDeserializationOperation cBINARY_DESERIALIZATION; 
     620 
    553621const tGetListElement cGET_LIST_ELEMENT; 
    554622const tForEach cFOR_EACH; 
    555 const tGetArrayElement cGET_ARRAY_ELEMENT; 
    556 const tForEachArray cFOR_EACH_ARRAY; 
     623const tArrayToVector cARRAY_TO_VECTOR; 
     624const tGetTupleElement cGET_TUPLE_ELEMENT; 
     625 
    557626const tWrapByteVectorOperation cWRAP_BYTE_VECTOR; 
    558627const tListSize cLIST_SIZE; 
     
    566635const tRegisteredConversionOperation& cBINARY_SERIALIZATION_OPERATION = cBINARY_SERIALIZATION; 
    567636const tRegisteredConversionOperation& cBINARY_DESERIALIZATION_OPERATION = cBINARY_DESERIALIZATION; 
     637 
    568638const tRegisteredConversionOperation& cGET_LIST_ELEMENT_OPERATION = cGET_LIST_ELEMENT; 
    569639const tRegisteredConversionOperation& cFOR_EACH_OPERATION = cFOR_EACH; 
    570 const tRegisteredConversionOperation& cGET_ARRAY_ELEMENT_OPERATION = cGET_ARRAY_ELEMENT; 
    571 const tRegisteredConversionOperation& cFOR_EACH_OPERATION_ARRAY = cFOR_EACH_ARRAY; 
     640const tRegisteredConversionOperation& cARRAY_TO_VECTOR_OPERATION = cARRAY_TO_VECTOR; 
     641const tRegisteredConversionOperation& cGET_TUPLE_ELEMENT_OPERATION = cGET_TUPLE_ELEMENT; 
     642 
    572643const tRegisteredConversionOperation& cWRAP_BYTE_VECTOR_OPERATION = cWRAP_BYTE_VECTOR; 
    573644const tRegisteredConversionOperation& cLIST_SIZE_OPERATION = cLIST_SIZE; 
  • defined_conversions.h

    r7 r8  
    8080extern const tRegisteredConversionOperation& cBINARY_DESERIALIZATION_OPERATION; //!< Deserializes binary serializable type from serialization::tMemoryBuffer 
    8181 
    82 extern const tRegisteredConversionOperation& cGET_LIST_ELEMENT_OPERATION;       //!< Get Element with specified index (parameter) from list type (std::vector) 
    83 extern const tRegisteredConversionOperation& cFOR_EACH_OPERATION;               //!< Special conversion operation for std::vectors that applies second conversion operation on all elements 
    84  
    85 extern const tRegisteredConversionOperation& cGET_ARRAY_ELEMENT_OPERATION;      //!< Get Element with specified index (parameter) from array type (std::array) 
    86 extern const tRegisteredConversionOperation& cFOR_EACH_OPERATION_ARRAY;         //!< Special conversion operation for std::arrays that applies second conversion operation on all elements 
     82extern const tRegisteredConversionOperation& cGET_LIST_ELEMENT_OPERATION;       //!< Get Element with specified index (parameter) from list type (std::vector) or array type (std::array) 
     83extern const tRegisteredConversionOperation& cFOR_EACH_OPERATION;               //!< Special conversion operation for std::vectors and std::arrays that applies second conversion operation on all elements (can convert std::vector<T> to std::vector<U>, std::array<T> to std::array<U>, and std::array<T> to std::vector<U>) 
    8784extern const tRegisteredConversionOperation& cARRAY_TO_VECTOR_OPERATION;        //!< Converts std::array<T> to std::vector<T> 
     85extern const tRegisteredConversionOperation& cGET_TUPLE_ELEMENT_OPERATION;      //!< Get element of std::pair or std::tuple object 
    8886 
    8987extern const tRegisteredConversionOperation& cWRAP_BYTE_VECTOR_OPERATION;       //!< Converts std::vector<uint> to a MemoryBuffer. This is particulary efficient (zero-copy) when first operation in a sequence. 
  • tConversionOperationSequence.cpp

    r7 r8  
    198198 
    199199  // For each operation 
    200   else if (first_operation == &cFOR_EACH_OPERATION || first_operation == &cFOR_EACH_OPERATION_ARRAY) 
    201   { 
    202     if ((first_operation == &cFOR_EACH_OPERATION && (!(type_source.IsListType() && type_destination.IsListType()))) || (first_operation == &cFOR_EACH_OPERATION_ARRAY && (!(type_source.IsArray() && type_destination.IsArray() && type_source.GetArraySize() == destination_type.GetArraySize())))) 
    203     { 
    204       throw std::runtime_error("ForEach operation only applicable on list types and array types (of same size)"); 
     200  else if (first_operation == &cFOR_EACH_OPERATION) 
     201  { 
     202    if (!((type_source.IsListType() && type_destination.IsListType()) || 
     203          (type_source.IsArray() && type_destination.IsArray() && type_source.GetArraySize() == destination_type.GetArraySize()) || 
     204          (type_source.IsArray() && type_destination.IsListType()))) 
     205    { 
     206      throw std::runtime_error("ForEach operation only applicable on list types and array types"); 
    205207    } 
    206208    if (!second_operation) 
  • tRegisteredConversionOperation.h

    r7 r8  
    8484  // Special operations defined in rrlib_rtti_conversion (known in Java tooling) 
    8585  STATIC_CAST,         //!< Types supported by static casts (only used for tStaticCastOperation) 
    86   GENERIC_VECTOR_CAST, //!< Types supported by generic vector cast 
    87   GENERIC_ARRAY_CAST,  //!< Types supported by generic array cast 
     86  FOR_EACH,            //!< Types supported by for-each operation 
    8887  GET_LIST_ELEMENT,    //!< Types supported by get list element 
    89   GET_ARRAY_ELEMENT,   //!< Types supported by get array element 
     88  ARRAY_TO_VECTOR,     //!< Types supported by array to vector operation 
     89  GET_TUPLE_ELEMENT    //!< Types supported by get tuple element operation 
    9090}; 
    9191 
Note: See TracChangeset for help on using the changeset viewer.