odxtools 7.1.1__py3-none-any.whl → 7.3.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.
Files changed (135) hide show
  1. odxtools/__init__.py +6 -4
  2. odxtools/additionalaudience.py +3 -5
  3. odxtools/admindata.py +5 -7
  4. odxtools/audience.py +3 -5
  5. odxtools/basecomparam.py +3 -5
  6. odxtools/basicstructure.py +19 -23
  7. odxtools/cli/_parser_utils.py +1 -1
  8. odxtools/cli/_print_utils.py +3 -2
  9. odxtools/cli/compare.py +1 -1
  10. odxtools/companydata.py +5 -7
  11. odxtools/companydocinfo.py +7 -8
  12. odxtools/companyrevisioninfo.py +3 -5
  13. odxtools/companyspecificinfo.py +8 -9
  14. odxtools/comparam.py +4 -6
  15. odxtools/comparaminstance.py +6 -8
  16. odxtools/comparamspec.py +14 -13
  17. odxtools/comparamsubset.py +17 -16
  18. odxtools/complexcomparam.py +5 -7
  19. odxtools/compumethods/compuconst.py +31 -0
  20. odxtools/compumethods/compudefaultvalue.py +27 -0
  21. odxtools/compumethods/compuinternaltophys.py +39 -0
  22. odxtools/compumethods/compuinversevalue.py +7 -0
  23. odxtools/compumethods/compumethod.py +67 -12
  24. odxtools/compumethods/compuphystointernal.py +39 -0
  25. odxtools/compumethods/compuscale.py +15 -26
  26. odxtools/compumethods/createanycompumethod.py +14 -160
  27. odxtools/compumethods/identicalcompumethod.py +31 -6
  28. odxtools/compumethods/linearcompumethod.py +69 -189
  29. odxtools/compumethods/linearsegment.py +191 -0
  30. odxtools/compumethods/scalelinearcompumethod.py +132 -26
  31. odxtools/compumethods/tabintpcompumethod.py +119 -99
  32. odxtools/compumethods/texttablecompumethod.py +107 -43
  33. odxtools/createanydiagcodedtype.py +10 -67
  34. odxtools/database.py +84 -72
  35. odxtools/dataobjectproperty.py +10 -19
  36. odxtools/decodestate.py +8 -2
  37. odxtools/description.py +47 -0
  38. odxtools/determinenumberofitems.py +4 -5
  39. odxtools/diagcodedtype.py +29 -12
  40. odxtools/diagcomm.py +10 -6
  41. odxtools/diagdatadictionaryspec.py +20 -21
  42. odxtools/diaglayer.py +39 -9
  43. odxtools/diaglayercontainer.py +17 -11
  44. odxtools/diaglayerraw.py +20 -21
  45. odxtools/diagnostictroublecode.py +8 -9
  46. odxtools/diagservice.py +42 -27
  47. odxtools/docrevision.py +5 -7
  48. odxtools/dopbase.py +7 -8
  49. odxtools/dtcdop.py +44 -22
  50. odxtools/dynamicendmarkerfield.py +22 -9
  51. odxtools/dynamiclengthfield.py +5 -11
  52. odxtools/element.py +4 -3
  53. odxtools/encodestate.py +14 -2
  54. odxtools/endofpdufield.py +0 -2
  55. odxtools/environmentdatadescription.py +137 -19
  56. odxtools/exceptions.py +11 -2
  57. odxtools/field.py +9 -9
  58. odxtools/functionalclass.py +3 -5
  59. odxtools/inputparam.py +3 -5
  60. odxtools/leadinglengthinfotype.py +15 -2
  61. odxtools/loadfile.py +64 -0
  62. odxtools/minmaxlengthtype.py +20 -2
  63. odxtools/modification.py +3 -5
  64. odxtools/multiplexer.py +98 -69
  65. odxtools/multiplexercase.py +10 -11
  66. odxtools/multiplexerdefaultcase.py +11 -12
  67. odxtools/multiplexerswitchkey.py +4 -5
  68. odxtools/negoutputparam.py +3 -5
  69. odxtools/odxlink.py +12 -26
  70. odxtools/odxtypes.py +1 -1
  71. odxtools/outputparam.py +3 -5
  72. odxtools/parameterinfo.py +5 -5
  73. odxtools/parameters/codedconstparameter.py +2 -14
  74. odxtools/parameters/lengthkeyparameter.py +3 -17
  75. odxtools/parameters/nrcconstparameter.py +29 -50
  76. odxtools/parameters/parameter.py +22 -22
  77. odxtools/parameters/parameterwithdop.py +6 -8
  78. odxtools/parameters/physicalconstantparameter.py +5 -8
  79. odxtools/parameters/reservedparameter.py +4 -3
  80. odxtools/parameters/systemparameter.py +1 -1
  81. odxtools/parameters/tablekeyparameter.py +6 -9
  82. odxtools/parameters/tablestructparameter.py +6 -8
  83. odxtools/parameters/valueparameter.py +5 -8
  84. odxtools/paramlengthinfotype.py +19 -6
  85. odxtools/parentref.py +15 -1
  86. odxtools/physicaldimension.py +3 -5
  87. odxtools/progcode.py +18 -7
  88. odxtools/protstack.py +3 -5
  89. odxtools/relateddoc.py +7 -9
  90. odxtools/request.py +8 -0
  91. odxtools/response.py +8 -0
  92. odxtools/scaleconstr.py +3 -3
  93. odxtools/singleecujob.py +12 -10
  94. odxtools/snrefcontext.py +29 -0
  95. odxtools/specialdata.py +3 -5
  96. odxtools/specialdatagroup.py +5 -7
  97. odxtools/specialdatagroupcaption.py +3 -6
  98. odxtools/standardlengthtype.py +27 -2
  99. odxtools/state.py +3 -5
  100. odxtools/statechart.py +9 -11
  101. odxtools/statetransition.py +4 -9
  102. odxtools/staticfield.py +4 -8
  103. odxtools/table.py +7 -8
  104. odxtools/tablerow.py +7 -6
  105. odxtools/teammember.py +3 -5
  106. odxtools/templates/comparam-spec.odx-c.xml.jinja2 +2 -5
  107. odxtools/templates/comparam-subset.odx-cs.xml.jinja2 +2 -5
  108. odxtools/templates/macros/printCompanyData.xml.jinja2 +2 -5
  109. odxtools/templates/macros/printComparamRef.xml.jinja2 +5 -12
  110. odxtools/templates/macros/printCompuMethod.xml.jinja2 +153 -0
  111. odxtools/templates/macros/printDOP.xml.jinja2 +10 -132
  112. odxtools/templates/macros/printDescription.xml.jinja2 +18 -0
  113. odxtools/templates/macros/printElementId.xml.jinja2 +3 -3
  114. odxtools/templates/macros/printMux.xml.jinja2 +3 -2
  115. odxtools/templates/macros/printTable.xml.jinja2 +2 -3
  116. odxtools/unit.py +3 -5
  117. odxtools/unitgroup.py +3 -5
  118. odxtools/unitspec.py +9 -10
  119. odxtools/utils.py +1 -26
  120. odxtools/version.py +2 -2
  121. odxtools/{write_pdx_file.py → writepdxfile.py} +19 -10
  122. odxtools/xdoc.py +3 -5
  123. {odxtools-7.1.1.dist-info → odxtools-7.3.0.dist-info}/METADATA +1 -1
  124. odxtools-7.3.0.dist-info/RECORD +192 -0
  125. {odxtools-7.1.1.dist-info → odxtools-7.3.0.dist-info}/WHEEL +1 -1
  126. odxtools/createcompanydatas.py +0 -17
  127. odxtools/createsdgs.py +0 -19
  128. odxtools/load_file.py +0 -13
  129. odxtools/load_odx_d_file.py +0 -6
  130. odxtools/load_pdx_file.py +0 -8
  131. odxtools-7.1.1.dist-info/RECORD +0 -186
  132. /odxtools/templates/{index.xml.xml.jinja2 → index.xml.jinja2} +0 -0
  133. {odxtools-7.1.1.dist-info → odxtools-7.3.0.dist-info}/LICENSE +0 -0
  134. {odxtools-7.1.1.dist-info → odxtools-7.3.0.dist-info}/entry_points.txt +0 -0
  135. {odxtools-7.1.1.dist-info → odxtools-7.3.0.dist-info}/top_level.txt +0 -0
