Skip to content

Commit acafa84

Browse files
committed
Merge branch 'tools-ynl-decode-link-types-present-in-tests'
Jakub Kicinski says: ==================== tools: ynl: decode link types present in tests Using a kernel built for the net selftest target to run drivers/net tests currently fails, because the net kernel automatically spawns a handful of tunnel devices which YNL can't decode. Fill in those missing link types in rt_link. We need to extend subset support a bit for it to work. v1: https://lore.kernel.org/20250105012523.1722231-1-kuba@kernel.org ==================== Link: https://patch.msgid.link/20250107022820.2087101-1-kuba@kernel.org Signed-off-by: Jakub Kicinski <kuba@kernel.org>
2 parents d8c2e5f + 6ffdbb9 commit acafa84

File tree

4 files changed

+152
-40
lines changed

4 files changed

+152
-40
lines changed

Documentation/netlink/specs/rt_link.yaml

Lines changed: 87 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1825,6 +1825,48 @@ attribute-sets:
18251825
-
18261826
name: erspan-hwid
18271827
type: u16
1828+
-
1829+
name: linkinfo-vti-attrs
1830+
name-prefix: ifla-vti-
1831+
attributes:
1832+
-
1833+
name: link
1834+
type: u32
1835+
-
1836+
name: ikey
1837+
type: u32
1838+
-
1839+
name: okey
1840+
type: u32
1841+
-
1842+
name: local
1843+
type: binary
1844+
display-hint: ipv4
1845+
-
1846+
name: remote
1847+
type: binary
1848+
display-hint: ipv4
1849+
-
1850+
name: fwmark
1851+
type: u32
1852+
-
1853+
name: linkinfo-vti6-attrs
1854+
subset-of: linkinfo-vti-attrs
1855+
attributes:
1856+
-
1857+
name: link
1858+
-
1859+
name: ikey
1860+
-
1861+
name: okey
1862+
-
1863+
name: local
1864+
display-hint: ipv6
1865+
-
1866+
name: remote
1867+
display-hint: ipv6
1868+
-
1869+
name: fwmark
18281870
-
18291871
name: linkinfo-geneve-attrs
18301872
name-prefix: ifla-geneve-
@@ -1941,6 +1983,42 @@ attribute-sets:
19411983
-
19421984
name: fwmark
19431985
type: u32
1986+
-
1987+
name: linkinfo-ip6tnl-attrs
1988+
subset-of: linkinfo-iptun-attrs
1989+
attributes:
1990+
-
1991+
name: link
1992+
-
1993+
name: local
1994+
display-hint: ipv6
1995+
-
1996+
name: remote
1997+
display-hint: ipv6
1998+
-
1999+
name: ttl
2000+
-
2001+
name: encap-limit
2002+
-
2003+
name: flowinfo
2004+
-
2005+
name: flags
2006+
# ip6tnl unlike ipip and sit has 32b flags
2007+
type: u32
2008+
-
2009+
name: proto
2010+
-
2011+
name: encap-type
2012+
-
2013+
name: encap-flags
2014+
-
2015+
name: encap-sport
2016+
-
2017+
name: encap-dport
2018+
-
2019+
name: collect-metadata
2020+
-
2021+
name: fwmark
19442022
-
19452023
name: linkinfo-tun-attrs
19462024
name-prefix: ifla-tun-
@@ -2201,6 +2279,9 @@ sub-messages:
22012279
-
22022280
value: ipip
22032281
attribute-set: linkinfo-iptun-attrs
2282+
-
2283+
value: ip6tnl
2284+
attribute-set: linkinfo-ip6tnl-attrs
22042285
-
22052286
value: sit
22062287
attribute-set: linkinfo-iptun-attrs
@@ -2213,6 +2294,12 @@ sub-messages:
22132294
-
22142295
value: vrf
22152296
attribute-set: linkinfo-vrf-attrs
2297+
-
2298+
value: vti
2299+
attribute-set: linkinfo-vti-attrs
2300+
-
2301+
value: vti6
2302+
attribute-set: linkinfo-vti6-attrs
22162303
-
22172304
value: netkit
22182305
attribute-set: linkinfo-netkit-attrs

tools/net/ynl/lib/nlspec.py

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -219,7 +219,10 @@ def __init__(self, family, yaml):
219219
else:
220220
real_set = family.attr_sets[self.subset_of]
221221
for elem in self.yaml['attributes']:
222-
attr = real_set[elem['name']]
222+
real_attr = real_set[elem['name']]
223+
combined_elem = real_attr.yaml | elem
224+
attr = self.new_attr(combined_elem, real_attr.value)
225+
223226
self.attrs[attr.name] = attr
224227
self.attrs_by_val[attr.value] = attr
225228

tools/net/ynl/lib/ynl.py

Lines changed: 39 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -733,41 +733,45 @@ def _decode(self, attrs, space, outer_attrs = None):
733733
self._rsp_add(rsp, attr_name, None, self._decode_unknown(attr))
734734
continue
735735

