diff --git a/Client.py b/Client.py index cad592a..5567ce4 100644 --- a/Client.py +++ b/Client.py @@ -1,7 +1,8 @@ from typing import TYPE_CHECKING, Optional, Dict, Set import struct from NetUtils import ClientStatus -from .Locations import roomCount, nonBlock, beanstones +from .Locations import roomCount, nonBlock, beanstones, roomException, shop, badge, pants +from .Items import items_by_id, ItemData import sys import logging import math @@ -36,110 +37,152 @@ class MLSSClient(BizHawkClient): - game = "Mario & Luigi Superstar Saga" - system = "GBA" - local_checked_locations: Set[int] - goal_flag: int - rom_slot_name: Optional[str] - player_name: Optional[str] - - def __init__(self) -> None: - super().__init__() - self.local_checked_locations = set() - self.local_set_events = {} - self.local_found_key_items = {} - self.rom_slot_name = None - - async def validate_rom(self, ctx: BizHawkClientContext) -> bool: - from CommonClient import logger - - try: - # Check ROM name/patch version - rom_name_bytes = ((await bizhawk.read(ctx.bizhawk_ctx, [(0xA0, 14, "ROM")]))[0]) - rom_name = bytes([byte for byte in rom_name_bytes if byte != 0]).decode("UTF-8") - if not rom_name.startswith("MARIO&LUIGIU"): - return False - if rom_name == "MARIO&LUIGIUA8": - logger.info("ERROR: You appear to be running an unpatched version of Mario & Luigi Superstar Saga. " - "You need to generate a patch file and use it to create a patched ROM.") - return False - if rom_name != "MARIO&LUIGIUAP": - logger.info(rom_name) - logger.info("ERROR: The patch file used to create this ROM is not compatible with " - "this client. Double check your client version against the version being " - "used by the generator.") - return False - except UnicodeDecodeError: + game = "Mario & Luigi Superstar Saga" + system = "GBA" + local_checked_locations: Set[int] + goal_flag: int + rom_slot_name: Optional[str] + player_name: Optional[str] + + def __init__(self) -> None: + super().__init__() + self.local_checked_locations = set() + self.local_set_events = {} + self.local_found_key_items = {} + self.rom_slot_name = None + + async def validate_rom(self, ctx: BizHawkClientContext) -> bool: + from CommonClient import logger + + try: + # Check ROM name/patch version + rom_name_bytes = ((await bizhawk.read(ctx.bizhawk_ctx, [(0xA0, 14, "ROM")]))[0]) + rom_name = bytes([byte for byte in rom_name_bytes if byte != 0]).decode("UTF-8") + if not rom_name.startswith("MARIO&LUIGIU"): return False - except bizhawk.RequestFailedError: - return False # Should verify on the next pass - - ctx.game = self.game - ctx.items_handling = 0b001 - ctx.want_slot_data = True - ctx.watcher_timeout = 0.125 - self.rom_slot_name = rom_name - name_bytes = ((await bizhawk.read(ctx.bizhawk_ctx, [(0xB0, 16, "ROM")]))[0]) - name = bytes([byte for byte in name_bytes if byte != 0]).decode("UTF-8") - self.player_name = name - - return True - - async def set_auth(self, ctx: BizHawkClientContext) -> None: - ctx.auth = self.player_name - - async def game_watcher(self, ctx: BizHawkClientContext) -> None: - from CommonClient import logger - try: - read_state = await bizhawk.read(ctx.bizhawk_ctx, [(0x4564, 59, "EWRAM")]) - flags = read_state[0] - - - # TODO Confirm a save has been made - - locs_to_send = set() - - # Check for set location flags. - for byte_i, byte in enumerate(bytearray(flags)): - for i in range(8): - and_value = 1 << i - if byte & and_value != 0: - flag_id = byte_i * 8 + (i + 1) - room, item = find_key(roomCount, flag_id) - pointer_arr = await bizhawk.read(ctx.bizhawk_ctx, [(ROOM_ARRAY_POINTER + ((room - 1) * 4), 4, "ROM")]) - pointer = (struct.unpack(' None: + ctx.auth = self.player_name + + async def game_watcher(self, ctx: BizHawkClientContext) -> None: + from CommonClient import logger + try: + read_state = await bizhawk.read(ctx.bizhawk_ctx, [(0x4564, 59, "EWRAM"), + (0x2330, 2, "IWRAM"), (0x3FE0, 1, "IWRAM"), (0x3FE4, 1, "IWRAM"), (0x304B, 1, "EWRAM"), (0x304C, 4, "EWRAM"), (0x3058, 6, "EWRAM")]) + flags = read_state[0] + room = (read_state[1][1] << 8) + read_state[1][0] + shop_init = read_state[2][0] + shop_scroll = read_state[3][0] + is_buy = (read_state[4][0] != 0) + shop_address = (struct.unpack('