History

scripts/gdb: fix lx-dmesg when CONFIG_PRINTK_CALLER is set

When CONFIG_PRINTK_CALLER is set, struct printk_log contains an additional member caller_id. This affects the offset of the log text. Account for this by using the type information from gdb to determine all the offsets instead of using hardcoded values. This fixes following error: (gdb) lx-dmesg Python Exception <class 'ValueError'> embedded null character: Error occurred in Python command: embedded null character The read_u* utility functions now take an offset argument to make them easier to use.

Joel Colledge committed 7 years ago

Commit ca210ba1 parent 96c804a2 files · +25 −16Browse files

Unified · Split

2 files
  1. scripts/gdb/linux/dmesg.py +12 −4
  2. scripts/gdb/linux/utils.py +13 −12
scripts/gdb/linux/dmesg.py+12−4
@@ -16,6 +16,8 @@ import sys · 15 unmodified lines
1616
1717 from linux import utils
1818
19+printk_log_type = utils.CachedType("struct printk_log")
20+
1921
2022 class LxDmesg(gdb.Command):
2123 """Print Linux kernel log buffer."""
@@ -42,9 +44,14 @@ class LxDmesg(gdb.Command): · 20 unmodified lines
4244 b = utils.read_memoryview(inf, log_buf_addr, log_next_idx)
4345 log_buf = a.tobytes() + b.tobytes()
4446
47+ length_offset = printk_log_type.get_type()['len'].bitpos // 8
48+ text_len_offset = printk_log_type.get_type()['text_len'].bitpos // 8
49+ time_stamp_offset = printk_log_type.get_type()['ts_nsec'].bitpos // 8
50+ text_offset = printk_log_type.get_type().sizeof
51+
4552 pos = 0
4653 while pos < log_buf.__len__():
47− length = utils.read_u16(log_buf[pos + 8:pos + 10])
54+ length = utils.read_u16(log_buf, pos + length_offset)
4855 if length == 0:
4956 if log_buf_2nd_half == -1:
5057 gdb.write("Corrupted log buffer!\n")
@@ -52,10 +59,11 @@ class LxDmesg(gdb.Command): · 1 unmodified line
5259 pos = log_buf_2nd_half
5360 continue
5461
55− text_len = utils.read_u16(log_buf[pos + 10:pos + 12])
56− text = log_buf[pos + 16:pos + 16 + text_len].decode(
62+ text_len = utils.read_u16(log_buf, pos + text_len_offset)
63+ text_start = pos + text_offset
64+ text = log_buf[text_start:text_start + text_len].decode(
5765 encoding='utf8', errors='replace')
58− time_stamp = utils.read_u64(log_buf[pos:pos + 8])
66+ time_stamp = utils.read_u64(log_buf, pos + time_stamp_offset)
5967
6068 for line in text.splitlines():
6169 msg = u"[{time:12.6f}] {line}\n".format(
scripts/gdb/linux/utils.py+13−12
@@ -92,15 +92,16 @@ def read_memoryview(inf, start, length): · 91 unmodified lines
9292 return memoryview(inf.read_memory(start, length))
9393
9494
95−def read_u16(buffer):
95+def read_u16(buffer, offset):
96+ buffer_val = buffer[offset:offset + 2]
9697 value = [0, 0]
9798
98− if type(buffer[0]) is str:
99− value[0] = ord(buffer[0])
100− value[1] = ord(buffer[1])
99+ if type(buffer_val[0]) is str:
100+ value[0] = ord(buffer_val[0])
101+ value[1] = ord(buffer_val[1])
101102 else:
102− value[0] = buffer[0]
103− value[1] = buffer[1]
103+ value[0] = buffer_val[0]
104+ value[1] = buffer_val[1]
104105
105106 if get_target_endianness() == LITTLE_ENDIAN:
106107 return value[0] + (value[1] << 8)
@@ -108,18 +109,18 @@ def read_u16(buffer): · 1 unmodified line
108109 return value[1] + (value[0] << 8)
109110
110111
111−def read_u32(buffer):
112+def read_u32(buffer, offset):
112113 if get_target_endianness() == LITTLE_ENDIAN:
113− return read_u16(buffer[0:2]) + (read_u16(buffer[2:4]) << 16)
114+ return read_u16(buffer, offset) + (read_u16(buffer, offset + 2) << 16)
114115 else:
115− return read_u16(buffer[2:4]) + (read_u16(buffer[0:2]) << 16)
116+ return read_u16(buffer, offset + 2) + (read_u16(buffer, offset) << 16)
116117
117118
118−def read_u64(buffer):
119+def read_u64(buffer, offset):
119120 if get_target_endianness() == LITTLE_ENDIAN:
120− return read_u32(buffer[0:4]) + (read_u32(buffer[4:8]) << 32)
121+ return read_u32(buffer, offset) + (read_u32(buffer, offset + 4) << 32)
121122 else:
122− return read_u32(buffer[4:8]) + (read_u32(buffer[0:4]) << 32)
123+ return read_u32(buffer, offset + 4) + (read_u32(buffer, offset) << 32)
123124
124125
125126 target_arch = None