cogu / autosar

A set of python modules for working with AUTOSAR XML files
MIT License
353 stars 160 forks source link

ApplicationDataTypeRef in S/R port creation #106

Open qg020 opened 3 months ago

qg020 commented 3 months ago

My application reads an Excel file of new runnables and interfaces and adds them to existing project ARXML files. Almost all the data types used in the port interfaces are our own data types.

My script adds the data types to the workspace before adding the interfaces.

This worked with 0.4's createSenderReceiverInterface().

In 0.5.3, I am running into an issue creating the interface's data elements. Here is the code:

                port_if = ar_element.SenderReceiverInterface(if_name)
                data_element = ws_accelera.find_element(adt_key, data_type)
                if not data_element:
                    ws_accelera.add_element(adt_key, data_type)

                port_if.create_data_element(data_type, type_ref=data_element.ref())

When data_type is one of our defined data types, I get the following exception:

  File "C:\Users\qg020\sandbox\tools\arxml_generator\arxml_generator.py", line 285, in get_arxml
    port_if.create_data_element(data_type, type_ref=data_element.ref())
  File "C:\Users\qg020\sandbox\tools\arxml_generator\venv\Lib\site-packages\autosar\xml\element.py", line 3902, in create_data_element
    data_element = VariableDataPrototype(name, init_value, **kwargs)
                   ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "C:\Users\qg020\sandbox\tools\arxml_generator\venv\Lib\site-packages\autosar\xml\element.py", line 2622, in __init__
    super().__init__(name, **kwargs)
  File "C:\Users\qg020\sandbox\tools\arxml_generator\venv\Lib\site-packages\autosar\xml\element.py", line 2607, in __init__
    raise TypeError(msg + " Expected type 'AutosarDataTypeRef' or 'ImplementationDataTypeRef'")
TypeError: type_ref: Invalid type '<class 'autosar.xml.element.ApplicationDataTypeRef'>'. Expected type 'AutosarDataTypeRef' or 'ImplementationDataTypeRef'
ERROR:arxml_gen:FAIL

My hunch is this is because application-defined types are not yet supported when creating send/receive interfaces. Is that correct?

If so, when is this targetted for implementation?

Thanks!

cogu commented 3 months ago

@qg020, you need to convert whatever reference you get from the data-element into an AutosarDataTypeRef object before handing it over to the port-interface.

The create_data_element should only accept the type AutosarDataTypeRef and nothing else. Otherwise we will break the XML-schema. The addition of ImplementationDataTypeRef was a temporary workaround (see below) and should be removed in the near future.

Try something like this:

port_if = ar_element.SenderReceiverInterface(if_name)
data_element = ws_accelera.find_element(adt_key, data_type)
if not data_element:
    ws_accelera.add_element(adt_key, data_type)

type_ref=data_element.ref()
port_if.create_data_element(data_type, type_ref=ar_element.AutosarDataTypeRef(type_ref.value, type_ref.dest))

I haven't actually executed this code so I can't verify its correctness.

If you run into a problem. a safer version could be to use this:

import autosar.xml.enumeration as ar_enum

...

port_if.create_data_element(data_type, type_ref=ar_element.AutosarDataTypeRef(str(type_ref), ar_enum.IdentifiableSubTypes.APPLICATION_DATA_TYPE))

However, that will loose some type information (what kind of application type it is).

The root-cause of the issue is that the AUTOSAR XML-schema uses many different kinds of references, many which are overlapping and/or are sub-sets of each other.

I know how to solve the issue by implementing a "magic" self-checking type-casting between compatible reference classes but that requires a complete refactoring of the entire family of classes which is a lot of work.

So, until then you need to manually "cast" between the various reference types when the argument types don't match up.

qg020 commented 3 months ago

Almost! The new problem is create_data_element() wants ValueSpecificationElement for the second parameter not a DataTypeRef. Don't know how to get there from here.

Whatever happened to duck-typing-I-can-send-anything-anywhere python? (Don't answer that - I know.)

Edited code:

                port_if = ar_element.SenderReceiverInterface(if_name)
                data_element = ws_accelera.find_element(adt_key, data_type)
                if not data_element:
                    ws_accelera.add_element(adt_key, data_type)

                type_ref = data_element.ref()
                port_if.create_data_element(
                    data_type,
                    ar_element.AutosarDataTypeRef(str(type_ref), ar_enum.IdentifiableSubTypes.APPLICATION_DATA_TYPE))

The actual exception text:

  File "C:\Users\qg020\sandbox\tools\arxml_generator\arxml_generator.py", line 287, in get_arxml
    port_if.create_data_element(
  File "C:\Users\qg020\sandbox\tools\arxml_generator\venv\Lib\site-packages\autosar\xml\element.py", line 3902, in create_data_element
    data_element = VariableDataPrototype(name, init_value, **kwargs)
                   ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "C:\Users\qg020\sandbox\tools\arxml_generator\venv\Lib\site-packages\autosar\xml\element.py", line 2625, in __init__
    self._assign_optional_strict("init_value", init_value, ValueSpecification)
  File "C:\Users\qg020\sandbox\tools\arxml_generator\venv\Lib\site-packages\autosar\xml\element.py", line 207, in _assign_optional_strict
    self._set_attr_with_strict_type(attr_name, value, type_name)
  File "C:\Users\qg020\sandbox\tools\arxml_generator\venv\Lib\site-packages\autosar\xml\element.py", line 223, in _set_attr_with_strict_type
    raise TypeError(
TypeError: Invalid type for parameter 'init_value'. Expected type <class 'autosar.xml.element.ValueSpecification'>, got <class 'autosar.xml.element.AutosarDataTypeRef'>
ERROR:arxml_gen:FAIL
cogu commented 3 months ago

Ah, I simply forgot type_ref= in the example. I edited my post above with the correct code. Second positional argument was the init_value, that's not what we wanted to set.

qg020 commented 3 months ago

That got it - thank you!