smc-tools/5-a60b96821be3.patch
Čestmír Kalina 3fae52deba smc-tools: smc_rnics is not listing the NetH/NetD cards inside the guest
Resolves: RHEL-159089

Signed-off-by: Čestmír Kalina <ckalina@redhat.com>
2026-08-04 11:57:43 +02:00

141 lines
5.1 KiB
Diff

commit a60b96821be3fadaf89d643072488e4762b28d10
Author: Halil Pasic <pasic@linux.ibm.com>
Date: Tue Dec 2 15:25:40 2025 +0100
smc_rnics: fix regression when PFT not available
Before commit 0b965ae ("smc_rnics: Add support for Network Express RNIC
in smc_rnics") the device type detection was based on PCI vendor and
device ID. The aforementioned commit switched smc_rnics to doing
the device type detection primarily on PCI function type (PFT), which
is in general a sound thing to do.
In certain virtualized environments however (most notably QEMU+KVM) PFT
is generally not available, and even for passed through devices, as of
now PFT 0 is reported regardless of the actual PFT as seen by G1 (i.e.
LPAR). And that leads to not detecting passed through rnics as such, and
generally displaying an empty list when smc_rnics is called with no
parameters, even in a presence of rnics to display.
The patch also degraded the ability of the script to handle unknown
vendor id 0x15b3 devices gracefully. This can be relevant if a not
enlightened version of the script is used on new hardware.
Adding a warning about the surprise PFT 0 does not seem to be a good
idea, because there are PCI devices which are readily available on
s390x and for which PFT 0 is just expected: most notably virtio-pci, and
frankly it isn't all that helpful either.
On the other hand, using the PFT, when available and suitable, is still
considered superior.
Use the old PCI vendor and device ID based logic as a fall back when PFT
is not available or not known.
With this the regressions introduced by commit 0b965ae ("smc_rnics: Add
support for Network Express RNIC in smc_rnics") shall be gone.
While at it fix the handling of ports too. The call to
set_RoCE_dev_and_port in the loop that iterates over network interfaces
does not make sense; and 'RoCE Express' needs special handling as a
device that has multiple ports and interfaces per PCI function
regardless of the value the variable 'rawIDs'.
I don't quite understand why grabbing port from the interface's dev_port
attribute is a bad idea. That precedence was established by 05d1c7e
("smc_rnics: Fix RoCE Express2 port display"). My best guess is that
dev_port is only valid if a PCI function can interact with multiple
physical ports, which is not the case with RoCE Express2 and higher. So
I am leaving that as is.
Fixes: commit 0b965ae ("smc_rnics: Add support for Network Express RNIC in smc_rnics")
Reviewed-by: Sidraya Jayagond <sidraya@linux.ibm.com>
Signed-off-by: Halil Pasic <pasic@linux.ibm.com>
diff --git a/smc_rnics b/smc_rnics
index 70b6f69..279da22 100755
--- a/smc_rnics
+++ b/smc_rnics
@@ -144,6 +144,26 @@ function set_by_firmware_lvl() {
set_RoCE_dev_and_port $name;
}
+function set_by_pciid(){
+
+ case "$vend" in
+ "0x1014" ) # IBM
+ case "$id" in
+ "0x04ed") dev_type="ISM";
+ int="n/a";;
+ esac;;
+ "0x15b3" ) # Mellanox
+ case "$id" in
+ "0x1003" | \
+ "0x1004") dev_type="RoCE_Express";
+ multiport_f=1;;
+ "0x1016") set_RoCE_dev_and_port "RoCE_Express2";;
+ "0x101e") set_by_firmware_lvl;;
+ *) set_RoCE_dev_and_port "Mlx_$id";;
+ esac;;
+ esac
+}
+
function print_rnics() {
# iterate over slots, as powered-off devices won't show elsewhere
for fid in `ls -1 /sys/bus/pci/slots`; do
@@ -188,12 +208,15 @@ function print_rnics() {
dev_type="${vend#0x}:${id#0x}";
pft=`cat pft`;
vfn=`cat vfn`;
+ multiport_f=0;
if [ $rawIDs -eq 0 ]; then
+ # prefer PFT for disamgibuating devices
case "$pft" in
"0x05") dev_type="ISM";
int="n/a";
set_RoCE_pft_and_vfn "$pft" "$vfn";;
"0x02") dev_type="RoCE_Express";
+ multiport_f=1;
set_RoCE_pft_and_vfn "$pft" "$vfn";;
"0x0a") set_by_firmware_lvl;
set_RoCE_pft_and_vfn "$pft" "$vfn";;
@@ -201,15 +224,20 @@ function print_rnics() {
"0x0f") set_RoCE_dev_and_port "Network_Express";
set_RoCE_pft_and_vfn "$pft" "$vfn";;
*)
+ # but if that fails go via the pci IDs
+ set_by_pciid
# For unknown PCI vendors, determine VF flag based on VFN value.
# This ensures consistent handling even for unrecognized vendor devices
- [ $all -eq 0 ] && continue
+ [ "$dev_type" = "${vend#0x}:${id#0x}" ] && [ $all -eq 0 ] && continue
if (( 16#${vfn#0x} != 0 )); then
vfn="y";
else
vfn="n";
fi;;
- esac
+ esac
+ else
+ set_RoCE_dev_and_port "$dev_type";
+ [ "0x15b3" = "$vend" ] && [ "0x1004" = "$id" ] && multiport_f=1;
fi
pchid="`cat pchid | sed 's/^0x//'`";
pnetids="`cat util_string | sed 's/\x0/\x40/g' | iconv -f IBM-1047 -t ASCII`";
@@ -221,10 +249,10 @@ function print_rnics() {
print_rnic;
continue;
fi
- # one device can have multiple interfaces (one per port)
for int in $interfaces; do
+ # one device can have multiple interfaces (one per port)
cd /sys/bus/pci/devices/$addr/net/$int;
- if [ "$dev_type" == "RoCE_Express" ] && [ -e dev_port ]; then
+ if [ $multiport_f -eq 1 ] && [ -e dev_port ]; then
port=`cat dev_port`;
fi
print_rnic;
--
2.54.0