@@ -8,6 +8,7 @@
8
8
  {%- import('macros/printAdminData.xml.jinja2') as pad -%}
9
9
  {%- import('macros/printCompanyData.xml.jinja2') as pcd -%}
10
10
  {%- import('macros/printProtStack.xml.jinja2') as pps %}
11
+ {%- import('macros/printDescription.xml.jinja2') as pd %}
11
12
  {#- -#}
12
13
 
13
14
  <?xml version="1.0" encoding="UTF-8" standalone="no" ?>
@@ -18,11 +19,7 @@
18
19
  {%- if comparam_spec.long_name is not none %}
19
20
  <LONG-NAME>{{comparam_spec.long_name|e}}</LONG-NAME>
20
21
  {%- endif %}
21
- {%- if comparam_spec.description and comparam_spec.description.strip() %}
22
- <DESC>
23
- {{comparam_spec.description}}
24
- </DESC>
25
- {%- endif %}
22
+ {{pd.printDescription(comparam_spec.description)}}
26
23
  {%- if comparam_spec.admin_data is not none %}
27
24
  {{- pad.printAdminData(comparam_spec.admin_data) | indent(3) }}
28
25
  {%- endif %}
@@ -11,6 +11,7 @@
11
11
  {%- import('macros/printDOP.xml.jinja2') as pdop %}
12
12
  {%- import('macros/printUnitSpec.xml.jinja2') as pus %}
13
13
  {%- import('macros/printSpecialData.xml.jinja2') as psd %}
14
+ {%- import('macros/printDescription.xml.jinja2') as pd %}
14
15
  {#- -#}
15
16
 
16
17
  <?xml version="1.0" encoding="UTF-8" standalone="no" ?>
@@ -22,11 +23,7 @@
22
23
  {%- if comparam_subset.long_name is not none %}
23
24
  <LONG-NAME>{{comparam_subset.long_name|e}}</LONG-NAME>
24
25
  {%- endif %}
25
- {%- if comparam_subset.description and comparam_subset.description.strip() %}
26
- <DESC>
27
- {{comparam_subset.description}}
28
- </DESC>
29
- {%- endif %}
26
+ {{pd.printDescription(comparam_subset.description)}}
30
27
  {%- if comparam_subset.admin_data is not none %}
31
28
  {{- pad.printAdminData(comparam_subset.admin_data) | indent(3) }}
32
29
  {%- endif %}
@@ -5,6 +5,7 @@
5
5
 
6
6
  {%- import('macros/printElementId.xml.jinja2') as peid %}
7
7
  {%- import('macros/printSpecialData.xml.jinja2') as psd %}
8
+ {%- import('macros/printDescription.xml.jinja2') as pd %}
8
9
 
9
10
  {%- macro printCompanyData(company_data) %}
10
11
  <COMPANY-DATA ID="{{company_data.odx_id.local_id}}">
@@ -81,11 +82,7 @@
81
82
  {%- endif %}
82
83
  </XDOC>
83
84
  {%- endif %}
84
- {%- if rd.description is not none %}
85
- <DESC>
86
- {{rd.description}}
87
- </DESC>
88
- {%- endif %}
85
+ {{pd.printDescription(rd.description)}}
89
86
  </RELATED-DOC>
90
87
  {%- endfor %}
91
88
  </RELATED-DOCS>
@@ -3,6 +3,7 @@
3
3
  # SPDX-License-Identifier: MIT
4
4
  -#}
5
5
  {%- import('macros/printComparam.xml.jinja2') as pcp %}
6
+ {%- import('macros/printDescription.xml.jinja2') as pd %}
6
7
  {#- -#}
7
8
 
8
9
  {%- macro printComparamRef(cp) %}
@@ -11,27 +12,19 @@
11
12
  DOCTYPE="COMPARAM-SUBSET">
12
13
  {%- if cp.value is string %}
13
14
  <SIMPLE-VALUE>{{cp.value}}</SIMPLE-VALUE>
14
- {%- if cp.description %}
15
- <DESC>{{cp.description}}</DESC>
16
- {%- endif %}
15
+ {{ pd.printDescription(cp.description) }}
17
16
  {%- elif cp.value is iterable %}
18
17
  {%- if hasattr(cp.value, "hex") %}
19
18
  {#- the value has a hex() method. assume that is a bytes or bytestring #}
20
19
  <SIMPLE-VALUE>{{cp.value.hex().upper()}}</SIMPLE-VALUE>
21
- {%- if cp.description %}
22
- <DESC>{{cp.description}}</DESC>
23
- {%- endif %}
20
+ {{ pd.printDescription(cp.description) }}
24
21
  {%- else %}
25
22
  {{ pcp.printComplexValue(cp.value)|indent(1) }}
26
- {%- if cp.description %}
27
- <DESC>{{cp.description}}</DESC>
28
- {%- endif %}
23
+ {{ pd.printDescription(cp.description) }}
29
24
  {%- endif %}
30
25
  {%- else %}
31
26
  <SIMPLE-VALUE>{{cp.value}}</SIMPLE-VALUE>
32
- {%- if cp.description %}
33
- <DESC>{{cp.description}}</DESC>
34
- {%- endif %}
27
+ {{ pd.printDescription(cp.description) }}
35
28
  {%- endif %}
36
29
  {%- if cp.prot_stack_snref is not none %}
37
30
  <PROT-STACK-SNREF SHORT-NAME="{{cp.prot_stack_snref}}"/>
@@ -0,0 +1,153 @@
1
+ {#- -*- mode: sgml; tab-width: 1; indent-tabs-mode: nil -*-
2
+ #
3
+ # SPDX-License-Identifier: MIT
4
+ -#}
5
+
6
+ {%- import('macros/printElementId.xml.jinja2') as peid %}
7
+ {%- import('macros/printAdminData.xml.jinja2') as pad %}
8
+ {%- import('macros/printSpecialData.xml.jinja2') as psd %}
9
+ {%- import('macros/printDescription.xml.jinja2') as pd %}
10
+
11
+
12
+ {%- macro printLimit(tag_name, limit_obj) -%}
13
+ {%- if limit_obj is not none %}
14
+ <{{tag_name}}
15
+ {%- if limit_obj.interval_type is not none %}
16
+ {{- make_xml_attrib("INTERVAL-TYPE", limit_obj.interval_type.value) }}
17
+ {%- endif %}
18
+ {%- if limit_obj.value_raw is none %}
19
+ {#- #}/>
20
+ {%- else %}
21
+ {#- #}>
22
+ {%- if hasattr(limit_obj._value, 'hex') -%}
23
+ {#- bytes or bytarray limit #}
24
+ {{- limit_obj._value.hex().upper() }}
25
+ {%- else -%}
26
+ {{- limit_obj._value }}
27
+ {%- endif -%}
28
+ </{{tag_name}}>
29
+ {%- endif -%}
30
+ {%- endif -%}
31
+ {%- endmacro -%}
32
+
33
+ {%- macro printCompuInverseValue(civ) -%}
34
+ <COMPU-INVERSE-VALUE>
35
+ {%- if civ.v is not none %}
36
+ <V>{{civ.v}}</V>
37
+ {%- endif %}
38
+ {%- if civ.vt is not none %}
39
+ <VT>{{civ.vt | e}}</VT>
40
+ {%- endif %}
41
+ </COMPU-INVERSE-VALUE>
42
+ {%- endmacro -%}
43
+
44
+ {%- macro printCompuDefaultValue(cdv) -%}
45
+ <COMPU-DEFAULT-VALUE>
46
+ {%- if cdv.v is not none %}
47
+ <V>{{cdv.v}}</V>
48
+ {%- endif %}
49
+ {%- if cdv.vt is not none %}
50
+ <VT>{{cdv.vt | e}}</VT>
51
+ {%- endif %}
52
+ {%- if cdv.compu_inverse_value is not none %}
53
+ {{printCompuInverseValue(cdv.compu_inverse_value)}}
54
+ {%- endif %}
55
+ </COMPU-DEFAULT-VALUE>
56
+ {%- endmacro -%}
57
+
58
+ {%- macro printCompuScale(cs) -%}
59
+ <COMPU-SCALE>
60
+ {%- if cs.short_label is not none %}
61
+ <SHORT-LABEL>{{cs.short_label|e}}</SHORT-LABEL>
62
+ {%- endif %}
63
+ {{- pd.printDescription(cs.description)|indent(2, first=True) }}
64
+ {{- printLimit("LOWER-LIMIT", cs.lower_limit)|indent(2, first=True) }}
65
+ {{- printLimit("UPPER-LIMIT", cs.upper_limit)|indent(2, first=True) }}
66
+ {%- if cs.compu_inverse_value is not none %}
67
+ {{printCompuInverseValue(cs.compu_inverse_value)}}
68
+ {%- endif %}
69
+ {%- if cs.compu_const is not none %}
70
+ <COMPU-CONST>
71
+ {%- if cs.compu_const.v is not none %}
72
+ <V>{{cs.compu_const.v}}</V>
73
+ {%- endif %}
74
+ {%- if cs.compu_const.vt is not none %}
75
+ <VT>{{cs.compu_const.vt | e}}</VT>
76
+ {%- endif %}
77
+ </COMPU-CONST>
78
+ {%- endif %}
79
+ {%- set crc = cs.compu_rational_coeffs %}
80
+ {%- if crc is not none %}
81
+ <COMPU-RATIONAL-COEFFS>
82
+ <COMPU-NUMERATOR>
83
+ {%- for v in crc.numerators %}
84
+ <V>{{v}}</V>
85
+ {%- endfor %}
86
+ </COMPU-NUMERATOR>
87
+ {%- if crc.denominators %}
88
+ <COMPU-DENOMINATOR>
89
+ {%- for v in crc.denominators %}
90
+ <V>{{v}}</V>
91
+ {%- endfor %}
92
+ </COMPU-DENOMINATOR>
93
+ {%- endif %}
94
+ </COMPU-RATIONAL-COEFFS>
95
+ {%- endif %}
96
+ </COMPU-SCALE>
97
+ {%- endmacro -%}
98
+
99
+ {%- macro printProgCode(pc) -%}
100
+ <PROG-CODE>
101
+ <CODE-FILE>{{pc.code_file}}</CODE-FILE>
102
+ <SYNTAX>{{pc.syntax}}</SYNTAX>
103
+ {%- if pc.encryption is not none %}
104
+ <ENCRYPTION>{{pc.encryption}}</ENCRYPTION>
105
+ {%- endif %}
106
+ {%- if pc.entry_point is not none %}
107
+ <ENTRY-POINT>{{pc.entry_point}}</ENTRY-POINT>
108
+ {%- endif %}
109
+ {%- if pc.library_refs %}
110
+ <LIBRARY-REFS>
111
+ {%- for libref in pc.library_refs %}
112
+ <LIBRARY-REF ID-REF="{{libref.ref_id}}" />
113
+ {%- endfor %}
114
+ </LIBRARY-REFS>
115
+ {%- endif %}
116
+ </PROG-CODE>
117
+ {%- endmacro -%}
118
+
119
+ {%- macro printCompuMethod(cm) -%}
120
+ <COMPU-METHOD>
121
+ <CATEGORY>{{cm.category.value}}</CATEGORY>
122
+ {%- if cm.compu_internal_to_phys is not none %}
123
+ <COMPU-INTERNAL-TO-PHYS>
124
+ <COMPU-SCALES>
125
+ {%- for cs in cm.compu_internal_to_phys.compu_scales %}
126
+ {{ printCompuScale(cs) | indent(3) }}
127
+ {%- endfor %}
128
+ </COMPU-SCALES>
129
+ {%- if cm.compu_internal_to_phys.prog_code is not none %}
130
+ {{ printProgCode(cm.compu_internal_to_phys.prog_code) | indent(3) }}
131
+ {%- endif %}
132
+ {%- if cm.compu_internal_to_phys.compu_default_value is not none %}
133
+ {{ printCompuDefaultValue(cm.compu_internal_to_phys.compu_default_value) | indent(3) }}
134
+ {%- endif %}
135
+ </COMPU-INTERNAL-TO-PHYS>
136
+ {%- endif %}
137
+ {%- if cm.compu_phys_to_internal is not none %}
138
+ <COMPU-PHYS-TO-INTERNAL>
139
+ <COMPU-SCALES>
140
+ {%- for cs in cm.compu_phys_to_internal.compu_scales %}
141
+ {{ printCompuScale(cs) | indent(3) }}
142
+ {%- endfor %}
143
+ </COMPU-SCALES>
144
+ {%- if cm.compu_phys_to_internal.prog_code is not none %}
145
+ {{ printProgCode(cm.compu_phys_to_internal.prog_code) | indent(3) }}
146
+ {%- endif %}
147
+ {%- if cm.compu_phys_to_internal.compu_default_value is not none %}
148
+ {{ printCompuDefaultValue(cm.compu_phys_to_internal.compu_default_value) | indent(3) }}
149
+ {%- endif %}
150
+ </COMPU-PHYS-TO-INTERNAL>
151
+ {%- endif %}
152
+ </COMPU-METHOD>
153
+ {%- endmacro -%}
@@ -6,6 +6,9 @@
6
6
  {%- import('macros/printElementId.xml.jinja2') as peid %}
7
7
  {%- import('macros/printAdminData.xml.jinja2') as pad %}
8
8
  {%- import('macros/printSpecialData.xml.jinja2') as psd %}
9
+ {%- import('macros/printCompuMethod.xml.jinja2') as pcm %}
10
+ {%- import('macros/printDescription.xml.jinja2') as pd %}
11
+
9
12
 
10
13
  {%- macro printDiagCodedType(dct) -%}
11
14
  <DIAG-CODED-TYPE {{-make_xml_attrib("BASE-DATA-TYPE", dct.base_data_type.value)}}
@@ -30,7 +33,6 @@
30
33
  </DIAG-CODED-TYPE>
31
34
  {%- endmacro -%}
32
35
 
33
-
34
36
  {%- macro printPhysicalType(physical_type) %}
35
37
  {%- if physical_type.display_radix is not none %}
36
38
  <PHYSICAL-TYPE BASE-DATA-TYPE="{{physical_type.base_data_type.value}}" DISPLAY-RADIX="{{physical_type.display_radix.name}}" />
@@ -43,39 +45,14 @@
43
45
  {%- endif %}
44
46
  {%- endmacro -%}
45
47
 
46
- {%- macro printLimit(tag_name, limit_obj) -%}
47
- {%- if limit_obj is not none %}
48
- <{{tag_name}}
49
- {%- if limit_obj.interval_type is not none %}
50
- {{- make_xml_attrib("INTERVAL-TYPE", limit_obj.interval_type.value) }}
51
- {%- endif %}
52
- {%- if limit_obj.value_raw is none %}
53
- {#- #}/>
54
- {%- else %}
55
- {#- #}>
56
- {%- if hasattr(limit_obj._value, 'hex') -%}
57
- {#- bytes or bytarray limit #}
58
- {{- limit_obj._value.hex().upper() }}
59
- {%- else -%}
60
- {{- limit_obj._value }}
61
- {%- endif -%}
62
- </{{tag_name}}>
63
- {%- endif -%}
64
- {%- endif -%}
65
- {%- endmacro -%}
66
-
67
48
  {%- macro printScaleConstr(sc) %}
68
49
  <SCALE-CONSTR VALIDITY="{{sc.validity.value}}">
69
50
  {%- if sc.short_label is not none %}
70
51
  <SHORT-LABEL>{{sc.short_label|e}}</SHORT-LABEL>
71
52
  {%- endif %}
72
- {%- if sc.description and sc.description.strip() %}
73
- <DESC>
74
- {{sc.description}}
75
- </DESC>
76
- {%- endif %}
77
- {{printLimit("LOWER-LIMIT", sc.lower_limit) }}
78
- {{printLimit("UPPER-LIMIT", sc.upper_limit) }}
53
+ {{pd.printDescription(sc.description)}}
54
+ {{pcm.printLimit("LOWER-LIMIT", sc.lower_limit) }}
55
+ {{pcm.printLimit("UPPER-LIMIT", sc.upper_limit) }}
79
56
  </SCALE-CONSTR>
80
57
  {%- endmacro -%}
81
58
 
@@ -85,8 +62,8 @@
85
62
  {%- else %}
86
63
  <INTERNAL-CONSTR>
87
64
  {%- endif %}
88
- {{printLimit("LOWER-LIMIT", ic.lower_limit) }}
89
- {{printLimit("UPPER-LIMIT", ic.upper_limit) }}
65
+ {{pcm.printLimit("LOWER-LIMIT", ic.lower_limit) }}
66
+ {{pcm.printLimit("UPPER-LIMIT", ic.upper_limit) }}
90
67
  {%- if ic.scale_constrs %}
91
68
  <SCALE-CONSTRS>
92
69
  {%- for sc in ic.scale_constrs %}
@@ -101,105 +78,6 @@
101
78
  {%- endif %}
102
79
  {%- endmacro -%}
103
80
 
104
- {%- macro printCompuMethod(cm) -%}
105
- <COMPU-METHOD>
106
- <CATEGORY>{{cm.category}}</CATEGORY>
107
- {%- if cm.category == "TEXTTABLE" %}
108
- <COMPU-INTERNAL-TO-PHYS>
109
- <COMPU-SCALES>
110
- {%- for cs in cm.internal_to_phys %}
111
- <COMPU-SCALE>
112
- {%- if cs.short_label and cs.short_label.strip() %}
113
- <SHORT-LABEL>{{cs.short_label|e}}</SHORT-LABEL>
114
- {%- endif %}
115
- {%- if cs.description and cs.description.strip() %}
116
- <DESC>
117
- {{cs.description}}
118
- </DESC>
119
- {%- endif %}
120
- {{printLimit("LOWER-LIMIT", cs.lower_limit) }}
121
- {{printLimit("UPPER-LIMIT", cs.upper_limit) }}
122
- {%- if cs.compu_inverse_value is not none %}
123
- <COMPU-INVERSE-VALUE>
124
- <V>{{cs.compu_inverse_value}}</V>
125
- </COMPU-INVERSE-VALUE>
126
- {%- endif %}
127
- <COMPU-CONST>
128
- <VT>{{cs.compu_const | e}}</VT>
129
- </COMPU-CONST>
130
- </COMPU-SCALE>
131
- {%- endfor %}
132
- </COMPU-SCALES>
133
- {%- if cm.compu_default_value is not none %}
134
- <COMPU-DEFAULT-VALUE>
135
- <VT>{{cm.compu_default_value.compu_const}}</VT>
136
- {%- if cm.compu_default_value.compu_inverse_value is not none %}
137
- <COMPU-INVERSE-VALUE>
138
- <V>{{cm.compu_default_value.compu_inverse_value}}</V>
139
- </COMPU-INVERSE-VALUE>
140
- {%- endif %}
141
- </COMPU-DEFAULT-VALUE>
142
- {%- endif %}
143
- </COMPU-INTERNAL-TO-PHYS>
144
- {%- elif cm.category == "LINEAR" %}
145
- <COMPU-INTERNAL-TO-PHYS>
146
- <COMPU-SCALES>
147
- <COMPU-SCALE>
148
- {{printLimit("LOWER-LIMIT", cm.internal_lower_limit) }}
149
- {{printLimit("UPPER-LIMIT", cm.internal_upper_limit) }}
150
- <COMPU-RATIONAL-COEFFS>
151
- <COMPU-NUMERATOR>
152
- <V>{{cm.offset}}</V>
153
- <V>{{cm.factor}}</V>
154
- </COMPU-NUMERATOR>
155
- {%- if cm.denominator != 1 %}
156
- <COMPU-DENOMINATOR>
157
- <V>{{cm.denominator}}</V>
158
- </COMPU-DENOMINATOR>
159
- {%- endif %}
160
- </COMPU-RATIONAL-COEFFS>
161
- </COMPU-SCALE>
162
- </COMPU-SCALES>
163
- </COMPU-INTERNAL-TO-PHYS>
164
- {%- elif cm.category == "SCALE-LINEAR" %}
165
- <COMPU-INTERNAL-TO-PHYS>
166
- <COMPU-SCALES>
167
- {%- for lm in cm.linear_methods %}
168
- <COMPU-SCALE>
169
- {{printLimit("LOWER-LIMIT", lm.internal_lower_limit) }}
170
- {{printLimit("UPPER-LIMIT", lm.internal_upper_limit) }}
171
- <COMPU-RATIONAL-COEFFS>
172
- <COMPU-NUMERATOR>
173
- <V>{{lm.offset}}</V>
174
- <V>{{lm.factor}}</V>
175
- </COMPU-NUMERATOR>
176
- {%- if lm.denominator != 1 %}
177
- <COMPU-DENOMINATOR>
178
- <V>{{lm.denominator}}</V>
179
- </COMPU-DENOMINATOR>
180
- {%- endif %}
181
- </COMPU-RATIONAL-COEFFS>
182
- </COMPU-SCALE>
183
- {%- endfor %}
184
- </COMPU-SCALES>
185
- </COMPU-INTERNAL-TO-PHYS>
186
- {%- elif cm.category == "TAB-INTP" %}
187
- <COMPU-INTERNAL-TO-PHYS>
188
- <COMPU-SCALES>
189
- {%- for idx in range( cm.internal_points | length ) %}
190
- <COMPU-SCALE>
191
- <LOWER-LIMIT>{{ cm.internal_points[idx] }}</LOWER-LIMIT>
192
- <COMPU-CONST>
193
- <V>{{ cm.physical_points[idx] }}</V>
194
- </COMPU-CONST>
195
- </COMPU-SCALE>
196
- {%- endfor %}
197
- </COMPU-SCALES>
198
- </COMPU-INTERNAL-TO-PHYS>
199
- {%- endif %}
200
- </COMPU-METHOD>
201
- {%- endmacro -%}
202
-
203
81
  {%- macro printDopBaseAttribs(dop) %}
204
82
  {{- make_xml_attrib("ID", dop.odx_id.local_id) }}
205
83
  {{- make_xml_attrib("OID", dop.oid) }}
@@ -225,7 +103,7 @@
225
103
  {%- macro printDataObjectProp(dop) %}
226
104
  <DATA-OBJECT-PROP {{- printDopBaseAttribs(dop) }}>
227
105
  {{- printDopBaseSubtags(dop) }}
228
- {{- printCompuMethod(dop.compu_method)|indent(1) }}
106
+ {{- pcm.printCompuMethod(dop.compu_method)|indent(1) }}
229
107
  {{- printDiagCodedType(dop.diag_coded_type)|indent(1) }}
230
108
  {{- printPhysicalType(dop.physical_type)|indent(1) }}
231
109
  {%- if dop.internal_constr %}
@@ -246,7 +124,7 @@
246
124
  {{- printDopBaseSubtags(dop)|indent(1) }}
247
125
  {{- printDiagCodedType(dop.diag_coded_type)|indent(1) }}
248
126
  {{- printPhysicalType(dop.physical_type)|indent(1) }}
249
- {{- printCompuMethod(dop.compu_method)|indent(1) }}
127
+ {{- pcm.printCompuMethod(dop.compu_method)|indent(1) }}
250
128
  <DTCS>
251
129
  {%- for dtc in dop.dtcs_raw %}
252
130
  {%- if hasattr(dtc, "ref_id") %}
@@ -0,0 +1,18 @@
1
+ {#- -*- mode: sgml; tab-width: 1; sgml-basic-offset: 1; indent-tabs-mode: nil -*-
2
+ #
3
+ # SPDX-License-Identifier: MIT
4
+ -#}
5
+
6
+ {%- macro printDescription(desc) %}
7
+ {%- if desc is not none %}
8
+ <DESC {{make_xml_attrib("TI", desc.text_identifier)}}>{{desc.text}}
9
+ {%- if desc.external_docs %}
10
+ <EXTERNAL-DOCS>
11
+ {%- for ed in desc.external_docs %}
12
+ <EXTERNAL-DOC HREF="{{ed}}" />
13
+ {%- endfor %}
14
+ </EXTERNAL-DOCS>
15
+ {%- endif -%}
16
+ </DESC>
17
+ {%- endif %}
18
+ {%- endmacro %}
@@ -3,12 +3,12 @@
3
3
  # SPDX-License-Identifier: MIT
4
4
  -#}
5
5
 
6
+ {%- import('macros/printDescription.xml.jinja2') as pd %}
7
+
6
8
  {%- macro printElementIdSubtags(obj) -%}
7
9
  <SHORT-NAME>{{ obj.short_name }}</SHORT-NAME>
8
10
  {%- if obj.long_name %}
9
11
  <LONG-NAME>{{ obj.long_name|e }}</LONG-NAME>
10
12
  {%- endif %}
11
- {%- if obj.description %}
12
- <DESC>{{ obj.description }}</DESC>
13
- {%- endif %}
13
+ {{- pd.printDescription(obj.description) }}
14
14
  {%- endmacro -%}
@@ -4,6 +4,7 @@
4
4
  -#}
5
5
 
6
6
  {%- import('macros/printElementId.xml.jinja2') as peid %}
7
+ {%- import('macros/printCompuMethod.xml.jinja2') as pcm %}
7
8
  {%- import('macros/printDOP.xml.jinja2') as pdop %}
8
9
 
9
10
  {%- macro printMux(mux) %}
@@ -41,8 +42,8 @@
41
42
  {%- if case.structure_snref is not none %}
42
43
  <STRUCTURE-SNREF SHORT_NAME="{{case.structure_snref}}"/>
43
44
  {%- endif %}
44
- {{ pdop.printLimit("LOWER-LIMIT", case.lower_limit) }}
45
- {{ pdop.printLimit("UPPER-LIMIT", case.upper_limit) }}
45
+ {{ pcm.printLimit("LOWER-LIMIT", case.lower_limit) }}
46
+ {{ pcm.printLimit("UPPER-LIMIT", case.upper_limit) }}
46
47
  </CASE>
47
48
  {%- endfor %}
48
49
  </CASES>
@@ -5,6 +5,7 @@
5
5
 
6
6
  {%- import('macros/printElementId.xml.jinja2') as peid %}
7
7
  {%- import('macros/printSpecialData.xml.jinja2') as psd %}
8
+ {%- import('macros/printDescription.xml.jinja2') as pd %}
8
9
 
9
10
  {%- macro printTable(table) %}
10
11
  <TABLE ID="{{table.odx_id.local_id}}"
@@ -21,9 +22,7 @@
21
22
  {%- if table_row.long_name %}
22
23
  <LONG-NAME>{{table_row.long_name|e}}</LONG-NAME>
23
24
  {%- endif %}
24
- {%- if table_row.description %}
25
- <DESC>{{table_row.description}}</DESC>
26
- {%- endif %}
25
+ {{ pd.printDescription(table_row.description) }}
27
26
  <KEY>{{table_row.key|e}}</KEY>
28
27
  {%- if table_row.dop_ref %}
29
28
  <DATA-OBJECT-PROP-REF ID-REF="{{ table_row.dop_ref.ref_id }}" />
odxtools/unit.py CHANGED
@@ -1,17 +1,15 @@
1
1
  # SPDX-License-Identifier: MIT
2
2
  from dataclasses import dataclass
3
- from typing import TYPE_CHECKING, Any, Dict, List, Optional
3
+ from typing import Any, Dict, List, Optional
4
4
  from xml.etree import ElementTree
5
5
 
6
6
  from .element import IdentifiableElement
7
7
  from .exceptions import odxassert, odxrequire
8
8
  from .odxlink import OdxDocFragment, OdxLinkDatabase, OdxLinkId, OdxLinkRef
9
9
  from .physicaldimension import PhysicalDimension
10
+ from .snrefcontext import SnRefContext
10
11
  from .utils import dataclass_fields_asdict
11
12
 
12
- if TYPE_CHECKING:
13
- from .diaglayer import DiagLayer
14
-
15
13
 
16
14
  @dataclass
17
15
  class Unit(IdentifiableElement):
@@ -104,5 +102,5 @@ class Unit(IdentifiableElement):
104
102
  f"The physical_dimension_ref must be resolved to a PhysicalDimension."
105
103
  f" {self.physical_dimension_ref} referenced {self._physical_dimension}")
106
104
 
107
- def _resolve_snrefs(self, diag_layer: "DiagLayer") -> None:
105
+ def _resolve_snrefs(self, context: SnRefContext) -> None:
108
106
  pass
odxtools/unitgroup.py CHANGED
@@ -1,19 +1,17 @@
1
1
  # SPDX-License-Identifier: MIT
2
2
  from dataclasses import dataclass
3
3
  from enum import Enum
4
- from typing import TYPE_CHECKING, Any, Dict, List, Optional, cast
4
+ from typing import Any, Dict, List, Optional, cast
5
5
  from xml.etree import ElementTree
6
6
 
7
7
  from .element import NamedElement
8
8
  from .exceptions import odxraise, odxrequire
9
9
  from .nameditemlist import NamedItemList
10
10
  from .odxlink import OdxDocFragment, OdxLinkDatabase, OdxLinkId, OdxLinkRef
11
+ from .snrefcontext import SnRefContext
11
12
  from .unit import Unit
12
13
  from .utils import dataclass_fields_asdict
13
14
 
14
- if TYPE_CHECKING:
15
- from .diaglayer import DiagLayer
16
-
17
15
 
18
16
  class UnitGroupCategory(Enum):
19
17
  COUNTRY = "COUNTRY"
@@ -57,7 +55,7 @@ class UnitGroup(NamedElement):
57
55
  def _resolve_odxlinks(self, odxlinks: OdxLinkDatabase) -> None:
58
56
  self._units = NamedItemList[Unit]([odxlinks.resolve(ref) for ref in self.unit_refs])
59
57
 
60
- def _resolve_snrefs(self, diag_layer: "DiagLayer") -> None:
58
+ def _resolve_snrefs(self, context: SnRefContext) -> None:
61
59
  pass
62
60
 
63
61
  @property
odxtools/unitspec.py CHANGED
@@ -1,19 +1,16 @@
1
1
  # SPDX-License-Identifier: MIT
2
2
  from dataclasses import dataclass
3
- from typing import TYPE_CHECKING, Any, Dict, List, Union
3
+ from typing import Any, Dict, List, Union
4
4
  from xml.etree import ElementTree
5
5
 
6
- from .createsdgs import create_sdgs_from_et
7
6
  from .nameditemlist import NamedItemList
8
7
  from .odxlink import OdxDocFragment, OdxLinkDatabase, OdxLinkId
9
8
  from .physicaldimension import PhysicalDimension
9
+ from .snrefcontext import SnRefContext
10
10
  from .specialdatagroup import SpecialDataGroup
11
11
  from .unit import Unit
12
12
  from .unitgroup import UnitGroup
13
13
 
14
- if TYPE_CHECKING:
15
- from .diaglayer import DiagLayer
16
-
17
14
 
18
15
  @dataclass
19
16
  class UnitSpec:
@@ -49,7 +46,9 @@ class UnitSpec:
49
46
  PhysicalDimension.from_et(el, doc_frags)
50
47
  for el in et_element.iterfind("PHYSICAL-DIMENSIONS/PHYSICAL-DIMENSION")
51
48
  ]
52
- sdgs = create_sdgs_from_et(et_element.find("SDGS"), doc_frags)
49
+ sdgs = [
50
+ SpecialDataGroup.from_et(sdge, doc_frags) for sdge in et_element.iterfind("SDGS/SDG")
51
+ ]
53
52
 
54
53
  return UnitSpec(
55
54
  unit_groups=unit_groups,
@@ -76,10 +75,10 @@ class UnitSpec:
76
75
  for sdg in self.sdgs:
77
76
  sdg._resolve_odxlinks(odxlinks)
78
77
 
79
- def _resolve_snrefs(self, diag_layer: "DiagLayer") -> None:
78
+ def _resolve_snrefs(self, context: SnRefContext) -> None:
80
79
  for unit in self.units:
81
- unit._resolve_snrefs(diag_layer)
80
+ unit._resolve_snrefs(context)
82
81
  for group in self.unit_groups:
83
- group._resolve_snrefs(diag_layer)
82
+ group._resolve_snrefs(context)
84
83
  for sdg in self.sdgs:
85
- sdg._resolve_snrefs(diag_layer)
84
+ sdg._resolve_snrefs(context)
odxtools/utils.py CHANGED
@@ -1,32 +1,7 @@
1
1
  # SPDX-License-Identifier: MIT
2
2
  import dataclasses
3
3
  import re
4
- from typing import Any, Dict, Optional
5
- from xml.etree import ElementTree
6
-
7
-
8
- def create_description_from_et(et_element: Optional[ElementTree.Element],) -> Optional[str]:
9
- """Read a description tag.
10
-
11
- The description is located underneath the DESC tag of an an ODX
12
- element."""
13
-
14
- if et_element is None:
15
- return None
16
-
17
- if et_element.tag != "DESC":
18
- raise TypeError(f"Attempted to extract an ODX description from a "
19
- f"'{et_element.tag}' XML node. (Must be a 'DESC' node!)")
20
-
21
- # Extract the contents of the tag as a XHTML string.
22
- raw_string = et_element.text or ""
23
- for e in et_element:
24
- raw_string += ElementTree.tostring(e, encoding="unicode")
25
-
26
- # remove white spaces at the beginning and at the end of lines
27
- stripped_lines = [x.strip() for x in raw_string.split("\n")]
28
-
29
- return "\n".join(stripped_lines).strip()
4
+ from typing import Any, Dict
30
5
 
31
6
 
32
7
  def dataclass_fields_asdict(obj: Any) -> Dict[str, Any]:
odxtools/version.py CHANGED
@@ -12,5 +12,5 @@ __version__: str
12
12
  __version_tuple__: VERSION_TUPLE
13
13
  version_tuple: VERSION_TUPLE
14
14
 
15
- __version__ = version = '7.1.1'
16
- __version_tuple__ = version_tuple = (7, 1, 1)
15
+ __version__ = version = '7.3.0'
16
+ __version_tuple__ = version_tuple = (7, 3, 0)