Ejemplo n.º 1
0
    def __init__(self, rom: NintendoDSRom):
        self.rom = rom
        data = rom.iconBanner

        self.version = read_u16(data, 0x0)
        assert len(data) == ICON_BANNER_SIZE
        assert self.version == 1  # EoS should always use version 1

        self.checksum = read_u16(data, 0x2)

        self.icon = Icon(read_bytes(data, 0x20, 0x200),
                         read_bytes(data, 0x220, 0x20))

        self.title_japanese = read_bytes(
            data, 0x240, 0x100).decode('UTF-16LE').rstrip('\x00')
        self.title_english = read_bytes(
            data, 0x340, 0x100).decode('UTF-16LE').rstrip('\x00')
        self.title_french = read_bytes(data, 0x440,
                                       0x100).decode('UTF-16LE').rstrip('\x00')
        self.title_german = read_bytes(data, 0x540,
                                       0x100).decode('UTF-16LE').rstrip('\x00')
        self.title_italian = read_bytes(
            data, 0x640, 0x100).decode('UTF-16LE').rstrip('\x00')
        self.title_spanish = read_bytes(
            data, 0x740, 0x100).decode('UTF-16LE').rstrip('\x00')
Ejemplo n.º 2
0
    def _look_ahead_two_int_sequence(self):
        seq = bytearray(NRL_LOOKAHEAD_COPY_BYTES_MAX_BYTES * 4)
        seq_len = 0
        # If the repeat counter reaches NRL_MIN_SEQ_LEN, the sequence ends NRL_MIN_SEQ_LEN entries before that
        repeat_counter = 0
        previous_ints_at_pos = 0x1000000  # Impossible "null" value for now
        nc = self.cursor
        while True:
            ints_at_pos = read_bytes(self.uncompressed_data, nc, 4)
            if ints_at_pos == previous_ints_at_pos:
                repeat_counter += 1
            else:
                repeat_counter = 0
            previous_ints_at_pos = ints_at_pos

            seq[seq_len * 4:(seq_len * 4) + 4] = ints_at_pos

            if repeat_counter > NRL_MIN_SEQ_LEN:
                seq_len -= NRL_MIN_SEQ_LEN
                break

            if seq_len + 1 >= NRL_LOOKAHEAD_COPY_BYTES_MAX_BYTES or nc >= self.length_input:
                break

            seq_len += 1
            nc += 4

        return seq_len, seq[:seq_len * 4]
Ejemplo n.º 3
0
 def _read(self) -> bytes:
     """Reads 4 bytes and increases cursor"""
     if self.cursor + 4 > self.length_input:
         raise ValueError("BMA Layer NRL Compressor: Reached EOF while reading data.")
     oc = self.cursor
     self.cursor += 4
     return read_bytes(self.uncompressed_data, oc, 4)
Ejemplo n.º 4
0
 def _look_ahead_repeats(self, data: bytes):
     """Look how often the 4 byte pattern in the input data repeats, up to NRL_LOOKAHEAD_MAX_BYTES"""
     nc = self.cursor
     repeats = 0
     while read_bytes(self.uncompressed_data, nc, 4) == data and \
             repeats < NRL_LOOKAHEAD_ZERO_MAX_BYTES and \
             nc < self.length_input:
         repeats += 1
         nc += 4
     return repeats
Ejemplo n.º 5
0
 def matches(cls, data: bytes, byte_offset=0):
     """Check if the given data stream is a At3px container"""
     return read_bytes(data, byte_offset, 5) == b'AT3PX'
Ejemplo n.º 6
0
 def matches(cls, data: bytes, byte_offset=0):
     """Check if the given data is a At4pn container"""
     return read_bytes(data, byte_offset, 5) == b'AT4PN'
Ejemplo n.º 7
0
 def matches(cls, data: bytes, byte_offset=0):
     """Check if the given data stream has the magic string for MD files."""
     return read_bytes(data, byte_offset, 4) == b'MD\0\0'
Ejemplo n.º 8
0
 def matches(cls, data: bytes, byte_offset: int = 0) -> bool:
     """Check if the given data is a container of its type"""
     return read_bytes(data, byte_offset,
                       len(cls.magic_word())) == cls.magic_word()
Ejemplo n.º 9
0
 def matches(cls, data: bytes, byte_offset=0):
     """Check if the given data stream is a Sir0 container"""
     return read_bytes(data, byte_offset, 4) == b'SIR0'