def _loop_quest_available_companions(*args): return StatementBlock( (try_for_range, ":i_stack", 0, ":num_stacks"), (party_stack_get_troop_id, ":stack_troop", "p_main_party", ":i_stack"), (troop_is_hero, ":stack_troop"), (is_between, ":stack_troop", companions_begin, companions_end), (store_character_level, ":stack_level", ":stack_troop"), # todo: what this 15 represent? that only +15 lvl heros can be used? (ge, ":stack_level", 15), # check that hero is not being used in another quest. (assign, ":is_quest_hero", 0), (try_for_range, ":i_quest", all_quests_begin, all_quests_end), (check_quest_active, ":i_quest"), (this_or_next|quest_slot_eq, ":i_quest", "slot_quest_target_troop", ":stack_troop"), (quest_slot_eq, ":i_quest", "slot_quest_object_troop", ":stack_troop"), (assign, ":is_quest_hero", 1), # todo: it was found: break the loop. (try_end), (eq, ":is_quest_hero", 0), StatementBlock(*args), (try_end), )
def resetInventory(): block = [] for slot in range(4): block += [ (agent_set_slot, ":agent_no", inventorySlot % slot, 0), ] return StatementBlock(*block)
def upgrade_tier(max_trials): return StatementBlock( # set the tier (assign, ":tier", 1), (try_for_range, ":unused", 0, max_trials), # upgrade with 10% chance (store_random_in_range, ":random_no", 0, 100), (le, ":random_no", 10), # select branch of the ugrade tree (store_random_in_range, ":random_no", 0, 2), (troop_get_upgrade_troop, ":upgrade_troop_no", ":troop_type", ":random_no"), (try_begin), # if chosen does not exist, set it to be the first branch. (le, ":upgrade_troop_no", 0), (troop_get_upgrade_troop, ":upgrade_troop_no", ":troop_type", 0), (try_end), # confirm that it still exists (i.e. not in the maximum) (gt, ":upgrade_troop_no", 0), # upgrade troop (val_add, ":tier", 1), (assign, ":troop_type", ":upgrade_troop_no"), (try_end), )
def memorizeInventory(): block = [] for slot in range(4): block += [ (try_begin), (eq, ":item_slot", slot), (agent_get_slot, ":item_stored", ":agent_no", inventorySlot % slot), (ge, ":item_stored", 0), (agent_set_slot, ":agent_no", inventorySlot % slot, ":item_id"), (try_end), ] return StatementBlock(*block)
def setWeaponOrderAny(): block = [ (set_show_messages, 0), ] for division in range(9): block += [ (try_begin), (class_is_listening_order, ":team_id", division), (team_give_order, ":team_id", division, mordr_use_any_weapon), (try_end), ] block += [ (set_show_messages, 1), ] return StatementBlock(*block)
def updateInventory(): block = [] for slot in range(4): block += [ (try_begin), (eq, ":item_slot", slot), (agent_get_slot, ":item_id", ":agent_no", inventorySlot % slot), (gt, ":item_id", 0), (try_begin), (eq, ":inventory_action", 1), #Restore (agent_equip_item, ":agent_no", ":item_id", ":item_slot"), (else_try), (eq, ":inventory_action", -1), #Clear (agent_unequip_item, ":agent_no", ":item_id", ":item_slot"), (try_end), (try_end), ] return StatementBlock(*block)
def _create_bounty_visitor(bounty_name, bounty_target): return StatementBlock( (try_begin), (check_quest_active, bounty_name), (neg | is_currently_night), (quest_slot_eq, bounty_name, "slot_quest_target_center", "$current_town"), (neg | check_quest_succeeded, bounty_name), (neg | check_quest_failed, bounty_name), (store_random_in_range, ":random", 0, 8), (try_begin), (eq, ":random", 0), (store_random_in_range, bounty_target, fugitives_begin, fugitives_end), (else_try), (eq, ":random", 1), (store_random_in_range, bounty_target, outlaws_begin, outlaws_end), (else_try), (eq, ":random", 2), (store_random_in_range, bounty_target, rogues_begin, rogues_end), (else_try), (eq, ":random", 3), (store_random_in_range, bounty_target, goblin_outlaws_begin, goblin_outlaws_end), (else_try), (eq, ":random", 4), (store_random_in_range, bounty_target, orc_outlaws_begin, orc_outlaws_end), (else_try), (eq, ":random", 5), (store_random_in_range, bounty_target, elf_outlaws_begin, elf_outlaws_end), (else_try), (eq, ":random", 6), (store_random_in_range, bounty_target, darkelf_outlaws_begin, darkelf_outlaws_end), (else_try), (store_random_in_range, bounty_target, saracen_outlaws_begin, saracen_outlaws_end), (try_end), (set_visitor, 45, bounty_target), (try_end), )
def updateInventoryDebug(): block = [] for slot in range(4): block += [ (try_begin), (eq, ":item_slot", slot), (agent_get_slot, ":item_id", ":agent_no", inventorySlot % slot), (gt, ":item_id", 0), (try_begin), (eq, ":inventory_action", 1), #Restore (agent_equip_item, ":agent_no", ":item_id", ":item_slot"), (str_store_item_name, s1, ":item_id"), (display_message, "@[DEBUG] {s0} eqipped {s1}"), (else_try), (eq, ":inventory_action", -1), #Clear (agent_unequip_item, ":agent_no", ":item_id", ":item_slot"), (str_store_item_name, s1, ":item_id"), (display_message, "@[DEBUG] {s0} uneqipped {s1}"), (try_end), (try_end), ] return StatementBlock(*block)
def _affect_morality_by_action(slot, slot_state, slot_value): return StatementBlock( (troop_slot_eq, ":npc", slot, ":action_type"), (troop_get_slot, ":value", ":npc", slot_value), (try_begin), (troop_slot_eq, ":npc", slot_state, tms_acknowledged), # npc is betrayed, major penalty to player honor and morale (troop_get_slot, ":grievance", ":npc", "slot_troop_morality_penalties" ), (val_mul, ":value", 2), (val_add, ":grievance", ":value"), (troop_set_slot, ":npc", "slot_troop_morality_penalties", ":grievance"), (else_try), (troop_slot_eq, ":npc", slot_state, tms_dismissed), # npc is quietly disappointed (troop_get_slot, ":grievance", ":npc", "slot_troop_morality_penalties" ), (val_add, ":grievance", ":value"), (troop_set_slot, ":npc", "slot_troop_morality_penalties", ":grievance"), (else_try), # npc raises the issue for the first time (troop_slot_eq, ":npc", slot_state, tms_no_problem), (gt, ":value", ":grievance_minimum"), (assign, "$npc_with_grievance", ":npc"), (assign, "$npc_grievance_string", ":action_string"), (assign, "$npc_grievance_slot", slot_state), (assign, ":grievance_minimum", ":value"), (assign, "$npc_praise_not_complaint", 0), (try_begin), (lt, ":value", 0), (assign, "$npc_praise_not_complaint", 1), (try_end), (try_end), )
from source.header_operations import * from source.header_common import * from source.header_dialogs import anyone, plyr from source.module_constants import villages_begin, villages_end from source.statement import StatementBlock quest_block = StatementBlock( (eq, ":quest_no", "qst_train_peasants_against_bandits"), (try_begin), (is_between, ":giver_center_no", villages_begin, villages_end), (store_skill_level, ":player_trainer", "skl_trainer", "trp_player"), (gt, ":player_trainer", 0), (store_random_in_range, ":quest_target_amount", 5, 8), (assign, ":quest_target_center", ":giver_center_no"), (assign, ":quest_expiration_days", 20), (assign, ":quest_dont_give_again_period", 60), # chief (assign, ":result", ":quest_no"), (try_end), ) dialogs = [ [ anyone, "village_elder_tell_mission", [(eq, "$random_quest_no", "qst_train_peasants_against_bandits")], "We are suffering greatly at the hands of a group of bandits. They take our " "food and livestock, and kill anyone who doesn't obey them immediately. " "Our men are angry that we cannot defend ourselves, but we are only " "simple farmers... However, with some help, I think that some of the "
quest = StatementBlock( (eq, ":quest_no", "qst_lend_companion"), (try_begin), (ge, "$g_talk_troop_faction_relation", 0), (party_get_num_companion_stacks, ":num_stacks", "p_main_party"), # count the number of available companions for the quest (assign, ":total_heroes", 0), _loop_quest_available_companions((val_add, ":total_heroes", 1),), # Skip if party has no eligible heroes (gt, ":total_heroes", 0), # select a random hero (:target_hero) (store_random_in_range, ":random_hero", 0, ":total_heroes"), (assign, ":target_hero", -1), (assign, ":total_heroes", 0), _loop_quest_available_companions( (val_add, ":total_heroes", 1), (gt, ":total_heroes", ":random_hero"), (assign, ":target_hero", ":stack_troop") # todo: break the loop or the last hero is always chosen ), # I'm almost certain that by construction it always finds, but well. (try_begin), (eq, ':target_hero', -1), (display_debug_message, "@qst_lend_companion quest failed to find " "a hero when it should."), (try_end), (neq, ':target_hero', -1), # build the quest (assign, ":quest_target_troop", ":target_hero"), (store_current_day, ":quest_target_amount"), (val_add, ":quest_target_amount", 8), (assign, ":quest_importance", 1), (assign, ":quest_xp_reward", 500), (assign, ":quest_gold_reward", 400), (assign, ":result", ":quest_no"), (assign, ":quest_dont_give_again_period", 25), (try_end), )
from source.header_dialogs import anyone, plyr from source.module_constants import companions_begin, companions_end from source.statement import StatementBlock trigger_dialog_block = StatementBlock( (eq, "$disable_sisterly_advice", 0), (eq, "$g_infinite_camping", 0), (gt, "$npc_with_sisterly_advice", 0), (try_begin), (main_party_has_troop, "$npc_with_sisterly_advice"), (neq, "$g_player_is_captive", 1), (assign, "$npc_map_talk_context", "slot_troop_woman_to_woman_string"), (start_map_conversation, "$npc_with_sisterly_advice", -1), (else_try), (assign, "$npc_with_sisterly_advice", 0), (try_end), ) dialogs = [ [anyone, "event_triggered", [ (eq, "$npc_map_talk_context", "slot_troop_woman_to_woman_string"), (store_conversation_troop, "$map_talk_troop"), (is_between, "$map_talk_troop", companions_begin, companions_end),
recruiter_village_conditions = StatementBlock( # own village or village from faction with non-negative relations (store_faction_of_party, ":village_current_faction", ":village"), (store_relation, ":faction_relation", "$players_kingdom", ":village_current_faction"), (this_or_next | eq, ":village_current_faction", "$players_kingdom"), (ge, ":faction_relation", 0), # village with non-negative relations (party_get_slot, ":village_relation", ":village", "slot_center_player_relation"), (ge, ":village_relation", 0), # village with recruits (party_get_slot, ":volunteers_in_village", ":village", "slot_center_volunteer_troop_amount"), (gt, ":volunteers_in_village", 0), # village with correct recruits, if any (i.e. != -1) (party_get_slot, ":village_faction", ":village", "slot_center_original_faction"), (this_or_next | eq, ":recruit_faction", -1), (eq, ":village_faction", ":recruit_faction"), # village not under fire (neg | party_slot_eq, ":village", "slot_village_state", svs_looted), (neg | party_slot_eq, ":village", "slot_village_state", svs_being_raided), (neg | party_slot_ge, ":village", "slot_village_infested_by_bandits", 1), )
from source.header_operations import * from source.header_common import s5, s19, s20, s21, reg3 from source.header_dialogs import anyone, plyr, auto_proceed from source.module_constants import * from source.statement import StatementBlock trigger_event_block = StatementBlock( # it is on a mission (troop_slot_ge, ":npc", "slot_troop_current_mission", 1), # the hero is not in a rejoin mission or it can join the party (this_or_next|neg|troop_slot_eq, ":npc", "slot_troop_current_mission", npc_mission_rejoin_when_possible), (hero_can_join, "p_main_party"), (assign, "$npc_to_rejoin_party", ":npc"), ) (eq, "$talk_context", tc_tavern_talk), (neg|troop_is_hero, "$g_talk_troop"), trigger_dialog_block = StatementBlock( (gt, "$npc_to_rejoin_party", 0), (eq, "$g_infinite_camping", 0), (try_begin), (neg|main_party_has_troop, "$npc_to_rejoin_party"), (neq, "$g_player_is_captive", 1), (assign, "$npc_map_talk_context", "slot_troop_days_on_mission"),
(party_set_name, ":spawned_party", "@{s5} patrol"), (party_set_ai_behavior, ":spawned_party", ai_bhvr_travel_to_party), (party_set_ai_object, ":spawned_party", ":target_party"), (party_set_slot, ":spawned_party", "slot_party_ai_object", ":target_party"), (party_set_slot, ":spawned_party", "slot_party_ai_state", spai_patrolling_around_center), (call_script, "script_party_add_party", ":spawned_party", ":party_no"), ]), ] consequences_battle_lost = StatementBlock( (try_begin), (party_slot_eq, ":root_defeated_party", "slot_party_type", spt_patrol), (party_slot_eq, ":root_defeated_party", "slot_party_mission_diplomacy", "trp_player"), (party_get_slot, ":target_party", ":root_defeated_party", "slot_party_ai_object"), (str_store_party_name, s13, ":target_party"), (display_log_message, "@Your soldiers patrolling {s13} have been defeated {s10}!", 0xFF0000), (try_end), ) consequences_player_disbands = StatementBlock( (try_for_parties, ":party_no"), (party_slot_eq, ":party_no", "slot_party_type", spt_patrol), (party_slot_eq, ":party_no", "slot_party_mission_diplomacy", "trp_player"), (party_get_slot, ":target_party", ":party_no", "slot_party_ai_object"), (str_store_party_name, s6, ":target_party"), (display_log_message, "@Your soldiers patrolling {s6} disbanded because you left the faction!", 0xFF0000), (remove_party, ":party_no"), (try_end), )
(try_end), (troop_set_slot, ":companion_1", "slot_troop_personalityclash_penalties", ":grievance_1"), (troop_set_slot, ":companion_2", "slot_troop_personalityclash_penalties", ":grievance_2"), ]), ] trigger_dialog_block = StatementBlock( (eq, "$disable_npc_clashes", 0), (gt, "$npc_with_personality_clash", 0), (eq, "$g_infinite_camping", 0), (troop_get_slot, ":object", "$npc_with_personality_clash", "slot_troop_personalityclash_object"), (try_begin), (main_party_has_troop, "$npc_with_personality_clash"), (main_party_has_troop, ":object"), (neq, "$g_player_is_captive", 1), (assign, "$npc_map_talk_context", "slot_troop_personalityclash_state"), (start_map_conversation, "$npc_with_personality_clash", -1), (else_try), (assign, "$npc_with_personality_clash", 0), (try_end), ) dialogs = [ # Personality clash 2 objections [anyone, "event_triggered", [ (store_conversation_troop, "$map_talk_troop"), (is_between, "$map_talk_troop", companions_begin, companions_end),
from source.header_operations import * from source.header_common import * from source.header_dialogs import anyone, plyr from source.module_constants import villages_begin, villages_end, \ logent_helped_peasants from source.statement import StatementBlock quest_block = StatementBlock( (eq, ":quest_no", "qst_deliver_grain"), (try_begin), (is_between, ":giver_center_no", villages_begin, villages_end), (call_script, "script_get_troop_item_amount", ":giver_troop", "itm_grain"), (eq, reg0, 0), (neg | party_slot_ge, ":giver_center_no", "slot_town_prosperity", 40), (assign, ":quest_target_center", ":giver_center_no"), (store_random_in_range, ":quest_target_amount", 4, 8), (assign, ":quest_expiration_days", 30), (assign, ":quest_dont_give_again_period", 25), (assign, ":result", ":quest_no"), (try_end), ) dialogs = [ [ anyone, "village_elder_tell_mission", [(eq, "$random_quest_no", "qst_deliver_grain")], "{My good sir/My good lady}, our village has been going through such " "hardships lately. The harvest has been bad, and recently some merciless " "bandits took away our seed grain that we had reserved for the planting " "season. If we cannot find some grain soon, we will not be able to plant "
from source.statement import StatementBlock trigger_event_block = StatementBlock( # updates objection state (try_begin), (troop_slot_ge, ":npc", "slot_troop_days_on_mission", 5), (troop_slot_eq, ":npc", "slot_troop_current_mission", npc_mission_kingsupport), (troop_get_slot, ":other_npc", ":npc", "slot_troop_kingsupport_opponent"), (troop_slot_eq, ":other_npc", "slot_troop_kingsupport_objection_state", 0), (troop_set_slot, ":other_npc", "slot_troop_kingsupport_objection_state", 1), (try_begin), (eq, "$cheat_mode", 1), (str_store_troop_name, s3, ":npc"), (str_store_troop_name, s4, ":other_npc"), (display_message, "str_s4_ready_to_voice_objection_to_s3s_mission_if_in_party"), (try_end), (try_end), (try_begin), (main_party_has_troop, ":npc"), (try_begin), (eq, "$npc_with_political_grievance", 0), (troop_slot_eq, ":npc", "slot_troop_kingsupport_objection_state", 1), (assign, "$npc_with_political_grievance", ":npc"), (try_end), (try_end), ) trigger_dialog_block = StatementBlock(
from source.header_dialogs import anyone, plyr from source.module_constants import villages_begin, villages_end, \ village_elders_begin, village_elders_end, \ logent_helped_peasants from source.statement import StatementBlock quest_block = StatementBlock( (eq, ":quest_no", "qst_deliver_cattle"), (try_begin), (is_between, ":giver_center_no", villages_begin, villages_end), (party_get_slot, ":num_cattle", ":giver_center_no", "slot_village_number_of_cattle"), (lt, ":num_cattle", 50), (assign, ":quest_target_center", ":giver_center_no"), (store_random_in_range, ":quest_target_amount", 5, 10), (assign, ":quest_expiration_days", 30), (assign, ":quest_dont_give_again_period", 25), # chief gdw (assign, ":result", ":quest_no"), (try_end), ) dialogs = [ [ anyone, "village_elder_tell_mission", [(eq, "$random_quest_no", "qst_deliver_cattle")], "Bandits have driven away our cattle. Our pastures are empty. If we had " "just a few heads of cattle we could start to raise a herd again.", "village_elder_tell_deliver_cattle_mission", [
from source.header_operations import * from compiler import Compiler from source.statement import StatementBlock compiler = Compiler('./output', log_dir='./logs') result1 = compiler.process_statement_block(0, 1, [ (assign, ":net_change", 0), (try_begin), (eq, ":net_change", 0), (assign, ":net_change", 1), (end_try), ]) result2 = compiler.process_statement_block(0, 1, [(assign, ":net_change", 0), StatementBlock( (try_begin), (eq, ":net_change", 0), (assign, ":net_change", 1), (end_try), )]) assert (result2 == result1)
from source.header_troops import ca_intelligence from source.statement import StatementBlock from ..module_constants import * trigger_event_block = StatementBlock( (try_begin), (main_party_has_troop, ":npc"), (try_begin), (call_script, "script_npc_morale", ":npc"), (assign, ":npc_morale", reg0), # todo: this never happens: P[x < a] = 0 when x ~ U(a, 1+a) (lt, ":npc_morale", 20), # random ~ U(0, 1) (store_random_in_range, ":random", 0, 100), # random ~ U(a, 1 + a) (val_add, ":npc_morale", ":random"), # random < a never happens (lt, ":npc_morale", 20), (assign, "$npc_is_quitting", ":npc"), (try_end), (try_end), ) trigger_dialog_block = StatementBlock( (gt, "$npc_is_quitting", 0), (eq, "$g_infinite_camping", 0), (try_begin), (main_party_has_troop, "$npc_is_quitting"),
"want to recruit new troops or get detailed information about your standing army.", "none", [], [ ("dplmc_continue", [], "Continue...", [ (change_screen_return), ]), ]), ] \ + scouts.menus # this block is added to the enter_court script to add the constable to the scene. court_visitor = StatementBlock( (try_begin), (gt, "$g_player_constable", 0), # todo: this is wrong: appoint constable should not be here (call_script, "script_dplmc_appoint_constable" ), #fix for wrong troops after update (party_get_slot, ":town_lord", ":center_no", "slot_town_lord"), (eq, ":town_lord", "trp_player"), (set_visitor, ":cur_pos", "$g_player_constable"), (val_add, ":cur_pos", 1), (try_end), ) consequences_give_center = StatementBlock( (try_begin), (eq, "$g_constable_training_center", ":center_no"), (assign, "$g_constable_training_center", -1), (try_end), ) consequences_staff_salary = StatementBlock( (try_begin),
from source.module_constants import villages_begin, villages_end, \ village_elders_begin, village_elders_end, fire_duration from source.statement import StatementBlock village_elder_talk_condition = StatementBlock( (party_get_slot, ":bound_center", "$current_town", "slot_village_bound_center"), (assign, ":num_heroes_in_dungeon", 0), (assign, ":num_heroes_given_parole", 0), (party_get_num_prisoner_stacks, ":num_stacks", ":bound_center"), (try_for_range, ":i_stack", 0, ":num_stacks"), (party_prisoner_stack_get_troop_id, ":stack_troop", ":bound_center", ":i_stack"), (troop_is_hero, ":stack_troop"), (try_begin), (call_script, "script_cf_prisoner_offered_parole", ":stack_troop"), (party_add_members, "p_temp_party_2", ":stack_troop", 1), (val_add, ":num_heroes_given_parole", 1), (else_try), (party_add_members, "p_temp_party", ":stack_troop", 1), (val_add, ":num_heroes_in_dungeon", 1), (try_end), (try_end), (ge, ":num_heroes_in_dungeon", 1), ) dialogs = [ [ anyone, "village_elder_ask_set_fire", [
from source.header_operations import * from source.header_common import * from source.header_dialogs import * from source.statement import StatementBlock from source.module_constants import * from source.module_troops import troops from . import indict_vassal, emissary, change_marshal, grant_fief, persuade, center_captured_lord_advice, replace consequences_staff_salary = StatementBlock( (try_begin), (gt, "$g_player_minister", 0), (val_add, ":staff_salary", 15), (try_end), ) consequences_deactivate_faction = StatementBlock( # todo: confirm this is enough to stop all minister activity (e.g. quests) (try_begin), (is_between, "$g_player_minister", companions_begin, companions_end), (assign, "$npc_to_rejoin_party", "$g_player_minister"), (try_end), (assign, "$g_player_minister", -1), ) court_visitor = StatementBlock( (try_begin), (eq, "$g_player_court", ":center_no"),
def process_statement_block(self, statement_name, is_can_fail_statement, statement_block): self._current_statement_name = statement_name self._local_variables = OrderedDict() statement_block = StatementBlock(*statement_block) result = " %d " % len(statement_block) store_script_param_1_uses = 0 store_script_param_2_uses = 0 current_depth = 0 for index, statement in enumerate(statement_block): if isinstance(statement, StatementBlock): result += self._process_statement_piece(statement) continue if isinstance(statement, (tuple, list)): opcode = statement[0] else: opcode = statement if opcode in [ h_operations.try_begin, h_operations.try_for_range, h_operations.try_for_range_backwards, h_operations.try_for_parties, h_operations.try_for_agents, h_operations.try_for_attached_parties, h_operations.try_for_active_players, h_operations.try_for_prop_instances ]: current_depth += 1 elif opcode == h_operations.try_end: current_depth -= 1 elif opcode == h_operations.store_script_param_1 or \ (opcode == h_operations.store_script_param and statement[2] == 1): store_script_param_1_uses += 1 elif opcode == h_operations.store_script_param_2 or \ (opcode == h_operations.store_script_param and statement[2] == 2): store_script_param_2_uses += 1 elif current_depth == 0 and not is_can_fail_statement \ and (opcode in h_operations.can_fail_operations or ( opcode == h_operations.call_script and statement[1].startswith("cf_", 7))) \ and not statement_name.startswith("cf_"): logging.warning( 'Script "%s" can fail at operation %d. Use cf_ at ' 'the beginning of its name' % (statement_name, index)) result += self._process_statement(opcode, statement) if current_depth != 0: if current_depth > 0: logging.critical( 'Statement "%s" misses %d "try_end" statement_blocks' % (statement_name, current_depth)) else: logging.critical('Statement "%s" has %d "try_end" too many' % (statement_name, -current_depth)) if store_script_param_1_uses > 1: logging.error('store_script_param_1 used more than once in "%s"' % statement_name) if store_script_param_2_uses > 1: logging.error('store_script_param_2 used more than once in "%s"' % statement_name) for local_variable in self._local_variables: if self._local_variables[local_variable] <= 0 and not \ local_variable.startswith("unused"): logging.warning( 'Local variable "%s" unused at statement "%s"' % (local_variable, statement_name)) if len(self._local_variables) > 128: logging.warning('Script "%s" uses %d>128 local wariables' % (statement_name, len(self._local_variables))) self._current_statement_name = 'unknown' return result