def write(self, stream: OutputStream): stream.put_u8(self.contents) for data in self.unused: stream.put_u8(data) stream.put_u32(self.pointer)
def write(self, stream: OutputStream) -> int: written_length = 0 if len(self.magic) > 0: for magic_id in self.magic: stream.put_u8(magic_id) written_length += 1 if len(self.armor) > 0: stream.put_u8(0xfc) for item_id in self.armor: stream.put_u8(item_id) written_length += 1 if len(self.weapons) > 0: stream.put_u8(0xfd) for item_id in self.weapons: stream.put_u8(item_id) written_length += 1 if len(self.items) > 0: stream.put_u8(0xfe) for item_id in self.items: stream.put_u8(item_id) written_length += 1 if written_length > 0xf: raise RuntimeError( f"Error: Too many items in shop: {written_length}") return written_length
def build(self): stream = OutputStream() written_length = 0 if len(self._magic) > 0: for magic_id in self._magic: stream.put_u8(magic_id) written_length += 1 if len(self._armor) > 0: stream.put_u8(0xfc) for item_id in self._armor: stream.put_u8(item_id) written_length += 1 if len(self._weapons) > 0: stream.put_u8(0xfd) for item_id in self._weapons: stream.put_u8(item_id) written_length += 1 if len(self._items) > 0: stream.put_u8(0xfe) for item_id in self._items: stream.put_u8(item_id) written_length += 1 if written_length > 0xf: raise RuntimeError( f"Error: Too many items in shop: {written_length}") return ShopInventory(InputStream(stream.get_buffer()), written_length)
def write(self, stream: OutputStream): stream.put_u16(self.exp_reward) stream.put_u16(self.gil_reward) stream.put_u16(self.max_hp) stream.put_u8(self.morale) stream.put_u8(self.unused_ai) stream.put_u8(self.evasion) stream.put_u8(self.pdef) stream.put_u8(self.hit_count) stream.put_u8(self.acc) stream.put_u8(self.atk) stream.put_u8(self.agi) stream.put_u8(self.intel) stream.put_u8(self.crit_rate) stream.put_u16(self.status_atk_elem) stream.put_u8(self.status_atk_ailment) stream.put_u8(self.family) stream.put_u8(self.mdef) stream.put_u8(self.unused) stream.put_u16(self.elem_weakness) stream.put_u16(self.elem_resists) stream.put_u8(self.drop_type) stream.put_u8(self.drop_id) stream.put_u8(self.drop_chance) for data in self.padding: stream.put_u8(data)
def write(self, stream: OutputStream): stream.put_u8(self.enemy_id) stream.put_u8(self.min_count) stream.put_u8(self.max_count) stream.put_u8(self.unused)
def write(self, stream: OutputStream): stream.put_u8(self.config) stream.put_u8(self.unrunnable) stream.put_u16(self.surprise_chance) for data in self.groups: data.write(stream)
def parse(source: str, base_addr: int, debug=False) -> bytearray: symbol_table = {} icode = [] current_addr = base_addr for line_number, line in enumerate(source.splitlines()): tokens = TokenStream(line_number, line) token = tokens.next() if token is None: # Empty or comment only line continue if isinstance(token, RawCommandToken): parameters = [] token = tokens.expect(GRAMMAR["$$value$$"]) while token is not None: if isinstance(token, SymbolToken): if token in symbol_table: parameters.append(symbol_table[token]) else: raise SymbolNotDefinedError(token, line, line_number) else: parameters.append(token) token = tokens.expect(GRAMMAR["$$value$$"]) icode.append(parameters) current_addr += parameters[1] else: # Save the op name op_name = token if type(token) not in GRAMMAR: raise ParserSyntaxError(token, line, line_number) match = GRAMMAR[type(token)] if isinstance(match, dict): rule_set = match["rule"] else: rule_set = match parameters = [] if rule_set is not None: for rule in rule_set: if isinstance(rule, str) and rule.startswith("$$"): rule = GRAMMAR[rule] token = tokens.expect(rule) if token is None: raise ParserSyntaxError(token, line, line_number) if isinstance(op_name, SymbolToken): parameters.append(token) else: if isinstance(token, SymbolToken): if token in symbol_table: parameters.append(symbol_table[token]) else: raise SymbolNotDefinedError( token, line, line_number) else: parameters.append(token) verify_end = tokens.expect(CommentToken()) else: verify_end = tokens.expect(CommentToken()) if op_name == "def_symbol" or op_name == "def_label": name = parameters[0] value = parameters[1] if name in symbol_table: raise DuplicateSymbolError(name, line, line_number) if isinstance(value, ColonToken): value = current_addr symbol_table[name] = value else: if isinstance(op_name, list): output = simple_gen(op_name, parameters) else: method = getattr(codegen, op_name) output = method(parameters) if output is not None: icode.append(output) current_addr += output[1] # At this point, all of the intermediate code is built and the only thing left is to resolve # the left over symbols, which will all bel labels. bytecode = OutputStream() for code in icode: txt = "" for bd in code: if isinstance(bd, LabelToken): label = bd if label not in symbol_table: raise UndefinedLabel(label) bytecode.put_u32(symbol_table[label]) txt += f"{label} ({hex(symbol_table[label])}) " else: txt += f"{hex(bd)} " bytecode.put_u8(bd) if debug: print(txt) # Done! return bytecode.get_buffer()
def write(self, stream: OutputStream): stream.put_u16(self.base_hp) stream.put_u16(self.base_mp) stream.put_u8(self.starting_spell_level) stream.put_u8(self.base_strength) stream.put_u8(self.base_agility) stream.put_u8(self.base_intellect) stream.put_u8(self.base_stamina) stream.put_u8(self.base_luck) stream.put_u8(self.base_accuracy) stream.put_u8(self.base_evade) stream.put_u8(self.base_mdef) stream.put_u8(self.weapon_id) stream.put_u8(self.armor_id) stream.put_u8(self.unused)