8

下面您将看到来自专有路由设备的 32b 内存转储中字符串“octeon”的一小段匹配。如您所见,它包含一些调整后的 ASCII,从行尾开始扩展到 16 个字符,然后是四个 32 位字(当然每个字 8 个字符),然后是地址偏移量。

000b27a0: 41646a75 7374206f 6374656f 6e5f6970    Adjust octeon_ip
000b2850: 73740a00 00000000 6f637465 6f6e5f72    st......octeon_r
000b2870: 5f73697a 65000000 6f637465 6f6e5f72    _size...octeon_r
000b2990: 6164696e 672e0a00 6f637465 6f6e5f72    ading...octeon_r
000b29b0: 785f7369 7a650000 6f637465 6f6e5f72    x_size..octeon_r
000b3050: 780a0000 00000000 6f637465 6f6e5f70    x.......octeon_p
000b3650: 6564204f 6374656f 6e206d6f 64656c0a    ed Octeon model.
000bade0: 20307825 71780a00 6f637465 6f6e5f6c     0x%qx..octeon_l
000bafd0: 696e6720 4f637465 6f6e2045 78656375    ing Octeon Execu
000bd710: 6564204f 6374656f 6e204d6f 64656c21    ed Octeon Model!
000bd950: 4f435445 4f4e2070 61737320 3120646f    OCTEON pass 1 do
000bda20: 6564206f 6374656f 6e206d6f 64656c3a    ed octeon model:

虽然这些数据包含一些有用的信息,但不幸的是,操作系统 ( HiveOS ) 并没有尝试连续分配内存或合并不同的堆(为什么要合并?),因此绝大多数内存是尚未开发的-malloc 堆。

0004d6b0: 00000000 00000000 00000000 00000000    ................
0004d6c0: 00000000 00000000 00000000 00000000    ................
0004d6d0: 00000000 00000000 00000000 00000000    ................
0004d6e0: 00000000 00000000 00000000 00000000    ................
0004d6f0: 00000000 00000000 00000000 00000000    ................
0004d700: 00000000 00000000 00000000 00000000    ................
0004d710: 00000000 00000000 00000000 00000000    ................
0004d720: 00000000 00000000 00000000 00000000    ................
0004d730: 00000000 00000000 00000000 00000000    ................
0004d740: 00000000 00000000 00000000 00000000    ................
0004d750: 00000000 00000000 00000000 00000000    ................

我想快速有效地提取与任意正则表达式模式匹配的一定大小的字符串([a-zA-z]想到)您可能自然认为运行常年对象转储检查最喜欢的“字符串”会产生结果,但md实用程序是一个残忍的情妇——由于存在 ASCII 编码的十六进制银行和地址,它将每一行都标识为包含一个“字符串”。

当然,我们都知道存在一个简单的脚本解决方案 ( for line in hexdump: f.write(line[-16:])+ grep '[A-z]' f)。

然而,有时我会觉得我应该更好地理解这些令人讨厌的压迫性但被误解的正则表达式,而不是回到我易于使用的新奇编程语言。我真的觉得在我用各种流编辑器和 Awk 脚本的正则表达式完全取代我的整个开发工具链生活之前,我无法开始长出真正的 Unix 脖子。

如何[a-zA-z]从行尾开始匹配一定数量的字符(在我的例子中是 16 个)——这似乎是一个非常简洁的结构,但都是 +, 的组合?{16} 并且在过去几分钟内对我来说有意义的其他方式立即失败了。

4

3 回答 3

6

使用“不匹配”开关-v

grep -v \.{16}$

这将去掉所有以 16 个点结尾的行。

这是man它的文档:

-v, --invert-match
反转匹配的感觉,选择不匹配的行。

于 2012-03-16T23:15:42.953 回答
4

这是做你想做的吗?" .{16}$"

这将匹配从行尾开始的任何 16 个字符。$确保它与行尾匹配。


经过仔细检查,如果您只想提取不是所有句点的行,您可以使用这个正则表达式:“ {4}(.*?\w.*?)$之前有一个空格,{4}以便它匹配数字和行尾之间的分隔符。从技术上讲,它并不是“只有 16 个字符”,但考虑到数据集,它似乎确实提供了所需的输出。(假设所需的输出是任何包含单词字符的行,即字母/数字/下划线。)

于 2012-03-15T17:34:14.077 回答
2

过滤有趣行的一个廉价技巧是用任何字符填充选择,直到行尾。在这里,我选择了一个不是点且距离行尾不超过 15 个字符的字符。(您使用 posix 正则表达式,因此您应该在 \{ \} 而不是 { } 之间编写重复量词)

grep '[^.].\{1,15\}$'

然后你可以用另一个 grep 管道结果来测试,或者你可以将这个想法适应另一个正则表达式:

grep 'abc.\{1,13\}$'

将在最后 16 个字符中匹配字符串“abc”。

于 2012-03-16T22:46:05.647 回答