odxtools 9.6.1__py3-none-any.whl → 9.7.0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- odxtools/addressing.py +8 -0
- odxtools/basecomparam.py +2 -15
- odxtools/basicstructure.py +4 -3
- odxtools/codec.py +1 -184
- odxtools/commrelation.py +1 -8
- odxtools/commrelationvaluetype.py +9 -0
- odxtools/compositecodec.py +191 -0
- odxtools/compumethods/compucategory.py +13 -0
- odxtools/compumethods/compucodecompumethod.py +2 -1
- odxtools/compumethods/compumethod.py +1 -12
- odxtools/compumethods/intervaltype.py +8 -0
- odxtools/compumethods/limit.py +1 -7
- odxtools/compumethods/linearcompumethod.py +2 -1
- odxtools/compumethods/ratfunccompumethod.py +2 -1
- odxtools/compumethods/scalelinearcompumethod.py +3 -2
- odxtools/compumethods/scaleratfunccompumethod.py +2 -1
- odxtools/compumethods/tabintpcompumethod.py +4 -2
- odxtools/compumethods/texttablecompumethod.py +2 -1
- odxtools/description.py +1 -17
- odxtools/diagclasstype.py +11 -0
- odxtools/diagcomm.py +2 -25
- odxtools/diagservice.py +3 -79
- odxtools/dtcconnector.py +45 -0
- odxtools/dtcdop.py +2 -47
- odxtools/dyndefinedspec.py +3 -155
- odxtools/dyniddefmodeinfo.py +161 -0
- odxtools/envdataconnector.py +49 -0
- odxtools/externalaccessmethod.py +23 -0
- odxtools/externaldoc.py +23 -0
- odxtools/linkeddtcdop.py +62 -0
- odxtools/minmaxlengthtype.py +1 -7
- odxtools/parameterinfo.py +1 -1
- odxtools/parameters/rowfragment.py +7 -0
- odxtools/parameters/tableentryparameter.py +1 -6
- odxtools/physicaltype.py +1 -8
- odxtools/posresponsesuppressible.py +73 -0
- odxtools/radix.py +9 -0
- odxtools/relateddiagcommref.py +23 -0
- odxtools/request.py +5 -3
- odxtools/response.py +5 -3
- odxtools/scaleconstr.py +1 -8
- odxtools/standardizationlevel.py +9 -0
- odxtools/standardlengthtype.py +2 -11
- odxtools/statetransition.py +1 -14
- odxtools/subcomponent.py +8 -241
- odxtools/subcomponentparamconnector.py +103 -0
- odxtools/subcomponentpattern.py +42 -0
- odxtools/table.py +3 -41
- odxtools/tablediagcommconnector.py +47 -0
- odxtools/tablerowconnector.py +46 -0
- odxtools/templates/macros/printService.xml.jinja2 +2 -1
- odxtools/termination.py +8 -0
- odxtools/transmode.py +9 -0
- odxtools/unitgroup.py +1 -6
- odxtools/unitgroupcategory.py +7 -0
- odxtools/usage.py +9 -0
- odxtools/utils.py +29 -0
- odxtools/validtype.py +9 -0
- odxtools/version.py +2 -2
- {odxtools-9.6.1.dist-info → odxtools-9.7.0.dist-info}/METADATA +1 -1
- {odxtools-9.6.1.dist-info → odxtools-9.7.0.dist-info}/RECORD +65 -39
- {odxtools-9.6.1.dist-info → odxtools-9.7.0.dist-info}/WHEEL +0 -0
- {odxtools-9.6.1.dist-info → odxtools-9.7.0.dist-info}/entry_points.txt +0 -0
- {odxtools-9.6.1.dist-info → odxtools-9.7.0.dist-info}/licenses/LICENSE +0 -0
- {odxtools-9.6.1.dist-info → odxtools-9.7.0.dist-info}/top_level.txt +0 -0
odxtools/diagcomm.py
CHANGED
@@ -1,11 +1,11 @@
|
|
1
1
|
# SPDX-License-Identifier: MIT
|
2
2
|
from dataclasses import dataclass
|
3
|
-
from enum import Enum
|
4
3
|
from typing import TYPE_CHECKING, Any, Dict, List, Optional
|
5
4
|
from xml.etree import ElementTree
|
6
5
|
|
7
6
|
from .admindata import AdminData
|
8
7
|
from .audience import Audience
|
8
|
+
from .diagclasstype import DiagClassType
|
9
9
|
from .element import IdentifiableElement
|
10
10
|
from .exceptions import odxraise, odxrequire
|
11
11
|
from .functionalclass import FunctionalClass
|
@@ -13,6 +13,7 @@ from .nameditemlist import NamedItemList
|
|
13
13
|
from .odxlink import OdxDocFragment, OdxLinkDatabase, OdxLinkId, OdxLinkRef, resolve_snref
|
14
14
|
from .odxtypes import odxstr_to_bool
|
15
15
|
from .preconditionstateref import PreConditionStateRef
|
16
|
+
from .relateddiagcommref import RelatedDiagCommRef
|
16
17
|
from .snrefcontext import SnRefContext
|
17
18
|
from .specialdatagroup import SpecialDataGroup
|
18
19
|
from .state import State
|
@@ -24,30 +25,6 @@ if TYPE_CHECKING:
|
|
24
25
|
from .diaglayers.protocol import Protocol
|
25
26
|
|
26
27
|
|
27
|
-
class DiagClassType(Enum):
|
28
|
-
STARTCOMM = "STARTCOMM"
|
29
|
-
STOPCOMM = "STOPCOMM"
|
30
|
-
VARIANTIDENTIFICATION = "VARIANTIDENTIFICATION"
|
31
|
-
READ_DYN_DEFINED_MESSAGE = "READ-DYN-DEFINED-MESSAGE"
|
32
|
-
DYN_DEF_MESSAGE = "DYN-DEF-MESSAGE"
|
33
|
-
CLEAR_DYN_DEF_MESSAGE = "CLEAR-DYN-DEF-MESSAGE"
|
34
|
-
|
35
|
-
|
36
|
-
@dataclass
|
37
|
-
class RelatedDiagCommRef(OdxLinkRef):
|
38
|
-
relation_type: str
|
39
|
-
|
40
|
-
@staticmethod
|
41
|
-
def from_et( # type: ignore[override]
|
42
|
-
et_element: ElementTree.Element,
|
43
|
-
doc_frags: List[OdxDocFragment]) -> "RelatedDiagCommRef":
|
44
|
-
kwargs = dataclass_fields_asdict(odxrequire(OdxLinkRef.from_et(et_element, doc_frags)))
|
45
|
-
|
46
|
-
relation_type = odxrequire(et_element.findtext("RELATION-TYPE"))
|
47
|
-
|
48
|
-
return RelatedDiagCommRef(relation_type=relation_type, **kwargs)
|
49
|
-
|
50
|
-
|
51
28
|
@dataclass
|
52
29
|
class DiagComm(IdentifiableElement):
|
53
30
|
"""Representation of a diagnostic communication object.
|
odxtools/diagservice.py
CHANGED
@@ -1,9 +1,9 @@
|
|
1
1
|
# SPDX-License-Identifier: MIT
|
2
2
|
from dataclasses import dataclass
|
3
|
-
from enum import Enum
|
4
3
|
from typing import Any, Dict, List, Optional, Union, cast
|
5
4
|
from xml.etree import ElementTree
|
6
5
|
|
6
|
+
from .addressing import Addressing
|
7
7
|
from .comparaminstance import ComparamInstance
|
8
8
|
from .diagcomm import DiagComm
|
9
9
|
from .exceptions import DecodeError, DecodeMismatch, odxassert, odxraise, odxrequire
|
@@ -12,90 +12,14 @@ from .nameditemlist import NamedItemList
|
|
12
12
|
from .odxlink import OdxDocFragment, OdxLinkDatabase, OdxLinkId, OdxLinkRef
|
13
13
|
from .odxtypes import ParameterValue, odxstr_to_bool
|
14
14
|
from .parameters.parameter import Parameter
|
15
|
+
from .posresponsesuppressible import PosResponseSuppressible
|
15
16
|
from .request import Request
|
16
17
|
from .response import Response
|
17
18
|
from .snrefcontext import SnRefContext
|
19
|
+
from .transmode import TransMode
|
18
20
|
from .utils import dataclass_fields_asdict
|
19
21
|
|
20
22
|
|
21
|
-
class Addressing(Enum):
|
22
|
-
FUNCTIONAL = "FUNCTIONAL"
|
23
|
-
PHYSICAL = "PHYSICAL"
|
24
|
-
FUNCTIONAL_OR_PHYSICAL = "FUNCTIONAL-OR-PHYSICAL"
|
25
|
-
|
26
|
-
|
27
|
-
class TransMode(Enum):
|
28
|
-
SEND_ONLY = "SEND-ONLY"
|
29
|
-
RECEIVE_ONLY = "RECEIVE-ONLY"
|
30
|
-
SEND_AND_RECEIVE = "SEND-AND-RECEIVE"
|
31
|
-
SEND_OR_RECEIVE = "SEND-OR-RECEIVE"
|
32
|
-
|
33
|
-
|
34
|
-
# note that the spec has a typo here: it calls the corresponding
|
35
|
-
# XML tag POS-RESPONSE-SUPPRESSABLE...
|
36
|
-
@dataclass
|
37
|
-
class PosResponseSuppressible:
|
38
|
-
bit_mask: int
|
39
|
-
|
40
|
-
coded_const_snref: Optional[str]
|
41
|
-
coded_const_snpathref: Optional[str]
|
42
|
-
|
43
|
-
value_snref: Optional[str]
|
44
|
-
value_snpathref: Optional[str]
|
45
|
-
|
46
|
-
phys_const_snref: Optional[str]
|
47
|
-
phys_const_snpathref: Optional[str]
|
48
|
-
|
49
|
-
table_key_snref: Optional[str]
|
50
|
-
table_key_snpathref: Optional[str]
|
51
|
-
|
52
|
-
@staticmethod
|
53
|
-
def from_et(et_element: ElementTree.Element,
|
54
|
-
doc_frags: List[OdxDocFragment]) -> "PosResponseSuppressible":
|
55
|
-
|
56
|
-
bit_mask = int(odxrequire(et_element.findtext("BIT-MASK")))
|
57
|
-
|
58
|
-
coded_const_snref = None
|
59
|
-
if (cc_snref_elem := et_element.find("CODED-CONST-SNREF")) is not None:
|
60
|
-
coded_const_snref = cc_snref_elem.attrib["SHORT-NAME"]
|
61
|
-
coded_const_snpathref = None
|
62
|
-
if (cc_snpathref_elem := et_element.find("CODED-CONST-SNPATHREF")) is not None:
|
63
|
-
coded_const_snpathref = cc_snpathref_elem.attrib["SHORT-NAME-PATH"]
|
64
|
-
|
65
|
-
value_snref = None
|
66
|
-
if (cc_snref_elem := et_element.find("VALUE-SNREF")) is not None:
|
67
|
-
value_snref = cc_snref_elem.attrib["SHORT-NAME"]
|
68
|
-
value_snpathref = None
|
69
|
-
if (cc_snpathref_elem := et_element.find("VALUE-SNPATHREF")) is not None:
|
70
|
-
value_snpathref = cc_snpathref_elem.attrib["SHORT-NAME-PATH"]
|
71
|
-
|
72
|
-
phys_const_snref = None
|
73
|
-
if (cc_snref_elem := et_element.find("PHYS-CONST-SNREF")) is not None:
|
74
|
-
phys_const_snref = cc_snref_elem.attrib["SHORT-NAME"]
|
75
|
-
phys_const_snpathref = None
|
76
|
-
if (cc_snpathref_elem := et_element.find("PHYS-CONST-SNPATHREF")) is not None:
|
77
|
-
phys_const_snpathref = cc_snpathref_elem.attrib["SHORT-NAME-PATH"]
|
78
|
-
|
79
|
-
table_key_snref = None
|
80
|
-
if (cc_snref_elem := et_element.find("TABLE-KEY-SNREF")) is not None:
|
81
|
-
table_key_snref = cc_snref_elem.attrib["SHORT-NAME"]
|
82
|
-
table_key_snpathref = None
|
83
|
-
if (cc_snpathref_elem := et_element.find("TABLE-KEY-SNPATHREF")) is not None:
|
84
|
-
table_key_snpathref = cc_snpathref_elem.attrib["SHORT-NAME-PATH"]
|
85
|
-
|
86
|
-
return PosResponseSuppressible(
|
87
|
-
bit_mask=bit_mask,
|
88
|
-
coded_const_snref=coded_const_snref,
|
89
|
-
coded_const_snpathref=coded_const_snpathref,
|
90
|
-
value_snref=value_snref,
|
91
|
-
value_snpathref=value_snpathref,
|
92
|
-
phys_const_snref=phys_const_snref,
|
93
|
-
phys_const_snpathref=phys_const_snpathref,
|
94
|
-
table_key_snref=table_key_snref,
|
95
|
-
table_key_snpathref=table_key_snpathref,
|
96
|
-
)
|
97
|
-
|
98
|
-
|
99
23
|
@dataclass
|
100
24
|
class DiagService(DiagComm):
|
101
25
|
"""Representation of a diagnostic service description.
|
odxtools/dtcconnector.py
ADDED
@@ -0,0 +1,45 @@
|
|
1
|
+
# SPDX-License-Identifier: MIT
|
2
|
+
from dataclasses import dataclass
|
3
|
+
from typing import Any, Dict, List
|
4
|
+
from xml.etree import ElementTree
|
5
|
+
|
6
|
+
from .diagnostictroublecode import DiagnosticTroubleCode
|
7
|
+
from .dtcdop import DtcDop
|
8
|
+
from .element import NamedElement
|
9
|
+
from .exceptions import odxrequire
|
10
|
+
from .odxlink import OdxDocFragment, OdxLinkDatabase, OdxLinkId, OdxLinkRef, resolve_snref
|
11
|
+
from .snrefcontext import SnRefContext
|
12
|
+
from .utils import dataclass_fields_asdict
|
13
|
+
|
14
|
+
|
15
|
+
@dataclass
|
16
|
+
class DtcConnector(NamedElement):
|
17
|
+
dtc_dop_ref: OdxLinkRef
|
18
|
+
dtc_snref: str
|
19
|
+
|
20
|
+
@property
|
21
|
+
def dtc_dop(self) -> DtcDop:
|
22
|
+
return self._dtc_dop
|
23
|
+
|
24
|
+
@property
|
25
|
+
def dtc(self) -> DiagnosticTroubleCode:
|
26
|
+
return self._dtc
|
27
|
+
|
28
|
+
@staticmethod
|
29
|
+
def from_et(et_element: ElementTree.Element, doc_frags: List[OdxDocFragment]) -> "DtcConnector":
|
30
|
+
kwargs = dataclass_fields_asdict(NamedElement.from_et(et_element, doc_frags))
|
31
|
+
|
32
|
+
dtc_dop_ref = odxrequire(OdxLinkRef.from_et(et_element.find("DTC-DOP-REF"), doc_frags))
|
33
|
+
dtc_snref_el = odxrequire(et_element.find("DTC-SNREF"))
|
34
|
+
dtc_snref = odxrequire(dtc_snref_el.get("SHORT-NAME"))
|
35
|
+
|
36
|
+
return DtcConnector(dtc_dop_ref=dtc_dop_ref, dtc_snref=dtc_snref, **kwargs)
|
37
|
+
|
38
|
+
def _build_odxlinks(self) -> Dict[OdxLinkId, Any]:
|
39
|
+
return {}
|
40
|
+
|
41
|
+
def _resolve_odxlinks(self, odxlinks: OdxLinkDatabase) -> None:
|
42
|
+
self._dtc_dop = odxlinks.resolve(self.dtc_dop_ref, DtcDop)
|
43
|
+
|
44
|
+
def _resolve_snrefs(self, context: SnRefContext) -> None:
|
45
|
+
self._dtc = resolve_snref(self.dtc_snref, self._dtc_dop.dtcs, DiagnosticTroubleCode)
|
odxtools/dtcdop.py
CHANGED
@@ -14,60 +14,15 @@ from .diagnostictroublecode import DiagnosticTroubleCode
|
|
14
14
|
from .dopbase import DopBase
|
15
15
|
from .encodestate import EncodeState
|
16
16
|
from .exceptions import DecodeError, EncodeError, odxassert, odxraise, odxrequire
|
17
|
+
from .linkeddtcdop import LinkedDtcDop
|
17
18
|
from .nameditemlist import NamedItemList
|
18
|
-
from .odxlink import OdxDocFragment, OdxLinkDatabase, OdxLinkId, OdxLinkRef
|
19
|
+
from .odxlink import OdxDocFragment, OdxLinkDatabase, OdxLinkId, OdxLinkRef
|
19
20
|
from .odxtypes import ParameterValue, odxstr_to_bool
|
20
21
|
from .physicaltype import PhysicalType
|
21
22
|
from .snrefcontext import SnRefContext
|
22
23
|
from .utils import dataclass_fields_asdict
|
23
24
|
|
24
25
|
|
25
|
-
@dataclass
|
26
|
-
class LinkedDtcDop:
|
27
|
-
not_inherited_dtc_snrefs: List[str]
|
28
|
-
dtc_dop_ref: OdxLinkRef
|
29
|
-
|
30
|
-
@property
|
31
|
-
def not_inherited_dtcs(self) -> NamedItemList[DiagnosticTroubleCode]:
|
32
|
-
return self._not_inherited_dtcs
|
33
|
-
|
34
|
-
@property
|
35
|
-
def dtc_dop(self) -> "DtcDop":
|
36
|
-
return self._dtc_dop
|
37
|
-
|
38
|
-
@property
|
39
|
-
def short_name(self) -> str:
|
40
|
-
return self._dtc_dop.short_name
|
41
|
-
|
42
|
-
@staticmethod
|
43
|
-
def from_et(et_element: ElementTree.Element, doc_frags: List[OdxDocFragment]) -> "LinkedDtcDop":
|
44
|
-
not_inherited_dtc_snrefs = [
|
45
|
-
odxrequire(el.get("SHORT-NAME"))
|
46
|
-
for el in et_element.iterfind("NOT-INHERITED-DTC-SNREFS/"
|
47
|
-
"NOT-INHERITED-DTC-SNREF")
|
48
|
-
]
|
49
|
-
|
50
|
-
dtc_dop_ref = odxrequire(OdxLinkRef.from_et(et_element.find("DTC-DOP-REF"), doc_frags))
|
51
|
-
|
52
|
-
return LinkedDtcDop(
|
53
|
-
not_inherited_dtc_snrefs=not_inherited_dtc_snrefs, dtc_dop_ref=dtc_dop_ref)
|
54
|
-
|
55
|
-
def _build_odxlinks(self) -> Dict[OdxLinkId, Any]:
|
56
|
-
return {}
|
57
|
-
|
58
|
-
def _resolve_odxlinks(self, odxlinks: OdxLinkDatabase) -> None:
|
59
|
-
self._dtc_dop = odxlinks.resolve(self.dtc_dop_ref, DtcDop)
|
60
|
-
|
61
|
-
def _resolve_snrefs(self, context: SnRefContext) -> None:
|
62
|
-
dtc_dop = self._dtc_dop
|
63
|
-
not_inherited_dtcs = [
|
64
|
-
resolve_snref(ni_snref, dtc_dop.dtcs, DiagnosticTroubleCode)
|
65
|
-
for ni_snref in self.not_inherited_dtc_snrefs
|
66
|
-
]
|
67
|
-
|
68
|
-
self._not_inherited_dtcs = NamedItemList(not_inherited_dtcs)
|
69
|
-
|
70
|
-
|
71
26
|
@dataclass
|
72
27
|
class DtcDop(DopBase):
|
73
28
|
"""A DOP describing a diagnostic trouble code"""
|
odxtools/dyndefinedspec.py
CHANGED
@@ -1,163 +1,11 @@
|
|
1
1
|
# SPDX-License-Identifier: MIT
|
2
2
|
from dataclasses import dataclass
|
3
|
-
from typing import Any, Dict, List
|
3
|
+
from typing import Any, Dict, List
|
4
4
|
from xml.etree import ElementTree
|
5
5
|
|
6
|
-
from .
|
7
|
-
from .
|
8
|
-
from .nameditemlist import NamedItemList
|
9
|
-
from .odxlink import OdxDocFragment, OdxLinkDatabase, OdxLinkId, OdxLinkRef, resolve_snref
|
6
|
+
from .dyniddefmodeinfo import DynIdDefModeInfo
|
7
|
+
from .odxlink import OdxDocFragment, OdxLinkDatabase, OdxLinkId
|
10
8
|
from .snrefcontext import SnRefContext
|
11
|
-
from .table import Table
|
12
|
-
|
13
|
-
|
14
|
-
@dataclass
|
15
|
-
class DynIdDefModeInfo:
|
16
|
-
def_mode: str
|
17
|
-
|
18
|
-
clear_dyn_def_message_ref: Optional[OdxLinkRef]
|
19
|
-
clear_dyn_def_message_snref: Optional[str]
|
20
|
-
|
21
|
-
read_dyn_def_message_ref: Optional[OdxLinkRef]
|
22
|
-
read_dyn_def_message_snref: Optional[str]
|
23
|
-
|
24
|
-
dyn_def_message_ref: Optional[OdxLinkRef]
|
25
|
-
dyn_def_message_snref: Optional[str]
|
26
|
-
|
27
|
-
supported_dyn_ids: List[bytes]
|
28
|
-
selection_table_refs: List[Union[OdxLinkRef, str]]
|
29
|
-
|
30
|
-
@property
|
31
|
-
def clear_dyn_def_message(self) -> DiagComm:
|
32
|
-
return self._clear_dyn_def_message
|
33
|
-
|
34
|
-
@property
|
35
|
-
def read_dyn_def_message(self) -> DiagComm:
|
36
|
-
return self._read_dyn_def_message
|
37
|
-
|
38
|
-
@property
|
39
|
-
def dyn_def_message(self) -> DiagComm:
|
40
|
-
return self._dyn_def_message
|
41
|
-
|
42
|
-
@property
|
43
|
-
def selection_tables(self) -> NamedItemList[Table]:
|
44
|
-
return self._selection_tables
|
45
|
-
|
46
|
-
@staticmethod
|
47
|
-
def from_et(et_element: ElementTree.Element,
|
48
|
-
doc_frags: List[OdxDocFragment]) -> "DynIdDefModeInfo":
|
49
|
-
def_mode = odxrequire(et_element.findtext("DEF-MODE"))
|
50
|
-
|
51
|
-
clear_dyn_def_message_ref = OdxLinkRef.from_et(
|
52
|
-
et_element.find("CLEAR-DYN-DEF-MESSAGE-REF"), doc_frags)
|
53
|
-
clear_dyn_def_message_snref = None
|
54
|
-
if (snref_elem := et_element.find("CLEAR-DYN-DEF-MESSAGE-SNREF")) is not None:
|
55
|
-
clear_dyn_def_message_snref = odxrequire(snref_elem.attrib.get("SHORT-NAME"))
|
56
|
-
|
57
|
-
read_dyn_def_message_ref = OdxLinkRef.from_et(
|
58
|
-
et_element.find("READ-DYN-DEF-MESSAGE-REF"), doc_frags)
|
59
|
-
read_dyn_def_message_snref = None
|
60
|
-
if (snref_elem := et_element.find("READ-DYN-DEF-MESSAGE-SNREF")) is not None:
|
61
|
-
read_dyn_def_message_snref = odxrequire(snref_elem.attrib.get("SHORT-NAME"))
|
62
|
-
|
63
|
-
dyn_def_message_ref = OdxLinkRef.from_et(et_element.find("DYN-DEF-MESSAGE-REF"), doc_frags)
|
64
|
-
dyn_def_message_snref = None
|
65
|
-
if (snref_elem := et_element.find("DYN-DEF-MESSAGE-SNREF")) is not None:
|
66
|
-
dyn_def_message_snref = odxrequire(snref_elem.attrib.get("SHORT-NAME"))
|
67
|
-
|
68
|
-
supported_dyn_ids = [
|
69
|
-
bytes.fromhex(odxrequire(x.text))
|
70
|
-
for x in et_element.iterfind("SUPPORTED-DYN-IDS/SUPPORTED-DYN-ID")
|
71
|
-
]
|
72
|
-
|
73
|
-
selection_table_refs: List[Union[OdxLinkRef, str]] = []
|
74
|
-
if (st_elems := et_element.find("SELECTION-TABLE-REFS")) is not None:
|
75
|
-
for st_elem in st_elems:
|
76
|
-
if st_elem.tag == "SELECTION-TABLE-REF":
|
77
|
-
selection_table_refs.append(OdxLinkRef.from_et(st_elem, doc_frags))
|
78
|
-
elif st_elem.tag == "SELECTION-TABLE-SNREF":
|
79
|
-
selection_table_refs.append(odxrequire(st_elem.get("SHORT-NAME")))
|
80
|
-
else:
|
81
|
-
odxraise()
|
82
|
-
|
83
|
-
return DynIdDefModeInfo(
|
84
|
-
def_mode=def_mode,
|
85
|
-
clear_dyn_def_message_ref=clear_dyn_def_message_ref,
|
86
|
-
clear_dyn_def_message_snref=clear_dyn_def_message_snref,
|
87
|
-
read_dyn_def_message_ref=read_dyn_def_message_ref,
|
88
|
-
read_dyn_def_message_snref=read_dyn_def_message_snref,
|
89
|
-
dyn_def_message_ref=dyn_def_message_ref,
|
90
|
-
dyn_def_message_snref=dyn_def_message_snref,
|
91
|
-
supported_dyn_ids=supported_dyn_ids,
|
92
|
-
selection_table_refs=selection_table_refs,
|
93
|
-
)
|
94
|
-
|
95
|
-
def __post_init__(self) -> None:
|
96
|
-
odxassert(
|
97
|
-
self.clear_dyn_def_message_ref is not None or
|
98
|
-
self.clear_dyn_def_message_snref is not None,
|
99
|
-
"A CLEAR-DYN-DEF-MESSAGE must be specified")
|
100
|
-
odxassert(
|
101
|
-
self.read_dyn_def_message_ref is not None or
|
102
|
-
self.read_dyn_def_message_snref is not None, "A READ-DYN-DEF-MESSAGE must be specified")
|
103
|
-
odxassert(self.dyn_def_message_ref is not None or self.dyn_def_message_snref is not None,
|
104
|
-
"A DYN-DEF-MESSAGE must be specified")
|
105
|
-
|
106
|
-
def _build_odxlinks(self) -> Dict[OdxLinkId, Any]:
|
107
|
-
result: Dict[OdxLinkId, Any] = {}
|
108
|
-
|
109
|
-
return result
|
110
|
-
|
111
|
-
def _resolve_odxlinks(self, odxlinks: OdxLinkDatabase) -> None:
|
112
|
-
if self.clear_dyn_def_message_ref is not None:
|
113
|
-
self._clear_dyn_def_message = odxlinks.resolve(self.clear_dyn_def_message_ref, DiagComm)
|
114
|
-
|
115
|
-
if self.read_dyn_def_message_ref is not None:
|
116
|
-
self._read_dyn_def_message = odxlinks.resolve(self.read_dyn_def_message_ref, DiagComm)
|
117
|
-
|
118
|
-
if self.dyn_def_message_ref is not None:
|
119
|
-
self._dyn_def_message = odxlinks.resolve(self.dyn_def_message_ref, DiagComm)
|
120
|
-
|
121
|
-
# resolve the selection tables that are referenced via ODXLINK
|
122
|
-
self._selection_tables = NamedItemList[Table]()
|
123
|
-
for x in self.selection_table_refs:
|
124
|
-
if isinstance(x, OdxLinkRef):
|
125
|
-
self._selection_tables.append(odxlinks.resolve(x, Table))
|
126
|
-
|
127
|
-
def _resolve_snrefs(self, context: SnRefContext) -> None:
|
128
|
-
diag_layer = odxrequire(context.diag_layer)
|
129
|
-
|
130
|
-
if self.clear_dyn_def_message_snref is not None:
|
131
|
-
self._clear_dyn_def_message = resolve_snref(self.clear_dyn_def_message_snref,
|
132
|
-
diag_layer.diag_comms, DiagComm)
|
133
|
-
|
134
|
-
if self.read_dyn_def_message_snref is not None:
|
135
|
-
self._read_dyn_def_message = resolve_snref(self.read_dyn_def_message_snref,
|
136
|
-
diag_layer.diag_comms, DiagComm)
|
137
|
-
|
138
|
-
if self.dyn_def_message_snref is not None:
|
139
|
-
self._dyn_def_message = resolve_snref(self.dyn_def_message_snref, diag_layer.diag_comms,
|
140
|
-
DiagComm)
|
141
|
-
|
142
|
-
if self._clear_dyn_def_message.diagnostic_class != DiagClassType.CLEAR_DYN_DEF_MESSAGE:
|
143
|
-
odxraise(
|
144
|
-
f"Diagnostic communication object of wrong type referenced: "
|
145
|
-
f"({odxrequire(self._clear_dyn_def_message.diagnostic_class).value} instead of "
|
146
|
-
f"CLEAR-DYN-DEF-MESSAGE)")
|
147
|
-
if self._read_dyn_def_message.diagnostic_class != DiagClassType.READ_DYN_DEFINED_MESSAGE:
|
148
|
-
odxraise(f"Diagnostic communication object of wrong type referenced: "
|
149
|
-
f"({odxrequire(self._read_dyn_def_message.diagnostic_class).value} instead of "
|
150
|
-
f"READ-DYN-DEFINED-MESSAGE)")
|
151
|
-
if self._dyn_def_message.diagnostic_class != DiagClassType.DYN_DEF_MESSAGE:
|
152
|
-
odxraise(f"Diagnostic communication object of wrong type referenced: "
|
153
|
-
f"({odxrequire(self._dyn_def_message.diagnostic_class).value} instead of "
|
154
|
-
f"DYN-DEF-MESSAGE)")
|
155
|
-
|
156
|
-
# resolve the remaining selection tables that are referenced via SNREF
|
157
|
-
ddd_spec = odxrequire(diag_layer.diag_data_dictionary_spec)
|
158
|
-
for i, x in enumerate(self.selection_table_refs):
|
159
|
-
if isinstance(x, str):
|
160
|
-
self._selection_tables.insert(i, resolve_snref(x, ddd_spec.tables, Table))
|
161
9
|
|
162
10
|
|
163
11
|
@dataclass
|
@@ -0,0 +1,161 @@
|
|
1
|
+
# SPDX-License-Identifier: MIT
|
2
|
+
from dataclasses import dataclass
|
3
|
+
from typing import Any, Dict, List, Optional, Union
|
4
|
+
from xml.etree import ElementTree
|
5
|
+
|
6
|
+
from .diagclasstype import DiagClassType
|
7
|
+
from .diagcomm import DiagComm
|
8
|
+
from .exceptions import odxassert, odxraise, odxrequire
|
9
|
+
from .nameditemlist import NamedItemList
|
10
|
+
from .odxlink import OdxDocFragment, OdxLinkDatabase, OdxLinkId, OdxLinkRef, resolve_snref
|
11
|
+
from .snrefcontext import SnRefContext
|
12
|
+
from .table import Table
|
13
|
+
|
14
|
+
|
15
|
+
@dataclass
|
16
|
+
class DynIdDefModeInfo:
|
17
|
+
def_mode: str
|
18
|
+
|
19
|
+
clear_dyn_def_message_ref: Optional[OdxLinkRef]
|
20
|
+
clear_dyn_def_message_snref: Optional[str]
|
21
|
+
|
22
|
+
read_dyn_def_message_ref: Optional[OdxLinkRef]
|
23
|
+
read_dyn_def_message_snref: Optional[str]
|
24
|
+
|
25
|
+
dyn_def_message_ref: Optional[OdxLinkRef]
|
26
|
+
dyn_def_message_snref: Optional[str]
|
27
|
+
|
28
|
+
supported_dyn_ids: List[bytes]
|
29
|
+
selection_table_refs: List[Union[OdxLinkRef, str]]
|
30
|
+
|
31
|
+
@property
|
32
|
+
def clear_dyn_def_message(self) -> DiagComm:
|
33
|
+
return self._clear_dyn_def_message
|
34
|
+
|
35
|
+
@property
|
36
|
+
def read_dyn_def_message(self) -> DiagComm:
|
37
|
+
return self._read_dyn_def_message
|
38
|
+
|
39
|
+
@property
|
40
|
+
def dyn_def_message(self) -> DiagComm:
|
41
|
+
return self._dyn_def_message
|
42
|
+
|
43
|
+
@property
|
44
|
+
def selection_tables(self) -> NamedItemList[Table]:
|
45
|
+
return self._selection_tables
|
46
|
+
|
47
|
+
@staticmethod
|
48
|
+
def from_et(et_element: ElementTree.Element,
|
49
|
+
doc_frags: List[OdxDocFragment]) -> "DynIdDefModeInfo":
|
50
|
+
def_mode = odxrequire(et_element.findtext("DEF-MODE"))
|
51
|
+
|
52
|
+
clear_dyn_def_message_ref = OdxLinkRef.from_et(
|
53
|
+
et_element.find("CLEAR-DYN-DEF-MESSAGE-REF"), doc_frags)
|
54
|
+
clear_dyn_def_message_snref = None
|
55
|
+
if (snref_elem := et_element.find("CLEAR-DYN-DEF-MESSAGE-SNREF")) is not None:
|
56
|
+
clear_dyn_def_message_snref = odxrequire(snref_elem.attrib.get("SHORT-NAME"))
|
57
|
+
|
58
|
+
read_dyn_def_message_ref = OdxLinkRef.from_et(
|
59
|
+
et_element.find("READ-DYN-DEF-MESSAGE-REF"), doc_frags)
|
60
|
+
read_dyn_def_message_snref = None
|
61
|
+
if (snref_elem := et_element.find("READ-DYN-DEF-MESSAGE-SNREF")) is not None:
|
62
|
+
read_dyn_def_message_snref = odxrequire(snref_elem.attrib.get("SHORT-NAME"))
|
63
|
+
|
64
|
+
dyn_def_message_ref = OdxLinkRef.from_et(et_element.find("DYN-DEF-MESSAGE-REF"), doc_frags)
|
65
|
+
dyn_def_message_snref = None
|
66
|
+
if (snref_elem := et_element.find("DYN-DEF-MESSAGE-SNREF")) is not None:
|
67
|
+
dyn_def_message_snref = odxrequire(snref_elem.attrib.get("SHORT-NAME"))
|
68
|
+
|
69
|
+
supported_dyn_ids = [
|
70
|
+
bytes.fromhex(odxrequire(x.text))
|
71
|
+
for x in et_element.iterfind("SUPPORTED-DYN-IDS/SUPPORTED-DYN-ID")
|
72
|
+
]
|
73
|
+
|
74
|
+
selection_table_refs: List[Union[OdxLinkRef, str]] = []
|
75
|
+
if (st_elems := et_element.find("SELECTION-TABLE-REFS")) is not None:
|
76
|
+
for st_elem in st_elems:
|
77
|
+
if st_elem.tag == "SELECTION-TABLE-REF":
|
78
|
+
selection_table_refs.append(OdxLinkRef.from_et(st_elem, doc_frags))
|
79
|
+
elif st_elem.tag == "SELECTION-TABLE-SNREF":
|
80
|
+
selection_table_refs.append(odxrequire(st_elem.get("SHORT-NAME")))
|
81
|
+
else:
|
82
|
+
odxraise()
|
83
|
+
|
84
|
+
return DynIdDefModeInfo(
|
85
|
+
def_mode=def_mode,
|
86
|
+
clear_dyn_def_message_ref=clear_dyn_def_message_ref,
|
87
|
+
clear_dyn_def_message_snref=clear_dyn_def_message_snref,
|
88
|
+
read_dyn_def_message_ref=read_dyn_def_message_ref,
|
89
|
+
read_dyn_def_message_snref=read_dyn_def_message_snref,
|
90
|
+
dyn_def_message_ref=dyn_def_message_ref,
|
91
|
+
dyn_def_message_snref=dyn_def_message_snref,
|
92
|
+
supported_dyn_ids=supported_dyn_ids,
|
93
|
+
selection_table_refs=selection_table_refs,
|
94
|
+
)
|
95
|
+
|
96
|
+
def __post_init__(self) -> None:
|
97
|
+
odxassert(
|
98
|
+
self.clear_dyn_def_message_ref is not None or
|
99
|
+
self.clear_dyn_def_message_snref is not None,
|
100
|
+
"A CLEAR-DYN-DEF-MESSAGE must be specified")
|
101
|
+
odxassert(
|
102
|
+
self.read_dyn_def_message_ref is not None or
|
103
|
+
self.read_dyn_def_message_snref is not None, "A READ-DYN-DEF-MESSAGE must be specified")
|
104
|
+
odxassert(self.dyn_def_message_ref is not None or self.dyn_def_message_snref is not None,
|
105
|
+
"A DYN-DEF-MESSAGE must be specified")
|
106
|
+
|
107
|
+
def _build_odxlinks(self) -> Dict[OdxLinkId, Any]:
|
108
|
+
result: Dict[OdxLinkId, Any] = {}
|
109
|
+
|
110
|
+
return result
|
111
|
+
|
112
|
+
def _resolve_odxlinks(self, odxlinks: OdxLinkDatabase) -> None:
|
113
|
+
if self.clear_dyn_def_message_ref is not None:
|
114
|
+
self._clear_dyn_def_message = odxlinks.resolve(self.clear_dyn_def_message_ref, DiagComm)
|
115
|
+
|
116
|
+
if self.read_dyn_def_message_ref is not None:
|
117
|
+
self._read_dyn_def_message = odxlinks.resolve(self.read_dyn_def_message_ref, DiagComm)
|
118
|
+
|
119
|
+
if self.dyn_def_message_ref is not None:
|
120
|
+
self._dyn_def_message = odxlinks.resolve(self.dyn_def_message_ref, DiagComm)
|
121
|
+
|
122
|
+
# resolve the selection tables that are referenced via ODXLINK
|
123
|
+
self._selection_tables = NamedItemList[Table]()
|
124
|
+
for x in self.selection_table_refs:
|
125
|
+
if isinstance(x, OdxLinkRef):
|
126
|
+
self._selection_tables.append(odxlinks.resolve(x, Table))
|
127
|
+
|
128
|
+
def _resolve_snrefs(self, context: SnRefContext) -> None:
|
129
|
+
diag_layer = odxrequire(context.diag_layer)
|
130
|
+
|
131
|
+
if self.clear_dyn_def_message_snref is not None:
|
132
|
+
self._clear_dyn_def_message = resolve_snref(self.clear_dyn_def_message_snref,
|
133
|
+
diag_layer.diag_comms, DiagComm)
|
134
|
+
|
135
|
+
if self.read_dyn_def_message_snref is not None:
|
136
|
+
self._read_dyn_def_message = resolve_snref(self.read_dyn_def_message_snref,
|
137
|
+
diag_layer.diag_comms, DiagComm)
|
138
|
+
|
139
|
+
if self.dyn_def_message_snref is not None:
|
140
|
+
self._dyn_def_message = resolve_snref(self.dyn_def_message_snref, diag_layer.diag_comms,
|
141
|
+
DiagComm)
|
142
|
+
|
143
|
+
if self._clear_dyn_def_message.diagnostic_class != DiagClassType.CLEAR_DYN_DEF_MESSAGE:
|
144
|
+
odxraise(
|
145
|
+
f"Diagnostic communication object of wrong type referenced: "
|
146
|
+
f"({odxrequire(self._clear_dyn_def_message.diagnostic_class).value} instead of "
|
147
|
+
f"CLEAR-DYN-DEF-MESSAGE)")
|
148
|
+
if self._read_dyn_def_message.diagnostic_class != DiagClassType.READ_DYN_DEFINED_MESSAGE:
|
149
|
+
odxraise(f"Diagnostic communication object of wrong type referenced: "
|
150
|
+
f"({odxrequire(self._read_dyn_def_message.diagnostic_class).value} instead of "
|
151
|
+
f"READ-DYN-DEFINED-MESSAGE)")
|
152
|
+
if self._dyn_def_message.diagnostic_class != DiagClassType.DYN_DEF_MESSAGE:
|
153
|
+
odxraise(f"Diagnostic communication object of wrong type referenced: "
|
154
|
+
f"({odxrequire(self._dyn_def_message.diagnostic_class).value} instead of "
|
155
|
+
f"DYN-DEF-MESSAGE)")
|
156
|
+
|
157
|
+
# resolve the remaining selection tables that are referenced via SNREF
|
158
|
+
ddd_spec = odxrequire(diag_layer.diag_data_dictionary_spec)
|
159
|
+
for i, x in enumerate(self.selection_table_refs):
|
160
|
+
if isinstance(x, str):
|
161
|
+
self._selection_tables.insert(i, resolve_snref(x, ddd_spec.tables, Table))
|
@@ -0,0 +1,49 @@
|
|
1
|
+
# SPDX-License-Identifier: MIT
|
2
|
+
from dataclasses import dataclass
|
3
|
+
from typing import Any, Dict, List
|
4
|
+
from xml.etree import ElementTree
|
5
|
+
|
6
|
+
from .element import NamedElement
|
7
|
+
from .environmentdata import EnvironmentData
|
8
|
+
from .environmentdatadescription import EnvironmentDataDescription
|
9
|
+
from .exceptions import odxrequire
|
10
|
+
from .odxlink import OdxDocFragment, OdxLinkDatabase, OdxLinkId, OdxLinkRef, resolve_snref
|
11
|
+
from .snrefcontext import SnRefContext
|
12
|
+
from .utils import dataclass_fields_asdict
|
13
|
+
|
14
|
+
|
15
|
+
@dataclass
|
16
|
+
class EnvDataConnector(NamedElement):
|
17
|
+
env_data_desc_ref: OdxLinkRef
|
18
|
+
env_data_snref: str
|
19
|
+
|
20
|
+
@property
|
21
|
+
def env_data_desc(self) -> EnvironmentDataDescription:
|
22
|
+
return self._env_data_desc
|
23
|
+
|
24
|
+
@property
|
25
|
+
def env_data(self) -> EnvironmentData:
|
26
|
+
return self._env_data
|
27
|
+
|
28
|
+
@staticmethod
|
29
|
+
def from_et(et_element: ElementTree.Element,
|
30
|
+
doc_frags: List[OdxDocFragment]) -> "EnvDataConnector":
|
31
|
+
kwargs = dataclass_fields_asdict(NamedElement.from_et(et_element, doc_frags))
|
32
|
+
|
33
|
+
env_data_desc_ref = odxrequire(
|
34
|
+
OdxLinkRef.from_et(et_element.find("ENV-DATA-DESC-REF"), doc_frags))
|
35
|
+
env_data_snref_el = odxrequire(et_element.find("ENV-DATA-SNREF"))
|
36
|
+
env_data_snref = odxrequire(env_data_snref_el.get("SHORT-NAME"))
|
37
|
+
|
38
|
+
return EnvDataConnector(
|
39
|
+
env_data_desc_ref=env_data_desc_ref, env_data_snref=env_data_snref, **kwargs)
|
40
|
+
|
41
|
+
def _build_odxlinks(self) -> Dict[OdxLinkId, Any]:
|
42
|
+
return {}
|
43
|
+
|
44
|
+
def _resolve_odxlinks(self, odxlinks: OdxLinkDatabase) -> None:
|
45
|
+
self._env_data_desc = odxlinks.resolve(self.env_data_desc_ref, EnvironmentDataDescription)
|
46
|
+
|
47
|
+
def _resolve_snrefs(self, context: SnRefContext) -> None:
|
48
|
+
self._env_data = resolve_snref(self.env_data_snref, self._env_data_desc.env_datas,
|
49
|
+
EnvironmentData)
|
@@ -0,0 +1,23 @@
|
|
1
|
+
# SPDX-License-Identifier: MIT
|
2
|
+
from dataclasses import dataclass
|
3
|
+
from typing import List
|
4
|
+
from xml.etree import ElementTree
|
5
|
+
|
6
|
+
from .element import IdentifiableElement
|
7
|
+
from .exceptions import odxrequire
|
8
|
+
from .odxlink import OdxDocFragment
|
9
|
+
from .utils import dataclass_fields_asdict
|
10
|
+
|
11
|
+
|
12
|
+
@dataclass
|
13
|
+
class ExternalAccessMethod(IdentifiableElement):
|
14
|
+
method: str
|
15
|
+
|
16
|
+
@staticmethod
|
17
|
+
def from_et(et_element: ElementTree.Element,
|
18
|
+
doc_frags: List[OdxDocFragment]) -> "ExternalAccessMethod":
|
19
|
+
kwargs = dataclass_fields_asdict(IdentifiableElement.from_et(et_element, doc_frags))
|
20
|
+
|
21
|
+
method = odxrequire(et_element.findtext("METHOD"))
|
22
|
+
|
23
|
+
return ExternalAccessMethod(method=method, **kwargs)
|