def __init__(self, reader: MemoryViewReader): self.name_index = reader.read_int() self.super_name_index = reader.read_int() self.flags = ClassFlags(reader.read_u8()) if ClassFlags.PROTECTED_NS in self.flags: self.protected_namespace_index = reader.read_int() self.interface_indices = read_array(reader, MemoryViewReader.read_int) self.init_index = reader.read_int() self.traits = read_array(reader, ASTrait)
def __init__(self, reader: MemoryViewReader): self.minor_version = reader.read_u16() self.major_version = reader.read_u16() self.constant_pool = ASConstantPool(reader) self.methods = read_array(reader, ASMethod) self.metadata = read_array(reader, ASMetadata) class_count = reader.read_int() self.instances = read_array(reader, ASInstance, class_count) self.classes = read_array(reader, ASClass, class_count) self.scripts = read_array(reader, ASScript) self.method_bodies = read_array(reader, ASMethodBody)
def __init__(self, reader: MemoryViewReader): self.param_count = reader.read_int() self.return_type_index = reader.read_int() self.param_type_indices = read_array(reader, MemoryViewReader.read_int, self.param_count) self.name_index = reader.read_int() self.flags = MethodFlags(reader.read_u8()) if MethodFlags.HAS_OPTIONAL in self.flags: self.options = read_array(reader, ASOptionDetail) if MethodFlags.HAS_PARAM_NAMES in self.flags: self.param_name_indices = read_array(reader, MemoryViewReader.read_int, self.param_count)
def parse_swf(input_: Union[memoryview, bytes]) -> Iterable[Tag]: """ Parse SWF file and get an iterable of its tags. """ reader = MemoryViewReader(input_) signature = Signature(reader.read_u8()) assert reader.read_u16() == 0x5357 reader.skip(1) # version reader.skip(4) # file length reader = decompress(reader, signature) reader.skip_rect() reader.skip(4) # frame rate and frame count return read_tags(reader)
def read_array_with_default(reader: MemoryViewReader, read: Callable[[MemoryViewReader], T], default: Optional[T]) -> List[T]: """ Read variable-length array where 0-th element has a "special meaning". """ return [default, *(read(reader) for _ in range(1, reader.read_int()))]
def read_array(reader: MemoryViewReader, read: Callable[[MemoryViewReader], T], size: Optional[int] = None) -> List[T]: """ Read variable-length array. """ if size is None: size = reader.read_int() return [read(reader) for _ in range(size)]
def __init__(self, reader: MemoryViewReader): self.name_index = reader.read_int() kind = reader.read_u8() self.kind = TraitKind(kind & 0x0F) self.attributes = TraitAttributes(kind >> 4) if self.kind in (TraitKind.SLOT, TraitKind.CONST): self.data = ASTraitSlot(reader) elif self.kind == TraitKind.CLASS: self.data = ASTraitClass(reader) elif self.kind == TraitKind.FUNCTION: self.data = ASTraitFunction(reader) elif self.kind in (TraitKind.METHOD, TraitKind.GETTER, TraitKind.SETTER): self.data = ASTraitMethod(reader) else: assert False, 'unreachable code' if TraitAttributes.METADATA in self.attributes: self.metadata = read_array(reader, MemoryViewReader.read_int)
def __init__(self, reader: MemoryViewReader): self.method_index = reader.read_int() self.max_stack = reader.read_int() self.local_count = reader.read_int() self.init_scope_depth = reader.read_int() self.max_scope_depth = reader.read_int() self.code = reader.read(reader.read_int()) self.exceptions = read_array(reader, ASException) self.traits = read_array(reader, ASTrait)
def execute_code(self, code: memoryview, environment: MethodEnvironment) -> Any: """ Execute the byte-code and get a return value. """ reader = MemoryViewReader(code) while True: try: # FIXME: cache already read instructions. avm2.abc.instructions.read_instruction(reader).execute(self, environment) except ASReturnException as e: return e.return_value except ASJumpException as e: reader.position += e.offset
def __init__(self, reader: MemoryViewReader): self.kind = MultinameKind(reader.read_u8()) if self.kind in (MultinameKind.Q_NAME, MultinameKind.Q_NAME_A): self.namespace_index = reader.read_int() self.name_index = reader.read_int() elif self.kind in (MultinameKind.RTQ_NAME, MultinameKind.RTQ_NAME_A): self.name_index = reader.read_int() elif self.kind in (MultinameKind.RTQ_NAME_L, MultinameKind.RTQ_NAME_LA): pass elif self.kind in (MultinameKind.MULTINAME, MultinameKind.MULTINAME_A): self.name_index = reader.read_int() self.namespace_set_index = reader.read_int() elif self.kind in (MultinameKind.MULTINAME_L, MultinameKind.MULTINAME_LA): self.namespace_set_index = reader.read_int() elif self.kind == MultinameKind.TYPE_NAME: self.q_name_index = reader.read_int() self.type_indices = read_array(reader, MemoryViewReader.read_int) else: assert False, 'unreachable code'
def decompress(reader: MemoryViewReader, signature: Signature) -> MemoryViewReader: """ Decompress the rest of an SWF file, depending on its signature. """ if signature == Signature.UNCOMPRESSED: return reader if signature == Signature.LZMA: # https://stackoverflow.com/a/39777419/359730 reader.skip(4) # skip compressed length return MemoryViewReader( lzma.decompress( reader.read(5).tobytes() + b'\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFF' + reader.read_all().tobytes())) if signature == Signature.ZLIB: return MemoryViewReader(zlib.decompress(reader.read_all())) assert False, 'unreachable code'
def read_tags(reader: MemoryViewReader) -> Iterable[Tag]: """ Read tags from the stream and get an iterable of tags. """ while not reader.is_eof(): code_length = reader.read_u16() length = code_length & 0b111111 if length == 0x3F: # Long tag header. length = reader.read_u32() try: type_ = TagType(code_length >> 6) except ValueError: # Unknown tag type. Skip the tag. reader.skip(length) else: yield Tag(type_=type_, raw=reader.read(length))
def __init__(self, reader: MemoryViewReader): self.slot_id = reader.read_int() self.type_name_index = reader.read_int() self.vindex = reader.read_int() if self.vindex: self.vkind = ConstantKind(reader.read_u8())
def __init__(self, raw: memoryview): reader = MemoryViewReader(raw) self.flags = DoABCTagFlags(reader.read_u32()) self.name = reader.read_string() self.abc_file = reader.read_all()
def __init__(self, reader: MemoryViewReader): self.kind = NamespaceKind(reader.read_u8()) self.name_index = reader.read_int()
def __init__(self, reader: MemoryViewReader): self.from_ = reader.read_int() self.to = reader.read_int() self.target = reader.read_int() self.exc_type_index = reader.read_int() self.var_name_index = reader.read_int()
def __init__(self, reader: MemoryViewReader): self.init_index = reader.read_int() self.traits = read_array(reader, ASTrait)
def __init__(self, reader: MemoryViewReader): self.disposition_id = reader.read_int() self.method_index = reader.read_int()
def abc_file(do_abc_tag: DoABCTag) -> ABCFile: return ABCFile(MemoryViewReader(do_abc_tag.abc_file))
def __init__(self, reader: MemoryViewReader): self.key_index = reader.read_int() self.value_index = reader.read_int()
def __init__(self, reader: MemoryViewReader): self.name_index = reader.read_int() self.items = read_array(reader, ASItem)
def __init__(self, reader: MemoryViewReader): self.value = reader.read_int() self.kind = ConstantKind(reader.read_u8())
def read_string(reader: MemoryViewReader) -> str: return reader.read(reader.read_int()).tobytes().decode('utf-8')
def __init__(self, reader: MemoryViewReader): self.slot_id = reader.read_int() self.class_index = reader.read_int()
def execute_do_abc_tag(do_abc_tag: DoABCTag) -> VirtualMachine: """ Create a virtual machine and execute the tag. """ return VirtualMachine(ABCFile(MemoryViewReader(do_abc_tag.abc_file)))
def __init__(self, reader: MemoryViewReader): self.slot_id = reader.read_int() self.function_index = reader.read_int()