736-
if attr_spec["type"] == 'nest':
737-
subdict = self._decode(NlAttrs(attr.raw), attr_spec['nested-attributes'], search_attrs)
738-
decoded = subdict
739-
elif attr_spec["type"] == 'string':
740-
decoded = attr.as_strz()
741-
elif attr_spec["type"] == 'binary':
742-
decoded = self._decode_binary(attr, attr_spec)
743-
elif attr_spec["type"] == 'flag':
744-
decoded = True
745-
elif attr_spec.is_auto_scalar:
746-
decoded = attr.as_auto_scalar(attr_spec['type'], attr_spec.byte_order)
747-
elif attr_spec["type"] in NlAttr.type_formats:
748-
decoded = attr.as_scalar(attr_spec['type'], attr_spec.byte_order)
749-
if 'enum' in attr_spec:
750-
decoded = self._decode_enum(decoded, attr_spec)
751-
elif attr_spec.display_hint:
752-
decoded = self._formatted_string(decoded, attr_spec.display_hint)
753-
elif attr_spec["type"] == 'indexed-array':
754-
decoded = self._decode_array_attr(attr, attr_spec)
755-
elif attr_spec["type"] == 'bitfield32':
756-
value, selector = struct.unpack("II", attr.raw)
757-
if 'enum' in attr_spec:
758-
value = self._decode_enum(value, attr_spec)
759-
selector = self._decode_enum(selector, attr_spec)
760-
decoded = {"value": value, "selector": selector}
761-
elif attr_spec["type"] == 'sub-message':
762-
decoded = self._decode_sub_msg(attr, attr_spec, search_attrs)
763-
elif attr_spec["type"] == 'nest-type-value':
764-
decoded = self._decode_nest_type_value(attr, attr_spec)
765-
else:
766-
if not self.process_unknown:
767-
raise Exception(f'Unknown {attr_spec["type"]} with name {attr_spec["name"]}')
768-
decoded = self._decode_unknown(attr)
769-
770-
self._rsp_add(rsp, attr_spec["name"], attr_spec.is_multi, decoded)
736+
try:
737+
if attr_spec["type"] == 'nest':
738+
subdict = self._decode(NlAttrs(attr.raw), attr_spec['nested-attributes'], search_attrs)
739+
decoded = subdict
740+
elif attr_spec["type"] == 'string':
741+
decoded = attr.as_strz()
742+
elif attr_spec["type"] == 'binary':
743+
decoded = self._decode_binary(attr, attr_spec)
744+
elif attr_spec["type"] == 'flag':
745+
decoded = True
746+
elif attr_spec.is_auto_scalar:
747+
decoded = attr.as_auto_scalar(attr_spec['type'], attr_spec.byte_order)
748+
elif attr_spec["type"] in NlAttr.type_formats:
749+
decoded = attr.as_scalar(attr_spec['type'], attr_spec.byte_order)
750+
if 'enum' in attr_spec:
751+
decoded = self._decode_enum(decoded, attr_spec)
752+
elif attr_spec.display_hint:
753+
decoded = self._formatted_string(decoded, attr_spec.display_hint)
754+
elif attr_spec["type"] == 'indexed-array':
755+
decoded = self._decode_array_attr(attr, attr_spec)
756+
elif attr_spec["type"] == 'bitfield32':
757+
value, selector = struct.unpack("II", attr.raw)
758+
if 'enum' in attr_spec:
759+
value = self._decode_enum(value, attr_spec)
760+
selector = self._decode_enum(selector, attr_spec)
761+
decoded = {"value": value, "selector": selector}
762+
elif attr_spec["type"] == 'sub-message':
763+
decoded = self._decode_sub_msg(attr, attr_spec, search_attrs)
764+
elif attr_spec["type"] == 'nest-type-value':
765+
decoded = self._decode_nest_type_value(attr, attr_spec)
766+
else:
767+
if not self.process_unknown:
768+
raise Exception(f'Unknown {attr_spec["type"]} with name {attr_spec["name"]}')
769+
decoded = self._decode_unknown(attr)
770+
771+
self._rsp_add(rsp, attr_spec["name"], attr_spec.is_multi, decoded)
772+
except:
773+
print(f"Error decoding '{attr_spec.name}' from '{space}'")
774+
raise
771775

772776
return rsp
773777

tools/net/ynl/ynl-gen-c.py

Lines changed: 22 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -79,6 +79,20 @@ def __init__(self, family, attr_set, attr, value):
7979
self.enum_name = None
8080
delattr(self, "enum_name")
8181

82+
def _get_real_attr(self):
83+
# if the attr is for a subset return the "real" attr (just one down, does not recurse)
84+
return self.family.attr_sets[self.attr_set.subset_of][self.name]
85+
86+
def set_request(self):
87+
self.request = True
88+
if self.attr_set.subset_of:
89+
self._get_real_attr().set_request()
90+
91+
def set_reply(self):
92+
self.reply = True
93+
if self.attr_set.subset_of:
94+
self._get_real_attr().set_reply()
95+
8296
def get_limit(self, limit, default=None):
8397
value = self.checks.get(limit, default)
8498
if value is None:
@@ -106,6 +120,10 @@ def resolve(self):
106120
enum_name = f"{self.attr_set.name_prefix}{self.name}"
107121
self.enum_name = c_upper(enum_name)
108122

123+
if self.attr_set.subset_of:
124+
if self.checks != self._get_real_attr().checks:
125+
raise Exception("Overriding checks not supported by codegen, yet")
126+
109127
def is_multi_val(self):
110128
return None
111129

@@ -1119,17 +1137,17 @@ def _load_attr_use(self):
11191137
for _, struct in self.pure_nested_structs.items():
11201138
if struct.request:
11211139
for _, arg in struct.member_list():
1122-
arg.request = True
1140+
arg.set_request()
11231141
if struct.reply:
11241142
for _, arg in struct.member_list():
1125-
arg.reply = True
1143+
arg.set_reply()
11261144

11271145
for root_set, rs_members in self.root_sets.items():
11281146
for attr, spec in self.attr_sets[root_set].items():
11291147
if attr in rs_members['request']:
1130-
spec.request = True
1148+
spec.set_request()
11311149
if attr in rs_members['reply']:
1132-
spec.reply = True
1150+
spec.set_reply()
11331151

11341152
def _load_global_policy(self):
11351153
global_set = set()

0 commit comments

Comments
 (0)