Apply sanitize string cc to all messages that need it
This commit is contained in:
parent
3df2a7fb12
commit
7dfaeda45f
|
@ -5,6 +5,22 @@ import json
|
|||
|
||||
from typing import TypedDict, Literal, Optional, Dict, Union
|
||||
|
||||
KIND = Literal[ \
|
||||
'int32', \
|
||||
'tick', \
|
||||
'string', \
|
||||
'raw', \
|
||||
'sha256', \
|
||||
'data', \
|
||||
'rest', \
|
||||
'enum', \
|
||||
'boolean', \
|
||||
'tune_param', \
|
||||
'snapshot_object', \
|
||||
'array', \
|
||||
'flags', \
|
||||
'optional']
|
||||
|
||||
class ConstantJson(TypedDict):
|
||||
name: list[str]
|
||||
type: str
|
||||
|
@ -19,41 +35,11 @@ class NetEnumJson(TypedDict):
|
|||
values: list[NetEnumValuesJson]
|
||||
|
||||
class InnerNetMessageMemberTypeJson(TypedDict):
|
||||
# TODO: define this literal as type
|
||||
# so it can be reused
|
||||
kind: Literal[ \
|
||||
'int32', \
|
||||
'tick', \
|
||||
'string', \
|
||||
'raw', \
|
||||
'sha256', \
|
||||
'data', \
|
||||
'rest', \
|
||||
'enum', \
|
||||
'boolean', \
|
||||
'tune_param', \
|
||||
'snapshot_object', \
|
||||
'array', \
|
||||
'flags', \
|
||||
'optional']
|
||||
kind: KIND
|
||||
disallow_cc: bool
|
||||
|
||||
class NetMessageMemberTypeJson(TypedDict):
|
||||
kind: Literal[ \
|
||||
'int32', \
|
||||
'tick', \
|
||||
'string', \
|
||||
'raw', \
|
||||
'sha256', \
|
||||
'data', \
|
||||
'rest', \
|
||||
'enum', \
|
||||
'boolean', \
|
||||
'tune_param', \
|
||||
'snapshot_object', \
|
||||
'array', \
|
||||
'flags', \
|
||||
'optional']
|
||||
kind: KIND
|
||||
inner: InnerNetMessageMemberTypeJson
|
||||
disallow_cc: bool
|
||||
|
||||
|
@ -172,7 +158,7 @@ def generate_msg(msg: NetMessageJson, game: Literal['game', 'system']) -> None:
|
|||
# {'name': ['message'], 'type': {'kind': 'string', 'disallow_cc': False}}
|
||||
ftype = 'int'
|
||||
default = '-1'
|
||||
if member['type']['kind'] == 'string': # TODO: sanitize cc
|
||||
if member['type']['kind'] == 'string':
|
||||
ftype = 'str'
|
||||
default = "'default'"
|
||||
elif member['type']['kind'] in \
|
||||
|
@ -204,7 +190,7 @@ def generate_msg(msg: NetMessageJson, game: Literal['game', 'system']) -> None:
|
|||
ftype = 'int'
|
||||
default = '0'
|
||||
elif member['type']['kind'] == 'optional':
|
||||
if member['type']['inner']['kind'] == 'string': # TODO: sanitize cc
|
||||
if member['type']['inner']['kind'] == 'string':
|
||||
ftype = 'str'
|
||||
default = "''"
|
||||
elif member['type']['inner']['kind'] in ('int32', 'tick'):
|
||||
|
@ -251,7 +237,7 @@ def generate_msg(msg: NetMessageJson, game: Literal['game', 'system']) -> None:
|
|||
elif member['type']['kind'] == 'flags': # TODO: think about flags
|
||||
ftype = 'int'
|
||||
elif member['type']['kind'] == 'optional':
|
||||
if member['type']['inner']['kind'] == 'string': # TODO: sanitize cc
|
||||
if member['type']['inner']['kind'] == 'string':
|
||||
ftype = 'str'
|
||||
elif member['type']['inner']['kind'] in ('int32', 'tick'):
|
||||
ftype = 'int'
|
||||
|
@ -271,8 +257,11 @@ def generate_msg(msg: NetMessageJson, game: Literal['game', 'system']) -> None:
|
|||
for member in msg['members']:
|
||||
# {'name': ['message'], 'type': {'kind': 'string', 'disallow_cc': False}}
|
||||
unpacker = 'int()'
|
||||
if member['type']['kind'] == 'string': # TODO: sanitize cc
|
||||
unpacker = 'str()'
|
||||
if member['type']['kind'] == 'string':
|
||||
if member['type']['disallow_cc']:
|
||||
unpacker = 'str(SANITIZE_CC)'
|
||||
else:
|
||||
unpacker = 'str()'
|
||||
elif member['type']['kind'] in \
|
||||
('raw', 'sha256', 'rest', 'data'): # TODO: data has a size field
|
||||
unpacker = 'raw()'
|
||||
|
@ -295,10 +284,14 @@ def generate_msg(msg: NetMessageJson, game: Literal['game', 'system']) -> None:
|
|||
elif member['type']['kind'] == 'optional':
|
||||
# TODO: unpacker should not crash on missing optional fields
|
||||
# check how tw code does it and be smart here
|
||||
if member['type']['inner']['kind'] == 'string': # TODO: sanitize cc
|
||||
unpacker = 'str() # TODO: this can fail for optionals'
|
||||
if member['type']['inner']['kind'] == 'string':
|
||||
if member['type']['inner']['disallow_cc']:
|
||||
unpacker = 'str(SANITIZE_CC)'
|
||||
unpacker += ' # TODO: optionals'
|
||||
else:
|
||||
unpacker = 'str() # TODO: optionals'
|
||||
elif member['type']['inner']['kind'] in ('int32', 'tick'):
|
||||
unpacker = 'int() # TODO: this can fail for optionals'
|
||||
unpacker = 'int() # TODO: optionals'
|
||||
else:
|
||||
raise ValueError(f"Error: unknown type {member['type']}")
|
||||
name = name_to_snake(member["name"])
|
||||
|
@ -311,8 +304,10 @@ def generate_msg(msg: NetMessageJson, game: Literal['game', 'system']) -> None:
|
|||
def get_dependencies(msg: NetMessageJson) -> str:
|
||||
packer_deps: list[str] = []
|
||||
for member in msg['members']:
|
||||
if member['type']['kind'] == 'string': # TODO: sanitize cc
|
||||
if member['type']['kind'] == 'string':
|
||||
packer_deps.append('pack_str')
|
||||
if member['type']['disallow_cc']:
|
||||
packer_deps.append('SANITIZE_CC')
|
||||
elif member['type']['kind'] in \
|
||||
('raw', 'sha256', 'rest', 'data'): # TODO: data has a size field
|
||||
pass
|
||||
|
@ -335,6 +330,8 @@ def get_dependencies(msg: NetMessageJson) -> str:
|
|||
elif member['type']['kind'] == 'optional':
|
||||
if member['type']['inner']['kind'] == 'string':
|
||||
packer_deps.append('pack_str')
|
||||
if member['type']['inner']['disallow_cc']:
|
||||
packer_deps.append('SANITIZE_CC')
|
||||
elif member['type']['inner']['kind'] in ('int32', 'tick'):
|
||||
packer_deps.append('pack_int')
|
||||
else:
|
||||
|
@ -348,7 +345,7 @@ def pack_field(member: NetMessageMemberJson) -> str:
|
|||
name: str = name_to_snake(member["name"])
|
||||
field: str = f'self.{name}'
|
||||
packer = 'int'
|
||||
if member['type']['kind'] == 'string': # TODO: sanitize cc
|
||||
if member['type']['kind'] == 'string':
|
||||
packer = 'str'
|
||||
elif member['type']['kind'] in \
|
||||
('raw', 'sha256', 'rest', 'data'): # TODO: data has a size field
|
||||
|
@ -374,7 +371,7 @@ def pack_field(member: NetMessageMemberJson) -> str:
|
|||
packer = 'int'
|
||||
# TODO: unpacker should allow not packing optional fields
|
||||
# check how tw code does it and be smart here
|
||||
if member['type']['inner']['kind'] == 'string': # TODO: sanitize cc
|
||||
if member['type']['inner']['kind'] == 'string':
|
||||
packer = 'str'
|
||||
elif member['type']['inner']['kind'] in ('int32', 'tick'):
|
||||
packer = 'int'
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
from twnet_parser.pretty_print import PrettyPrint
|
||||
from twnet_parser.packer import Unpacker
|
||||
from twnet_parser.chunk_header import ChunkHeader
|
||||
from twnet_parser.packer import pack_int, pack_str
|
||||
from twnet_parser.packer import SANITIZE_CC, pack_int, pack_str
|
||||
|
||||
class MsgClCallVote(PrettyPrint):
|
||||
def __init__(
|
||||
|
@ -27,9 +27,9 @@ class MsgClCallVote(PrettyPrint):
|
|||
# NOT the chunk header and NOT the message id
|
||||
def unpack(self, data: bytes) -> bool:
|
||||
unpacker = Unpacker(data)
|
||||
self.type = unpacker.get_str()
|
||||
self.value = unpacker.get_str()
|
||||
self.reason = unpacker.get_str()
|
||||
self.type = unpacker.get_str(SANITIZE_CC)
|
||||
self.value = unpacker.get_str(SANITIZE_CC)
|
||||
self.reason = unpacker.get_str(SANITIZE_CC)
|
||||
self.force = unpacker.get_int() == 1
|
||||
return True
|
||||
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
from twnet_parser.pretty_print import PrettyPrint
|
||||
from twnet_parser.packer import Unpacker
|
||||
from twnet_parser.chunk_header import ChunkHeader
|
||||
from twnet_parser.packer import pack_str
|
||||
from twnet_parser.packer import SANITIZE_CC, pack_str
|
||||
|
||||
class MsgClCommand(PrettyPrint):
|
||||
def __init__(
|
||||
|
@ -23,8 +23,8 @@ class MsgClCommand(PrettyPrint):
|
|||
# NOT the chunk header and NOT the message id
|
||||
def unpack(self, data: bytes) -> bool:
|
||||
unpacker = Unpacker(data)
|
||||
self.name = unpacker.get_str()
|
||||
self.arguments = unpacker.get_str()
|
||||
self.name = unpacker.get_str(SANITIZE_CC)
|
||||
self.arguments = unpacker.get_str(SANITIZE_CC)
|
||||
return True
|
||||
|
||||
def pack(self) -> bytes:
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
from twnet_parser.pretty_print import PrettyPrint
|
||||
from twnet_parser.packer import Unpacker
|
||||
from twnet_parser.chunk_header import ChunkHeader
|
||||
from twnet_parser.packer import pack_int, pack_str
|
||||
from twnet_parser.packer import SANITIZE_CC, pack_int, pack_str
|
||||
|
||||
class MsgClSay(PrettyPrint):
|
||||
def __init__(
|
||||
|
@ -27,7 +27,7 @@ class MsgClSay(PrettyPrint):
|
|||
unpacker = Unpacker(data)
|
||||
self.mode = unpacker.get_int() # TODO: this is a enum
|
||||
self.target = unpacker.get_int()
|
||||
self.message = unpacker.get_str()
|
||||
self.message = unpacker.get_str(SANITIZE_CC)
|
||||
return True
|
||||
|
||||
def pack(self) -> bytes:
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
from twnet_parser.pretty_print import PrettyPrint
|
||||
from twnet_parser.packer import Unpacker
|
||||
from twnet_parser.chunk_header import ChunkHeader
|
||||
from twnet_parser.packer import pack_int, pack_str
|
||||
from twnet_parser.packer import SANITIZE_CC, pack_int, pack_str
|
||||
|
||||
class MsgClStartInfo(PrettyPrint):
|
||||
def __init__(
|
||||
|
@ -31,8 +31,8 @@ class MsgClStartInfo(PrettyPrint):
|
|||
# NOT the chunk header and NOT the message id
|
||||
def unpack(self, data: bytes) -> bool:
|
||||
unpacker = Unpacker(data)
|
||||
self.name = unpacker.get_str()
|
||||
self.clan = unpacker.get_str()
|
||||
self.name = unpacker.get_str(SANITIZE_CC)
|
||||
self.clan = unpacker.get_str(SANITIZE_CC)
|
||||
self.country = unpacker.get_int()
|
||||
self.skin_part_names = unpacker.get_int() # TODO: this is an array
|
||||
self.use_custom_colors = unpacker.get_int() # TODO: this is an array
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
from twnet_parser.pretty_print import PrettyPrint
|
||||
from twnet_parser.packer import Unpacker
|
||||
from twnet_parser.chunk_header import ChunkHeader
|
||||
from twnet_parser.packer import pack_int, pack_str
|
||||
from twnet_parser.packer import SANITIZE_CC, pack_int, pack_str
|
||||
|
||||
class MsgDeClientEnter(PrettyPrint):
|
||||
def __init__(
|
||||
|
@ -25,7 +25,7 @@ class MsgDeClientEnter(PrettyPrint):
|
|||
# NOT the chunk header and NOT the message id
|
||||
def unpack(self, data: bytes) -> bool:
|
||||
unpacker = Unpacker(data)
|
||||
self.name = unpacker.get_str()
|
||||
self.name = unpacker.get_str(SANITIZE_CC)
|
||||
self.client_id = unpacker.get_int()
|
||||
self.team = unpacker.get_int() # TODO: this is a enum
|
||||
return True
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
from twnet_parser.pretty_print import PrettyPrint
|
||||
from twnet_parser.packer import Unpacker
|
||||
from twnet_parser.chunk_header import ChunkHeader
|
||||
from twnet_parser.packer import pack_int, pack_str
|
||||
from twnet_parser.packer import SANITIZE_CC, pack_int, pack_str
|
||||
|
||||
class MsgDeClientLeave(PrettyPrint):
|
||||
def __init__(
|
||||
|
@ -25,9 +25,9 @@ class MsgDeClientLeave(PrettyPrint):
|
|||
# NOT the chunk header and NOT the message id
|
||||
def unpack(self, data: bytes) -> bool:
|
||||
unpacker = Unpacker(data)
|
||||
self.name = unpacker.get_str()
|
||||
self.name = unpacker.get_str(SANITIZE_CC)
|
||||
self.client_id = unpacker.get_int()
|
||||
self.reason = unpacker.get_str()
|
||||
self.reason = unpacker.get_str(SANITIZE_CC)
|
||||
return True
|
||||
|
||||
def pack(self) -> bytes:
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
from twnet_parser.pretty_print import PrettyPrint
|
||||
from twnet_parser.packer import Unpacker
|
||||
from twnet_parser.chunk_header import ChunkHeader
|
||||
from twnet_parser.packer import pack_int, pack_str
|
||||
from twnet_parser.packer import SANITIZE_CC, pack_int, pack_str
|
||||
|
||||
class MsgSvChat(PrettyPrint):
|
||||
def __init__(
|
||||
|
@ -30,7 +30,7 @@ class MsgSvChat(PrettyPrint):
|
|||
self.mode = unpacker.get_int() # TODO: this is a enum
|
||||
self.client_id = unpacker.get_int()
|
||||
self.target_id = unpacker.get_int()
|
||||
self.message = unpacker.get_str()
|
||||
self.message = unpacker.get_str(SANITIZE_CC)
|
||||
return True
|
||||
|
||||
def pack(self) -> bytes:
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
from twnet_parser.pretty_print import PrettyPrint
|
||||
from twnet_parser.packer import Unpacker
|
||||
from twnet_parser.chunk_header import ChunkHeader
|
||||
from twnet_parser.packer import pack_int, pack_str
|
||||
from twnet_parser.packer import SANITIZE_CC, pack_int, pack_str
|
||||
|
||||
class MsgSvClientDrop(PrettyPrint):
|
||||
def __init__(
|
||||
|
@ -26,7 +26,7 @@ class MsgSvClientDrop(PrettyPrint):
|
|||
def unpack(self, data: bytes) -> bool:
|
||||
unpacker = Unpacker(data)
|
||||
self.client_id = unpacker.get_int()
|
||||
self.reason = unpacker.get_str()
|
||||
self.reason = unpacker.get_str(SANITIZE_CC)
|
||||
self.silent = unpacker.get_int() == 1
|
||||
return True
|
||||
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
from twnet_parser.pretty_print import PrettyPrint
|
||||
from twnet_parser.packer import Unpacker
|
||||
from twnet_parser.chunk_header import ChunkHeader
|
||||
from twnet_parser.packer import pack_int, pack_str
|
||||
from twnet_parser.packer import SANITIZE_CC, pack_int, pack_str
|
||||
|
||||
class MsgSvClientInfo(PrettyPrint):
|
||||
def __init__(
|
||||
|
@ -42,8 +42,8 @@ class MsgSvClientInfo(PrettyPrint):
|
|||
self.client_id = unpacker.get_int()
|
||||
self.local = unpacker.get_int() == 1
|
||||
self.team = unpacker.get_int() # TODO: this is a enum
|
||||
self.name = unpacker.get_str()
|
||||
self.clan = unpacker.get_str()
|
||||
self.name = unpacker.get_str(SANITIZE_CC)
|
||||
self.clan = unpacker.get_str(SANITIZE_CC)
|
||||
self.country = unpacker.get_int()
|
||||
self.skin_part_names = unpacker.get_int() # TODO: this is an array
|
||||
self.use_custom_colors = unpacker.get_int() # TODO: this is an array
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
from twnet_parser.pretty_print import PrettyPrint
|
||||
from twnet_parser.packer import Unpacker
|
||||
from twnet_parser.chunk_header import ChunkHeader
|
||||
from twnet_parser.packer import pack_str
|
||||
from twnet_parser.packer import SANITIZE_CC, pack_str
|
||||
|
||||
class MsgSvCommandInfo(PrettyPrint):
|
||||
def __init__(
|
||||
|
@ -25,9 +25,9 @@ class MsgSvCommandInfo(PrettyPrint):
|
|||
# NOT the chunk header and NOT the message id
|
||||
def unpack(self, data: bytes) -> bool:
|
||||
unpacker = Unpacker(data)
|
||||
self.name = unpacker.get_str()
|
||||
self.args_format = unpacker.get_str()
|
||||
self.help_text = unpacker.get_str()
|
||||
self.name = unpacker.get_str(SANITIZE_CC)
|
||||
self.args_format = unpacker.get_str(SANITIZE_CC)
|
||||
self.help_text = unpacker.get_str(SANITIZE_CC)
|
||||
return True
|
||||
|
||||
def pack(self) -> bytes:
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
from twnet_parser.pretty_print import PrettyPrint
|
||||
from twnet_parser.packer import Unpacker
|
||||
from twnet_parser.chunk_header import ChunkHeader
|
||||
from twnet_parser.packer import pack_str
|
||||
from twnet_parser.packer import SANITIZE_CC, pack_str
|
||||
|
||||
class MsgSvCommandInfoRemove(PrettyPrint):
|
||||
def __init__(
|
||||
|
@ -21,7 +21,7 @@ class MsgSvCommandInfoRemove(PrettyPrint):
|
|||
# NOT the chunk header and NOT the message id
|
||||
def unpack(self, data: bytes) -> bool:
|
||||
unpacker = Unpacker(data)
|
||||
self.name = unpacker.get_str()
|
||||
self.name = unpacker.get_str(SANITIZE_CC)
|
||||
return True
|
||||
|
||||
def pack(self) -> bytes:
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
from twnet_parser.pretty_print import PrettyPrint
|
||||
from twnet_parser.packer import Unpacker
|
||||
from twnet_parser.chunk_header import ChunkHeader
|
||||
from twnet_parser.packer import pack_str
|
||||
from twnet_parser.packer import SANITIZE_CC, pack_str
|
||||
|
||||
class MsgSvVoteOptionAdd(PrettyPrint):
|
||||
def __init__(
|
||||
|
@ -21,7 +21,7 @@ class MsgSvVoteOptionAdd(PrettyPrint):
|
|||
# NOT the chunk header and NOT the message id
|
||||
def unpack(self, data: bytes) -> bool:
|
||||
unpacker = Unpacker(data)
|
||||
self.description = unpacker.get_str()
|
||||
self.description = unpacker.get_str(SANITIZE_CC)
|
||||
return True
|
||||
|
||||
def pack(self) -> bytes:
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
from twnet_parser.pretty_print import PrettyPrint
|
||||
from twnet_parser.packer import Unpacker
|
||||
from twnet_parser.chunk_header import ChunkHeader
|
||||
from twnet_parser.packer import pack_str
|
||||
from twnet_parser.packer import SANITIZE_CC, pack_str
|
||||
|
||||
class MsgSvVoteOptionRemove(PrettyPrint):
|
||||
def __init__(
|
||||
|
@ -21,7 +21,7 @@ class MsgSvVoteOptionRemove(PrettyPrint):
|
|||
# NOT the chunk header and NOT the message id
|
||||
def unpack(self, data: bytes) -> bool:
|
||||
unpacker = Unpacker(data)
|
||||
self.description = unpacker.get_str()
|
||||
self.description = unpacker.get_str(SANITIZE_CC)
|
||||
return True
|
||||
|
||||
def pack(self) -> bytes:
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
from twnet_parser.pretty_print import PrettyPrint
|
||||
from twnet_parser.packer import Unpacker
|
||||
from twnet_parser.chunk_header import ChunkHeader
|
||||
from twnet_parser.packer import pack_int, pack_str
|
||||
from twnet_parser.packer import SANITIZE_CC, pack_int, pack_str
|
||||
|
||||
class MsgSvVoteSet(PrettyPrint):
|
||||
def __init__(
|
||||
|
@ -32,8 +32,8 @@ class MsgSvVoteSet(PrettyPrint):
|
|||
self.client_id = unpacker.get_int()
|
||||
self.type = unpacker.get_int() # TODO: this is a enum
|
||||
self.timeout = unpacker.get_int()
|
||||
self.description = unpacker.get_str()
|
||||
self.reason = unpacker.get_str()
|
||||
self.description = unpacker.get_str(SANITIZE_CC)
|
||||
self.reason = unpacker.get_str(SANITIZE_CC)
|
||||
return True
|
||||
|
||||
def pack(self) -> bytes:
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
from twnet_parser.pretty_print import PrettyPrint
|
||||
from twnet_parser.packer import Unpacker
|
||||
from twnet_parser.chunk_header import ChunkHeader
|
||||
from twnet_parser.packer import pack_int, pack_str
|
||||
from twnet_parser.packer import SANITIZE_CC, pack_int, pack_str
|
||||
|
||||
class MsgInfo(PrettyPrint):
|
||||
def __init__(
|
||||
|
@ -26,8 +26,8 @@ class MsgInfo(PrettyPrint):
|
|||
def unpack(self, data: bytes) -> bool:
|
||||
unpacker = Unpacker(data)
|
||||
self.version = unpacker.get_str()
|
||||
self.password = unpacker.get_str() # TODO: this can fail for optionals
|
||||
self.client_version = unpacker.get_int() # TODO: this can fail for optionals
|
||||
self.password = unpacker.get_str(SANITIZE_CC) # TODO: optionals
|
||||
self.client_version = unpacker.get_int() # TODO: optionals
|
||||
return True
|
||||
|
||||
def pack(self) -> bytes:
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
#!/usr/bin/env python
|
||||
|
||||
from typing import Literal, Final
|
||||
from typing import Final
|
||||
|
||||
# Before chaning the current packer code to extend it
|
||||
# Consider having two packers
|
||||
|
@ -80,7 +80,10 @@ class Unpacker():
|
|||
# If there is nothing from the python standard
|
||||
# this might be worth writing in Cython
|
||||
# external C or rust
|
||||
def get_str(self, sanitize: Literal[0,1,2,3] = 1) -> str:
|
||||
# TODO: make literals work currently passing in SANITIZE as arg
|
||||
# to unpacker.get_str() does not work because its not a literal ._.
|
||||
# def get_str(self, sanitize: Literal[0,1,2,3] = 1) -> str:
|
||||
def get_str(self, sanitize: int = SANITIZE) -> str:
|
||||
str_end: int = self.data().find(b'\x00')
|
||||
res: bytes = self.data()[:str_end]
|
||||
self.idx += str_end + 1
|
||||
|
|
Loading…
Reference in a new issue