-
Notifications
You must be signed in to change notification settings - Fork 538
Expand file tree
/
Copy pathhex.py
More file actions
47 lines (37 loc) · 1.36 KB
/
hex.py
File metadata and controls
47 lines (37 loc) · 1.36 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
from __future__ import annotations
from typing import TYPE_CHECKING
if TYPE_CHECKING:
from typing import Self # 3.11+
# Map an integer in the inclusive range 0-255 to its string byte representation
_printable = {i: chr(i) if 32 <= i < 128 else "." for i in range(256)}
def hexdump(data: bytes, linesize: int) -> list[str]:
"""
data is a bytes object. The returned result is a string.
"""
prettylines = []
if len(data) < 65536:
fmt = "%%04X %%-%ds %%s"
else:
fmt = "%%08X %%-%ds %%s"
fmt = fmt % (3 * linesize - 1,)
for i in range(0, len(data), linesize):
line = data[i : i + linesize]
hextext = " ".join('%02x' % b for b in line)
rawtext = "".join(_printable[b] for b in line)
prettylines.append(fmt % (i, str(hextext), str(rawtext)))
return prettylines
class HexString(bytes):
"""
Represents bytes that will be hex-dumped to a string when its string
representation is requested.
"""
def __init__(self, data: bytes, linesize: int = 16) -> None:
self.linesize = linesize
def __new__(cls, data: bytes, *args: object, **kwargs: object) -> Self:
return bytes.__new__(cls, data)
def __str__(self) -> str:
if not self:
return "''"
sep = "\n"
return sep + sep.join(
hexdump(self, self.linesize))