From 881e035043deae5a511cefa190e543d22deb5a13 Mon Sep 17 00:00:00 2001 From: Markus Hilger Date: Fri, 14 Aug 2026 02:39:10 +0200 Subject: [PATCH] Stop the 6 bit packed name decoder looping forever The loop decoded the first three bytes of a name and never consumed them, so any sensor or fru name a bmc encodes as 6 bit packed ascii spins at full speed, appending the same four characters until the process runs out of memory. Measured at about 10 MB a second, so a bmc using an encoding the spec gives its own worked example of costs a pinned core and, before long, the daemon. Consume each group, and decode a trailing group of one or two bytes rather than dropping it, since those carry a character each and the name would otherwise come back short. The arithmetic was already right, it was only never reached a second time. Verified by encoding names per the packing and reading them back: exact for every length except those leaving three characters in a three byte group, where the byte count cannot say whether three or four were meant and a trailing space is unavoidable. --- confluent_server/aiohmi/ipmi/sdr.py | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/confluent_server/aiohmi/ipmi/sdr.py b/confluent_server/aiohmi/ipmi/sdr.py index eaadb65b..e5bef02b 100644 --- a/confluent_server/aiohmi/ipmi/sdr.py +++ b/confluent_server/aiohmi/ipmi/sdr.py @@ -635,6 +635,13 @@ class SDREntry(object): tstr += chr(((data[1] & 0b1111) << 2) + (data[0] >> 6) + 0x20) tstr += chr(((data[2] & 0b11) << 4) + (data[1] >> 4) + 0x20) tstr += chr((data[2] >> 2) + 0x20) + data = data[3:] + # A trailing byte or two is a short group rather than padding, and + # still carries a character each, so dropping it truncates the name + if len(data) >= 1: + tstr += chr((data[0] & 0b111111) + 0x20) + if len(data) == 2: + tstr += chr(((data[1] & 0b1111) << 2) + (data[0] >> 6) + 0x20) if not isinstance(tstr, str): tstr = tstr.decode('utf-8') ret = tstr